加载中…
个人资料
  • 博客等级:
  • 博客积分:
  • 博客访问:
  • 关注人气:
  • 获赠金笔:0支
  • 赠出金笔:0支
  • 荣誉徽章:
正文 字体大小:

Processing中制作光晕(发光)效果及导出动画为gif

(2014-05-20 14:01:31)
标签:

processing

设计与编程

ae

镂空透光

教程

分类: Processing笔记
http://s14/mw690/003yPQBJzy6J1lmU2EB9d&690
http://s9/bmiddle/003yPQBJzy6J1lVqs2If8&690

画出光晕效果的原理很简单,就是计算平面上每一个点到“光源点”的距离,然后根据距离远近给每一个点分配颜色。在距离==>颜色的转换过程中加入一两个简单的函数(比如,倒数,倍数,平方等)就可以轻易控制“发光点”的大小和光晕的大小。

如何让光源动起来?每一帧在内存里(PGraphics,PImage)里画出来就好啦,然后呈现在画布上,每一帧里光源位置不同,最终呈现效果就是动起来。

在这个过程中可以在内存在再载入另一张图片(比如logo),逐个扫描PGraphics像素的时候顺便在同一个循环里扫描logo图片的像素,logo里不透光的地方就让PGraphics里的相对应像素保持黑色,logo里透光的地方就为PGraphics里的对应像素根据距离计算相应的颜色,最终就能得到题图那样的“镂空透光”效果。同样原理可以用于制作文字。


基本代码和注释:
PVector loc=new PVector(0,height/3*2);     //光源点起始位置
PVector mov=new PVector(5,-2);     //控制光源点移动的速度和方向
PGraphics glow;     //内存里绘制的图片
float distance;     //计算平面各点到光源点的距离

void setup(){
  size(600,400);
  glow=createGraphics(600,400);
}

void draw(){
  loc.add(mov);     //把光源点控制在画布内
  if (loc.x < 0) { mov.x *= -1; }
  if (loc.x > width) { mov.x *= -1; }
  if (loc.y < 0) { mov.y *= -1; }
  if (loc.y > height) { mov.y *=-1; }
 
  glow.beginDraw();
  for(int i=0;i
    for(int j=0;j
        distance=dist(i,j,loc.x,loc.y);    //计算平面各点到光源点的距离
        //distance=sq(distance);    //可以去掉双斜线看看平方后的效果
        distance=20000/distance;     //试着修改20000为其他数字看看效果
        color cl=color(0,distance,distance);     //试着摆弄下颜色里的参数看看变化
        glow.set(i,j,cl);     //染色
    }
  }
  glow.endDraw();
 
  image(glow,0,0);
  //saveFrame("frames/###.png");
}
运行后得到第二张图片的效果。


图一logo镂空透光效果用到的原材料和代码如下:
http://s2/mw690/003yPQBJzy6J1oaTMLT01&690
//import gifAnimation.*;

PImage logo;
PVector loc=new PVector(width/3,height/2);
PVector mov=new PVector(3,2);
PGraphics glow;
float distance;
//GifMaker halo;

void setup(){
  logo=loadImage("logo.jpg");
  logo.filter(GRAY);       //图片变为灰阶
  logo.filter(THRESHOLD,0.5);     //图片变为黑白两色
  size(logo.width,logo.height);
  glow=createGraphics(width,height);
  frameRate(24);
 
//  halo=new GifMaker(this,"logoShine.gif");
//  halo.setRepeat(0);
}

void draw(){
  loc.add(mov);
  if (loc.x < 0) { mov.x *= -1; }
  if (loc.x > width) { mov.x *= -1; }
  if (loc.y < 0) { mov.y *= -1; }
  if (loc.y > height) { mov.y *=-1; }
 
  glow.beginDraw();
  for(int i=0;i
    for(int j=0;j
      if(logo.get(i,j)==color(0)){     //如果在logo里该点是黑色的(不透光)
        glow.set(i,j,color(0));          //就把PGraphics里的该点设置为黑色。
      }else{                                   //否则,
        distance=(dist(i,j,loc.x,loc.y));
        distance=20000/distance;
        color cl=color(distance,0,0);
        glow.set(i,j,cl);               //就是透光效果
      }     
    }
  }
  glow.endDraw();
 
  image(glow,0,0);
  //saveFrame("frames/###.png");
//  halo.setDelay(1);
//  halo.addFrame();
}


关于导出动画为gif:
方法一,用Processing内置的movie maker 生成mov格式的视频后再用格式转化软件转成gif:
1.第二段代码中倒数第四行saveFrame加入运行,在文件夹里得到一大批帧图片存在一个叫frames的文件夹里,点击tools/movie maker,文件夹拖进去,设置好分辨率和帧率就可以点击生成视频。
2.上一步生成的视频效果挺好的,但是当我用格式工厂转换为gif格式后效果就有些惨不忍睹了,如下:
http://s14/mw690/003yPQBJzy6J1xl3jkN2d&690


*注意:在Windows上使用movie maker前需要安装苹果的QuickTime(Mac已内置)
*注意:理论上png,tif,tga格式的帧图片都能用来视频,但在实际使用中发现只有png可以,tif和tga生成的视频始终是黑屏。但在从sketch到帧图片这个过程中,生成png图片又比生成另外两种要慢。这个问题可以通过设置movie maker里的帧率来解决。

方法二,安装一个叫做gifAnimation的库。
1.sketch/import library, 然后找到gifAnimation并安装。
2.把第二段代码中关于“gif”和“halo”的那几行代码解除注释。
3.运行代码并关闭后就能在文件夹里找到gif文件,效果较上面那个较好,但还是不如视频的效果啊。


0

阅读 收藏 喜欢 打印举报/Report
  

新浪BLOG意见反馈留言板 欢迎批评指正

新浪简介 | About Sina | 广告服务 | 联系我们 | 招聘信息 | 网站律师 | SINA English | 产品答疑

新浪公司 版权所有