asteroids.java
来自「很有趣的射击游戏」· Java 代码 · 共 1,251 行 · 第 1/3 页
JAVA
1,251 行
loaded = true; loadThread.stop(); } // This is the main loop. while (Thread.currentThread() == loopThread) { if (!paused) { // Move and process all sprites. updateShip(); updatePhotons(); updateUfo(); updateMissle(); updateAsteroids(); updateExplosions(); // Check the score and advance high score, add a new ship or start the flying // saucer as necessary. if (score > highScore) highScore = score; if (score > newShipScore) { newShipScore += NEW_SHIP_POINTS; shipsLeft++; } if (playing && score > newUfoScore && !ufo.active) { newUfoScore += NEW_UFO_POINTS; ufoPassesLeft = UFO_PASSES; initUfo(); } // If all asteroids have been destroyed create a new batch. if (asteroidsLeft <= 0) if (--asteroidsCounter <= 0) initAsteroids(); } // Update the screen and set the timer for the next loop. repaint(); try { startTime += DELAY; Thread.sleep(Math.max(0, startTime - System.currentTimeMillis())); } catch (InterruptedException e) { break; } } } public void loadSounds() { // Load all sound clips by playing and immediately stopping them. try { crashSound = getAudioClip(new URL(getDocumentBase(), "crash.au")); explosionSound = getAudioClip(new URL(getDocumentBase(), "explosion.au")); fireSound = getAudioClip(new URL(getDocumentBase(), "fire.au")); missleSound = getAudioClip(new URL(getDocumentBase(), "missle.au")); saucerSound = getAudioClip(new URL(getDocumentBase(), "saucer.au")); thrustersSound = getAudioClip(new URL(getDocumentBase(), "thrusters.au")); warpSound = getAudioClip(new URL(getDocumentBase(), "warp.au")); } catch (MalformedURLException e) {} crashSound.play(); crashSound.stop(); explosionSound.play(); explosionSound.stop(); fireSound.play(); fireSound.stop(); missleSound.play(); missleSound.stop(); saucerSound.play(); saucerSound.stop(); thrustersSound.play(); thrustersSound.stop(); warpSound.play(); warpSound.stop(); } public void initShip() { ship.active = true; ship.angle = 0.0; ship.deltaAngle = 0.0; ship.currentX = 0.0; ship.currentY = 0.0; ship.deltaX = 0.0; ship.deltaY = 0.0; ship.render(); if (loaded) thrustersSound.stop(); thrustersPlaying = false; hyperCounter = 0; } public void updateShip() { double dx, dy, limit; if (!playing) return; // Rotate the ship if left or right cursor key is down. if (left) { ship.angle += Math.PI / 16.0; if (ship.angle > 2 * Math.PI) ship.angle -= 2 * Math.PI; } if (right) { ship.angle -= Math.PI / 16.0; if (ship.angle < 0) ship.angle += 2 * Math.PI; } // Fire thrusters if up or down cursor key is down. Don't let ship go past // the speed limit. dx = -Math.sin(ship.angle); dy = Math.cos(ship.angle); limit = 0.8 * MIN_ROCK_SIZE; if (up) { if (ship.deltaX + dx > -limit && ship.deltaX + dx < limit) ship.deltaX += dx; if (ship.deltaY + dy > -limit && ship.deltaY + dy < limit) ship.deltaY += dy; } if (down) { if (ship.deltaX - dx > -limit && ship.deltaX - dx < limit) ship.deltaX -= dx; if (ship.deltaY - dy > -limit && ship.deltaY - dy < limit) ship.deltaY -= dy; } // Move the ship. If it is currently in hyperspace, advance the countdown. if (ship.active) { ship.advance(); ship.render(); if (hyperCounter > 0) hyperCounter--; } // Ship is exploding, advance the countdown or create a new ship if it is // done exploding. The new ship is added as though it were in hyperspace. // (This gives the player time to move the ship if it is in imminent danger.) // If that was the last ship, end the game. else if (--shipCounter <= 0) if (shipsLeft > 0) { initShip(); hyperCounter = HYPER_COUNT; } else endGame(); } public void stopShip() { ship.active = false; shipCounter = SCRAP_COUNT; if (shipsLeft > 0) shipsLeft--; if (loaded) thrustersSound.stop(); thrustersPlaying = false; } public void initPhotons() { int i; for (i = 0; i < MAX_SHOTS; i++) { photons[i].active = false; photonCounter[i] = 0; } photonIndex = 0; } public void updatePhotons() { int i; // Move any active photons. Stop it when its counter has expired. for (i = 0; i < MAX_SHOTS; i++) if (photons[i].active) { photons[i].advance(); photons[i].render(); if (--photonCounter[i] < 0) photons[i].active = false; } } public void initUfo() { double temp; // Randomly set flying saucer at left or right edge of the screen. ufo.active = true; ufo.currentX = -AsteroidsSprite.width / 2; ufo.currentY = Math.random() * AsteroidsSprite.height; ufo.deltaX = MIN_ROCK_SPEED + Math.random() * (MAX_ROCK_SPEED - MIN_ROCK_SPEED); if (Math.random() < 0.5) { ufo.deltaX = -ufo.deltaX; ufo.currentX = AsteroidsSprite.width / 2; } ufo.deltaY = MIN_ROCK_SPEED + Math.random() * (MAX_ROCK_SPEED - MIN_ROCK_SPEED); if (Math.random() < 0.5) ufo.deltaY = -ufo.deltaY; ufo.render(); saucerPlaying = true; if (sound) saucerSound.loop(); // Set counter for this pass. ufoCounter = (int) Math.floor(AsteroidsSprite.width / Math.abs(ufo.deltaX)); } public void updateUfo() { int i, d; // Move the flying saucer and check for collision with a photon. Stop it when its // counter has expired. if (ufo.active) { ufo.advance(); ufo.render(); if (--ufoCounter <= 0) if (--ufoPassesLeft > 0) initUfo(); else stopUfo(); else { for (i = 0; i < MAX_SHOTS; i++) if (photons[i].active && ufo.isColliding(photons[i])) { if (sound) crashSound.play(); explode(ufo); stopUfo(); score += UFO_POINTS; } // On occassion, fire a missle at the ship if the saucer is not // too close to it. d = (int) Math.max(Math.abs(ufo.currentX - ship.currentX), Math.abs(ufo.currentY - ship.currentY)); if (ship.active && hyperCounter <= 0 && ufo.active && !missle.active && d > 4 * MAX_ROCK_SIZE && Math.random() < .03) initMissle(); } } } public void stopUfo() { ufo.active = false; ufoCounter = 0; ufoPassesLeft = 0; if (loaded) saucerSound.stop(); saucerPlaying = false; } public void initMissle() { missle.active = true; missle.angle = 0.0; missle.deltaAngle = 0.0; missle.currentX = ufo.currentX; missle.currentY = ufo.currentY; missle.deltaX = 0.0; missle.deltaY = 0.0; missle.render(); missleCounter = 3 * Math.max(AsteroidsSprite.width, AsteroidsSprite.height) / MIN_ROCK_SIZE; if (sound) missleSound.loop(); misslePlaying = true; } public void updateMissle() { int i; // Move the guided missle and check for collision with ship or photon. Stop it when its // counter has expired. if (missle.active) { if (--missleCounter <= 0) stopMissle(); else { guideMissle(); missle.advance(); missle.render(); for (i = 0; i < MAX_SHOTS; i++) if (photons[i].active && missle.isColliding(photons[i])) { if (sound) crashSound.play(); explode(missle); stopMissle(); score += MISSLE_POINTS; } if (missle.active && ship.active && hyperCounter <= 0 && ship.isColliding(missle)) { if (sound) crashSound.play(); explode(ship); stopShip(); stopUfo(); stopMissle(); } } } } public void guideMissle() { double dx, dy, angle; if (!ship.active || hyperCounter > 0) return; // Find the angle needed to hit the ship. dx = ship.currentX - missle.currentX; dy = ship.currentY - missle.currentY; if (dx == 0 && dy == 0) angle = 0; if (dx == 0) { if (dy < 0) angle = -Math.PI / 2; else angle = Math.PI / 2; } else { angle = Math.atan(Math.abs(dy / dx)); if (dy > 0) angle = -angle; if (dx < 0) angle = Math.PI - angle; } // Adjust angle for screen coordinates. missle.angle = angle - Math.PI / 2; // Change the missle's angle so that it points toward the ship. missle.deltaX = MIN_ROCK_SIZE / 3 * -Math.sin(missle.angle); missle.deltaY = MIN_ROCK_SIZE / 3 * Math.cos(missle.angle); } public void stopMissle() { missle.active = false; missleCounter = 0; if (loaded) missleSound.stop(); misslePlaying = false; } public void initAsteroids() { int i, j; int s; double theta, r; int x, y; // Create random shapes, positions and movements for each asteroid. for (i = 0; i < MAX_ROCKS; i++) { // Create a jagged shape for the asteroid and give it a random rotation. asteroids[i].shape = new Polygon(); s = MIN_ROCK_SIDES + (int) (Math.random() * (MAX_ROCK_SIDES - MIN_ROCK_SIDES)); for (j = 0; j < s; j ++) { theta = 2 * Math.PI / s * j; r = MIN_ROCK_SIZE + (int) (Math.random() * (MAX_ROCK_SIZE - MIN_ROCK_SIZE)); x = (int) -Math.round(r * Math.sin(theta)); y = (int) Math.round(r * Math.cos(theta)); asteroids[i].shape.addPoint(x, y); } asteroids[i].active = true; asteroids[i].angle = 0.0; asteroids[i].deltaAngle = (Math.random() - 0.5) / 10; // Place the asteroid at one edge of the screen. if (Math.random() < 0.5) { asteroids[i].currentX = -AsteroidsSprite.width / 2; if (Math.random() < 0.5) asteroids[i].currentX = AsteroidsSprite.width / 2; asteroids[i].currentY = Math.random() * AsteroidsSprite.height; } else { asteroids[i].currentX = Math.random() * AsteroidsSprite.width; asteroids[i].currentY = -AsteroidsSprite.height / 2; if (Math.random() < 0.5) asteroids[i].currentY = AsteroidsSprite.height / 2; } // Set a random motion for the asteroid. asteroids[i].deltaX = Math.random() * asteroidsSpeed; if (Math.random() < 0.5) asteroids[i].deltaX = -asteroids[i].deltaX; asteroids[i].deltaY = Math.random() * asteroidsSpeed; if (Math.random() < 0.5) asteroids[i].deltaY = -asteroids[i].deltaY; asteroids[i].render(); asteroidIsSmall[i] = false; }
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?