p5.js弹跳变色小球颜色被背景矩形覆盖问题求助
解决p5.js中小球撞边变色后被盒子fill覆盖的问题
你的问题根源在于p5.js的全局绘图状态:innerRect()函数里设置的fill(71, 71, 71)会覆盖之前changeColor()设置的填充色,而你当前的draw()顺序是先绘制背景(包含灰色盒子),再处理小球移动,最后画小球——此时绘图状态的fill还是盒子的灰色,所以小球会被画成灰色。
修复方案
- 用变量存储小球的颜色,而非直接通过
fill()设置全局状态 - 每次绘制小球前,主动设置小球的颜色,避免被其他绘图操作的fill覆盖
修改后的完整代码
// Bounce1 // 完美弹跳的小球,不会减速 // 画布和内部盒子参数 let canvasW = 900; let canvasH = 700; let innerborder = 100; // 小球的位置、大小、速度 let positionX = 300; let positionY = 300; let radius = 20; let velocityX = 3; let velocityY = 5; // 存储小球颜色,初始设一个默认色 let ballColor = color(255, 0, 0); function setup() { createCanvas(canvasW, canvasH); } function draw() { drawBackground(); moveBall(); drawBall(); } function drawBackground(){ background(220); innerRect(); } function innerRect(){ fill(71, 71, 71); rect(innerborder, 100, 700, 500); } function moveBall(){ // 更新小球位置 positionX += velocityX; positionY += velocityY; const rightEdge = width - 100; const leftEdge = 0 + 100; const topEdge = 0 + 100; const bottomEdge = height - 100; // 检测碰撞并反弹 if (positionX + radius > rightEdge) { velocityX *= -1; positionX = rightEdge - radius; changeColor(); } else if (positionX - radius < leftEdge) { velocityX *= -1; positionX = leftEdge + radius; changeColor(); } if (positionY + radius > bottomEdge) { velocityY *= -1; positionY = bottomEdge - radius; changeColor(); } else if (positionY - radius < topEdge) { velocityY *= -1; positionY = topEdge + radius; changeColor(); } } function drawBall(){ // 绘制小球前主动设置颜色 fill(ballColor); ellipse(positionX, positionY, radius * 2, radius * 2); } function changeColor(){ // 生成随机颜色并赋值给ballColor变量 let r = random(0, 255); let g = random(0, 255); let b = random(0, 255); ballColor = color(r, g, b); }
<script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.4.1/p5.js"></script>
关键改动说明
- 新增
ballColor变量专门存储小球的颜色,避免全局fill状态被其他绘图操作干扰 changeColor()不再直接调用fill(),而是更新ballColor的值drawBall()每次绘制前都会设置fill(ballColor),确保小球用自己的颜色绘制- 移除了原代码中多余的
change变量和noFill()逻辑,简化了碰撞处理流程
内容的提问来源于stack exchange,提问作者Hbomb02
相关产品推荐
相关产品推荐

