宜昌老张

Processing练习——圆球移动

0
阅读(7268)

     最近做了一个Processing的小例子,练练手了。体察下鼠标动作如何与Processing画面各图形互动。

    画面中,一条直线上方一个圆球向左或向右移动,按下直线下方的"Left_Reset"按钮,圆球回到左边初始位置,这时如果按下"Start"按钮,圆球向右移动,直至从画面消失。按下直线下方的"Right_Reset"按钮,圆球回到右边初始位置,这时如果按下"Start"按钮,圆球向左移动。并且,当用鼠标拖动圆球边沿时,圆球会随之放大或缩小。

    我还发现了一个网站,它把Processing函数参考手册翻译成了中文,这真是创客精神的体现,分享和互助。

    网址:http://hiprocessing.net/

    把下面程序复制到Processing 2.2.1编程环境,试试。

    Processing 2.2.1下载:https://www.processing.org/download/?processing

注意:新版Processing 2.2.1可以显示中文注释了,点击File→Preferences。把“Editor and Consoles font”字体切换为“宋体”即可,另外下面的“font size”字体尺寸也可以修改,数字越大,字体尺寸越大。


Processing程序:

int x,y,r;
float move =0;            //圆球相对于初始位置移动的距离
String move_state ="Stop";//圆球的移动状态,即“Start”或“Stop”
char move_DIR ='L';       //圆球的移动方向,即'L' 或 'R'
//初始化
void setup(){
  size(500,300);//设置画布尺寸为X像素500,Y像素300
  smooth();     //设置轮廓线条为光滑     
  noStroke();//设置绘制的图形不显示轮廓线
  textSize(16);//字体大小为像素16
  textAlign(CENTER);//字体中央对齐
  ellipseMode(RADIUS);//设置椭圆的第3、4参数为半径尺寸
  rectMode(CENTER);  
  x =50;//圆球中心的初始位置
  y =height/2;
  r =12;//圆球的初始半径  
}

//主程序
void draw(){
  background(204);//循环刷背景  
  button_draw();//调用按钮绘制子函数
  fill(0,0,255);  //绘制的狭长水平矩形条的填充色为蓝色
  rect(width/2,height/2+5,width,10);//绘制的狭长水平矩形条 
  fill(255,0,255);//绘制的圆球的填充色为紫色  
  //如果鼠标按下,同时鼠标位置在画布的上半部
  if(mousePressed==true  && mouseY <=height/2){
    //测得鼠标光标与圆球中心的尺寸,
    //该尺寸为圆球的实时半径
    r =(int)dist(mouseX,mouseY,x,y-r);
    //如果实时半径超过40,则半径固定为40
    if(r >40) r=40;
    //如果实时半径小于20,则半径固定为20
    if(r <20) r=20; 
    //以测得鼠标光标与圆球中心的尺寸为半径,画圆
    ellipse(x,y-r,r,r);
    println(r);//把半径r送到控制台显示    
  }
  //如果鼠标按下,同时鼠标位置位于"Start"按钮图形区域内,
  //圆球开始移动
  if(mousePressed ==true && overRect() =="Start"){
    move_state="Start";  //设置圆球状态为“活动”  
  }
 //如果鼠标按下,同时鼠标位置位于"Left_Reset"按钮图形区域内,
 //圆球回到左边初始位置
  if(mousePressed ==true && overRect() =="Left_Reset"){
     move_DIR='L'; //设置圆球状态为“静止”
     move_state="Stop";   
  }
  //如果鼠标按下,同时鼠标位置位于"Right_Reset"按钮图形区域内,
  //圆球回到右边初始位置,同时设置圆球状态为“静止”。
  if(mousePressed ==true && overRect() =="Right_Reset"){
     move_DIR='R'; //设置圆球状态为“静止”
     move_state="Stop";    
  }  
  //如果圆球状态为“静止”,则圆球回到左边初始位置
  if(move_state=="Stop" && move_DIR =='L'){ 
    x =50; //圆球初始位置回到左边
    move=0;//圆球相对于初始位置移动的距离归零
    ellipse(x+move,y-r,r,r);    
  }
  //如果圆球状态为“静止”,则圆球回到右边初始位置
  if(move_state=="Stop" && move_DIR =='R'){ 
    x =450; //圆球初始位置回到右边
    move=0; //圆球相对于初始位置移动的距离归零
    ellipse(x+move,y-r,r,r);    
  }  
  //如果圆球状态为“活动”,同时圆球处于左边初始位置,
  //则圆球以步数为两个像素的速度向右移动
  if(move_state=="Start" && move_DIR =='L'){
    move +=2;
    ellipse(x+move,y-r,r,r);   
  }
  //如果圆球状态为“活动”,同时圆球处于右边初始位置,
  //则圆球以步数为两个像素的速度向左移动
  if(move_state=="Start" && move_DIR =='R'){
    move -=2;
    ellipse(x+move,y-r,r,r);   
  }
}

//按钮绘制子函数
void button_draw(){
  fill(255,255,255);  //填充色为白色
  rect(width/5,height/2+50,100,50);//绘制矩形按钮
  fill(0);  //矩形按钮上的文字为Start
  text("Start",width/5,height/2+50);
  fill(255,255,255);  //填充色为白色 
  rect(width*2.5/5,height/2+50,100,50);//绘制矩形按钮
  fill(0);   //矩形按钮上的文字为Reset
  text("Left_Reset",width*2.5/5,height/2+50);
  fill(255,255,255);  //填充色为白色 
  rect(width*4/5,height/2+50,100,50);//绘制矩形按钮
  fill(0);   //矩形按钮上的文字为Reset
  text("Right_Reset",width*4/5,height/2+50);
}  

// 子函数用于判断鼠标光标位于哪个按钮矩形框中,并返回按钮“名称”值
String overRect() {
  //如果鼠标位置位于"Start"按钮图形区域内,则子函数返回值为"Start"
  if(mouseY >height/2+25 && mouseY < height/2+75){
    if(mouseX > width/5-50 && mouseX < width/5+50){
      return "Start";
    }
    //如果鼠标位置位于"Left_Reset"按钮图形区域内,
    //则子函数返回值为"Left_Reset"
    else if(mouseX > width*2.5/5-50 && mouseX < width*2.5/5+50){
      return "Left_Reset";
    }
    //如果鼠标位置位于"Right_Reset"按钮图形区域内,
    //则子函数返回值为"Right_Reset"
    else if(mouseX > width*4/5-50 && mouseX < width*4/5+50){
      return "Right_Reset";
    }
    //否则子函数返回值为"none"
    else {
    return "none";
    }
  }
  //否则子函数返回值为"none"
  else {
    return "none";
  }
}

    编程中,程序的可读性还是很重要的,对于可读性,我认为编程要注意以下几点:

1、变量名和变量参数都应该注意可读性,变量名以"英文_英文_英文“形式来表达,例如:move_state。为了增加可读性,变量参数可以用字符和字符串。

2、函数名应该注意可读性,变量名以"英文_英文_英文“形式来表达,例如void button_draw()。

3、主程序与子函数的关系就像建筑体与建筑模块的关系,主程序应该着重展示建筑模块之间的搭建逻辑,所以如果主程序中某些语句并不能展示模块之间的搭建逻辑,那么这些语句也应该想办法打包成子函数。这样才能使主程序条理清晰,可读性好。

4、子程序中不能有全局变量,子程序与调用它的程序之间的数据交流,只能通过它的输入输出参数来完成。

5、程序开始时的变量,要注释;每一个程序段前面都要有注释,解释这个程序段的作用;每个子函数要注释,解释子函数的作用;重要的和特殊的语句,要注释。