@@ -41,7 +41,78 @@ function setup() { |
| 41 | 41 | currentSkyColor1 = skyColor1; |
| 42 | 42 | currentSkyColor2 = skyColor2; |
| 43 | 43 | |
| 44 | | - spider = new Spider(width / 2, height - 50); |
| 44 | + // Create home branch for spider |
| 45 | + let homeBranchSide = random() < 0.5 ? 'left' : 'right'; |
| 46 | + let homeBranchLength = random(width * 0.33, width * 0.5); |
| 47 | + let homeBranchY = random(height * 0.7, height * 0.85); |
| 48 | + let homeBranchThickness = 25; |
| 49 | + |
| 50 | + // Generate twigs and leaves once during setup |
| 51 | + let twigs = []; |
| 52 | + let numTwigs = 5; |
| 53 | + for (let i = 0; i < numTwigs; i++) { |
| 54 | + twigs.push({ |
| 55 | + t: random(0.2, 0.8), |
| 56 | + length: random(20, 40), |
| 57 | + angle: random(-PI/3, -PI/6) * (homeBranchSide === 'right' ? -1 : 1), |
| 58 | + subTwigs: [ |
| 59 | + { pos: 0.7, length: 5, angle: -5 }, |
| 60 | + { pos: 0.5, length: 4, angle: 4 } |
| 61 | + ] |
| 62 | + }); |
| 63 | + } |
| 64 | + |
| 65 | + let leaves = []; |
| 66 | + for (let i = 0; i < 3; i++) { |
| 67 | + leaves.push({ |
| 68 | + t: random(0.3, 0.7), |
| 69 | + yOffset: random(-homeBranchThickness, -homeBranchThickness * 2), |
| 70 | + rotation: random(-PI/4, PI/4), |
| 71 | + width: 15, |
| 72 | + height: 8 |
| 73 | + }); |
| 74 | + } |
| 75 | + |
| 76 | + let barkTextures = []; |
| 77 | + let startX = homeBranchSide === 'left' ? -20 : width + 20; |
| 78 | + let endX = homeBranchSide === 'left' ? homeBranchLength : width - homeBranchLength; |
| 79 | + for (let x = Math.min(startX, endX); x < Math.max(startX, endX); x += 20) { |
| 80 | + barkTextures.push({ |
| 81 | + x: x, |
| 82 | + yOff: random(-homeBranchThickness/3, homeBranchThickness/3), |
| 83 | + endYOff: random(-5, 5) |
| 84 | + }); |
| 85 | + } |
| 86 | + |
| 87 | + // Store home branch info for rendering |
| 88 | + window.homeBranch = { |
| 89 | + side: homeBranchSide, |
| 90 | + startX: startX, |
| 91 | + endX: endX, |
| 92 | + y: homeBranchY, |
| 93 | + thickness: homeBranchThickness, |
| 94 | + angle: random(-0.1, 0.1), // Slight angle for natural look |
| 95 | + twigs: twigs, |
| 96 | + leaves: leaves, |
| 97 | + barkTextures: barkTextures |
| 98 | + }; |
| 99 | + |
| 100 | + // Place spider on the home branch |
| 101 | + let spiderStartX = homeBranchSide === 'left' ? |
| 102 | + homeBranchLength * 0.8 : |
| 103 | + width - homeBranchLength * 0.8; |
| 104 | + spider = new Spider(spiderStartX, homeBranchY - 15); |
| 105 | + |
| 106 | + // Add invisible obstacles along the branch for web anchor points |
| 107 | + let numBranchAnchors = 3; |
| 108 | + for (let i = 0; i < numBranchAnchors; i++) { |
| 109 | + let t = (i + 1) / (numBranchAnchors + 1); |
| 110 | + let x = homeBranchSide === 'left' ? |
| 111 | + homeBranchLength * t : |
| 112 | + width - homeBranchLength * t; |
| 113 | + let y = homeBranchY + sin(t * PI) * 10; // Slight curve |
| 114 | + obstacles.push(new Obstacle(x, y, 20, 'branch')); |
| 115 | + } |
| 45 | 116 | |
| 46 | 117 | // Create obstacles with better distribution |
| 47 | 118 | let numObstacles = Math.floor((width * height) / 60000); |
@@ -252,17 +323,106 @@ function drawSkyGradient() { |
| 252 | 323 | stroke(c); |
| 253 | 324 | line(0, i, width, i); |
| 254 | 325 | } |
| 326 | + |
| 327 | + // Draw home branch |
| 328 | + if (window.homeBranch) { |
| 329 | + push(); |
| 330 | + let branch = window.homeBranch; |
| 331 | + |
| 332 | + // Main branch |
| 333 | + strokeWeight(branch.thickness); |
| 334 | + if (gamePhase === 'NIGHT') { |
| 335 | + stroke(30, 15, 0); |
| 336 | + } else { |
| 337 | + stroke(101, 67, 33); |
| 338 | + } |
| 339 | + |
| 340 | + // Draw main branch with slight curve |
| 341 | + push(); |
| 342 | + translate(0, branch.y); |
| 343 | + rotate(branch.angle); |
| 344 | + |
| 345 | + let startX = branch.startX; |
| 346 | + let endX = branch.endX; |
| 347 | + let midX = (startX + endX) / 2; |
| 348 | + let midY = sin(PI * 0.5) * 15; // Slight sag in middle |
| 349 | + |
| 350 | + noFill(); |
| 351 | + beginShape(); |
| 352 | + curveVertex(startX, 0); |
| 353 | + curveVertex(startX, 0); |
| 354 | + curveVertex(midX, midY); |
| 355 | + curveVertex(endX, 0); |
| 356 | + curveVertex(endX, 0); |
| 357 | + endShape(); |
| 358 | + pop(); |
| 359 | + |
| 360 | + // Add texture and smaller branches |
| 361 | + push(); |
| 362 | + translate(0, branch.y); |
| 363 | + rotate(branch.angle); |
| 364 | + |
| 365 | + // Bark texture (using pre-generated positions) |
| 366 | + stroke(80, 50, 20, 100); |
| 367 | + strokeWeight(2); |
| 368 | + for (let texture of branch.barkTextures) { |
| 369 | + line(texture.x, texture.yOff, texture.x + 10, texture.yOff + texture.endYOff); |
| 370 | + } |
| 371 | + |
| 372 | + // Small twigs (using pre-generated positions) |
| 373 | + stroke(gamePhase === 'NIGHT' ? color(40, 20, 0) : color(101, 67, 33)); |
| 374 | + strokeWeight(3); |
| 375 | + for (let twig of branch.twigs) { |
| 376 | + let twigX = lerp(startX, endX, twig.t); |
| 377 | + |
| 378 | + push(); |
| 379 | + translate(twigX, 0); |
| 380 | + rotate(twig.angle); |
| 381 | + line(0, 0, twig.length, 0); |
| 382 | + |
| 383 | + // Tiny sub-twigs |
| 384 | + strokeWeight(1); |
| 385 | + for (let subTwig of twig.subTwigs) { |
| 386 | + line(twig.length * subTwig.pos, 0, |
| 387 | + twig.length * subTwig.pos + subTwig.length, |
| 388 | + subTwig.angle); |
| 389 | + } |
| 390 | + pop(); |
| 391 | + } |
| 392 | + |
| 393 | + // Add leaves (using pre-generated positions) |
| 394 | + fill(gamePhase === 'NIGHT' ? color(20, 40, 20) : color(34, 139, 34)); |
| 395 | + noStroke(); |
| 396 | + for (let leaf of branch.leaves) { |
| 397 | + let leafX = lerp(startX, endX, leaf.t); |
| 398 | + |
| 399 | + push(); |
| 400 | + translate(leafX, leaf.yOffset); |
| 401 | + rotate(leaf.rotation); |
| 402 | + ellipse(0, 0, leaf.width, leaf.height); |
| 403 | + pop(); |
| 404 | + } |
| 405 | + |
| 406 | + pop(); |
| 407 | + pop(); |
| 408 | + } |
| 255 | 409 | } |
| 256 | 410 | |
| 257 | 411 | function drawMoon() { |
| 258 | 412 | push(); |
| 259 | 413 | noStroke(); |
| 260 | | - fill(255, 255, 230, moonOpacity); |
| 414 | + // Brighter moon |
| 415 | + fill(255, 255, 240, moonOpacity); |
| 261 | 416 | ellipse(width - 100, moonY, 50); |
| 262 | | - fill(255, 255, 200, moonOpacity * 0.3); |
| 417 | + // Brighter glow |
| 418 | + fill(255, 255, 220, moonOpacity * 0.5); |
| 263 | 419 | ellipse(width - 100, moonY, 70); |
| 420 | + // Extra outer glow for more brightness |
| 421 | + fill(255, 255, 200, moonOpacity * 0.2); |
| 422 | + ellipse(width - 100, moonY, 100); |
| 264 | 423 | |
| 265 | | - fill(230, 230, 200, moonOpacity * 0.5); |
| 424 | + // Moon craters with better contrast |
| 425 | + fill(240, 240, 210, moonOpacity * 0.7); |
| 266 | 426 | ellipse(width - 105, moonY - 5, 8); |
| 267 | 427 | ellipse(width - 95, moonY + 8, 12); |
| 268 | 428 | ellipse(width - 110, moonY + 10, 6); |