Monday 8 December 2008

Switch Block - First Draft

Version 3 is harder on the eyes
Our next type of code block uses a switch, to determine which block of code to run. In Java the switch value must be an integer, a byte, a short, char or enumerated type.
Its basic outline follows this pattern:

switch(int){
case 1:
statements;
break;
case 2:
case 3:
statements;
break;
case 4:
statements;
return(someValue);
case 9:
case 5:
default: statements;
}
In this example, if the switch statement has a value of 1, 3, or 4 then the statements in the case blocks for 1, 3 or 4 will execute. To stop them executing the code in the other cases, break is used to exit the switch. In the case of the switch having a value of 4 the loop is exited by returning a value. Break and return allow the switch block to be exited cleanly.
If switch has a value of 2 it doesnt have a code block of its own and continues so it executes the case 3 code block before exiting with break.
If the switch has a value of 5, 9 or some number that doesnt have a case statement then the default case will carried out before the block is exited. Notice that the order of the case statements doesnt matter, as can be seen with case 9.
Enumerated types can also be used and might be a nifty modification for chunk 16's program. We will just look at a simple example of how this could be implemented:
enum Shape{SQUARE, CIRCLE, CFILLED, SFILLED, LINE}
Shape currentShape=CFILLED;
switch(currentShape){
case CIRCLE: doThis; break;
case SQUARE: doThis; break;
case CFILLED: doThis; break;
default: println("Mot Implemented Yet!");//we add the default here //because we havent written the //code for the other cases yet
}
In chunk 16 we have a large case statement (Line 40) which has cases for switch values of 1-9.
The design variable used by the switch is a random number between 1 and 9 inclusive.
Lets try some modifications to make chunk 16 more maintainable.
We would prefer it if the pattern always starts with a plain black background! Remove the statement on line 36 and add background(0) at line 35.
So now we have:
//local variables
int count=0;
int design=0;
background(0);
for(count=0;count
at the start of the draw method.
We can remove the line code in case 5 to its own function(line 63). Lets try omitting the break statement so the lines function is always covered up by the pattern in case 6.
Wow that is much better! We will leave lines in now!

case 5: //lovely lines!
doLines();
case 6:
...
Place the doLines function with the other functions
void doLines(){
strokeWeight(getSW());
for(int b=1;b
int down=round(random(width/2));
int across=round(random(width/2));
line(xpos,ypos,across-b,down-b);
line(xpos,ypos,across+b+xpos,down-b);
line(xpos,ypos,across-b,width-down+b);
line(xpos,ypos,across+b+xpos,width-down+b);}
}
Looking at our case statements we can see that cases 1,3,4,6,7 and 9 all use some dupkicate code. Our switch block would be much neater and easier to maintain if we could encapsulate this mess in a function!
We will move case 1's code to a function to begin with...
case 1:
repeatShapes();
break;
Place the repeatShapes function with the other functions
void repeatShapes(){
while(interval
drawCircle2(interval-round(random(40,width/2)));
interval+=round(random(3,70)); }}
The code still works correctly when we run it so this change is ok
The only difference between case 1 and case 3 is the interval variable. We can accomodate this by passing it as a parameter to the repeatShapes function...
It is bow possible to remove all the while loops that use the drawCircles2 Function with the repeatShapes(gap) function. We are left with the while loops that use the drawSquares and drawCircle3 functions. Lets add a new parameter to the repeat shapes function so that we can deal with those cases too.
Right, phew we now have a very versatile repeatShapes function but(theres always a but!) the program takes about a second longer to start. We will ignore this for the moment...
We can remove the noFill() statements for the filled shape cases and replace them with a noFill() statement at the start of the for loop code block.
If the case that makes filled circles didnt change colour so often we might see some more interesting shapes created. I added a 50/50 chance of this happening, to the else statement in the drawShapes method. See if you can work out how this works in the repeatShapes function.
By tweaking and adjusting the repeatShapes function and removing some repetitive code from the case statements, our switch block now looks like this:
switch(design){
case 1:
repeatShapes(round(random(3,70)),'2');
break;
case 2:
drawCircles(round(random(20,round(random(1,50)))));
break;
case 3:
repeatShapes(round(random(1,width/2)),'2');
break;
case 4:
repeatShapes(width-round(random(2,width/4)),'3');
break;
case 5: //lovely lines!
doLines();
case 6:
repeatShapes(round(random(2,200)),'5');
break;
case 7:
repeatShapes(round(random(1,40)),'2');
break;
case 8:
default:
repeatShapes(width-round(random(1,width/2)),'4');
}
The one remaining change we could attempt is to do something about the cases where large filled shapes are drawn over the top of our funky patterns. Later in our lessons, we will learn how to use transparent colours, so for the moment lets leave our switch statement as it is.
If you examine the switch block in the getSW function, you may notice something strange... The whole switch block can be replaced by one statement!
The getSW function now looks like this:

int getSW(){
int fc=round(random(frameRate*500)/5);
return fc%10;
}
Our code is now much leaner ans easier to maintain now and this will help us when we start the next modification which will involve arrays.

No comments:

Post a Comment