目前,您直接将 squareY 增加 1 个像素。
理想情况下,您只需在想要移动方块时将其设置为 > 0 的值来控制速度,或者在您想要停止移动时将其重置为 0。
还有一些其他的东西可以让它变得更好,例如:
- 在检查方块是否在屏幕区域之外时使用方块的大小
- 记住正方形离开屏幕之前最后一个好的 y 位置,以便在翻转位置时重置位置。
这是您的草图的修改版本,其中包含上述注释以及以保持相关元素分组的方式命名变量:
int squarePositionX = 20;
int squarePositionY = 20;
int squareVelocityY = 0;
int squareLastGoodY = squarePositionY;
int squareSize = 70;
int squareSpeed = 9;
int circleX = 150;
void setup () {
size (700, 700);
}
void draw () {
// handle keys
if(keyPressed){
if(key == 'w'){
squareVelocityY = -squareSpeed;
}
if(key == 's'){
squareVelocityY = squareSpeed;
}
}else{
// reset velocity (stop square from moving)
squareVelocityY = 0;
}
// update big square position based on velocity
squarePositionY += squareVelocityY;
// check if square is still on screen (reset velocity if it's not otherwise keep track of it's last
if (squarePositionY >= width - squareSize || squarePositionY <= 0) {
// flip Y velocity
squareVelocityY *= -1;
// reset to last good known Y position
squarePositionY = squareLastGoodY;
}else{
squareLastGoodY = squarePositionY;
}
// clear screen
background (0);
// render big square
fill (225);
rect (squarePositionX, squarePositionY, squareSize, squareSize);
// render circle
fill(100);
ellipse (circleX, 140, 150, 150);
// update circle position
circleX -= 2;
if (circleX < - 20) {
circleX = 550;
}
}
希望 cmets 帮助更详细地解释发生了什么。
关于拍摄迷你方块,您需要跟踪每个迷你方块的位置。您可以使用数组和append() 在新子弹射击时扩展它,或者只使用具有动态大小的数组类型,例如ArrayList 或IntList。为了保持列表有效且不被屏幕区域之外的项目符号淹没,您可以对大方块进行类似的测试,以检查小方块何时从列表中移除。剩下要做的最后一件事就是简单地渲染小方块,只要它们可见。
这是一个注释草图来说明这个想法:
int squareSize = 70;
int squarePositionX = squareSize;
int squarePositionY = squareSize;
int squareVelocityY = 0;
int squareLastGoodY = squarePositionY;
int squareSpeed = 3;
int circleX = 150;
// store positions for
IntList miniSquarePositionsX = new IntList();
IntList miniSquarePositionsY = new IntList();
int miniSquareSpeed = 9;
int miniSquareSize = 35;
void setup () {
size (700, 700);
rectMode(CENTER);
}
void draw () {
// handle keys
if(keyPressed){
if(key == 'w' && key != ' '){
squareVelocityY = -squareSpeed;
}else
if(key == 's' && key != ' '){
squareVelocityY = squareSpeed;
}
}else{
// reset velocity (stop square from moving)
squareVelocityY = 0;
}
// update big square position based on velocity
squarePositionY += squareVelocityY;
// check if square is still on screen (reset velocity if it's not otherwise keep track of it's last
if (squarePositionY >= width - (squareSize * 0.5) || squarePositionY <= (squareSize * 0.5)) {
// flip Y velocity
squareVelocityY *= -1;
// reset to last good known Y position
squarePositionY = squareLastGoodY;
}else{
squareLastGoodY = squarePositionY;
}
// update mini squares: assumes the size of both x and y lists match
for(int i = 0 ; i < miniSquarePositionsX.size(); i++){
// update X position
miniSquarePositionsX.set(i, miniSquarePositionsX.get(i) + miniSquareSpeed);
// remove element if it's outside the screen
if(miniSquarePositionsX.get(i) > width){
miniSquarePositionsX.remove(i);
miniSquarePositionsY.remove(i);
}
}
// clear screen
background (0);
// render circle
fill(100);
ellipse (circleX, 140, 150, 150);
// render big square
fill (225);
rect (squarePositionX, squarePositionY, squareSize, squareSize);
// update circle position
circleX -= 2;
if (circleX < - 20) {
circleX = 550;
}
// render mini squares: assumes the size of both x and y lists match
for(int i = 0 ; i < miniSquarePositionsX.size(); i++){
rect(miniSquarePositionsX.get(i), miniSquarePositionsY.get(i), miniSquareSize, miniSquareSize);
}
}
void keyReleased(){
// SPACE key shoot
if(key == ' '){
// add position entries for a mini square
miniSquarePositionsX.append(squarePositionX);
miniSquarePositionsY.append(squarePositionY);
println(miniSquarePositionsY);
}
}
如果您熟悉面向对象编程 (OOP) 基础知识,则可以使用几个类很好地封装上述内容(例如“船”的 Square 类和“子弹”的 MiniSquare 类) .玩得开心!