为了论证和简单,这里的代码有一个矩形精灵/纹理向上射击(因为它是一把枪)。并且敌人的矩形/精灵/纹理向下生成。然后玩家检测它是否击中了敌人。当玩家击中敌人时,我会获得越界异常-1
package com.TheGame.Pack;
import java.util.Iterator;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Input.Keys;
import com.badlogic.gdx.Screen;
import com.badlogic.gdx.audio.Music;
import com.badlogic.gdx.audio.Sound;
import com.badlogic.gdx.graphics.GL20;
import com.badlogic.gdx.graphics.OrthographicCamera;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.math.MathUtils;
import com.badlogic.gdx.math.Rectangle;
import com.badlogic.gdx.math.Vector3;
import com.badlogic.gdx.utils.Array;
import com.badlogic.gdx.utils.TimeUtils;
public class GameScreen implements Screen {
final MasterClass game;
Texture FleetTexture;
Texture PlayerTexture;
Texture ShootingTexture;
OrthographicCamera camera;
Rectangle Player;
Array<Rectangle> Emma;
Array<Rectangle> Shooting;
long EmmaSpawnTime;
long ShootingTime;
public static int EmmaKilled = 0;
public GameScreen(final MasterClass gam) {
this.game = gam;
// load the images for the droplet and the Player, 64x64 pixels each
FleetTexture = new Texture(Gdx.files.internal("cirA.png")); //Enemies
PlayerTexture = new Texture(Gdx.files.internal("BoxA.png"));
ShootingTexture = new Texture(Gdx.files.internal("gun.png"));
// load the drop sound effect and the rain background "music"
// dropSound = Gdx.audio.newSound(Gdx.files.internal("drop.wav"));
// rainMusic = Gdx.audio.newMusic(Gdx.files.internal("rain.mp3"));
// rainMusic.setLooping(true);
// create the camera and the SpriteBatch
camera = new OrthographicCamera();
camera.setToOrtho(false, 800, 480);
// create a Rectangle to logically represent the Player
Player = new Rectangle();
Player.x = 800 / 2 - 64 / 2; // center the Player horizontally
Player.y = 20; // bottom left corner of the Player is 20 pixels above
// the bottom screen edge
Player.width = 40;
Player.height = 30;
// create the Emma array and spawn the first EmmaInArray
Emma = new Array<Rectangle>();
Shooting = new Array<Rectangle>();
spawnEmma();
}
private void spawnEmma() {
Rectangle EmmaInArray = new Rectangle();
EmmaInArray.x = MathUtils.random(0, 800 - 64);
EmmaInArray.y = 480;
EmmaInArray.width = 40;
EmmaInArray.height = 30;
Emma.add(EmmaInArray);
EmmaSpawnTime = TimeUtils.nanoTime();
}
private void spawnShooting(){
Rectangle ShootingInArray = new Rectangle();
ShootingInArray.x = Player.x;
ShootingInArray.y = Player.y;
ShootingInArray.width = 40;
ShootingInArray.height = 30;
Shooting.add(ShootingInArray);
ShootingTime = TimeUtils.nanoTime();
}
@Override
public void render(float delta) {
// clear the screen with a dark blue color. The
// arguments to glClearColor are the red, green
// blue and alpha component in the range [0,1]
// of the color to be used to clear the screen.
Gdx.gl.glClearColor(0, 0, 0.2f, 1);
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
// tell the camera to update its matrices.
camera.update();
// tell the SpriteBatch to render in the
// coordinate system specified by the camera.
game.batch.setProjectionMatrix(camera.combined);
// begin a new batch and draw the Player and
// all drops
game.batch.begin();
game.font.draw(game.batch, "Drops Collected: " + EmmaKilled, 0, 480);
game.batch.draw(PlayerTexture, Player.x, Player.y, Gdx.graphics.getWidth() / 20,
Gdx.graphics.getHeight()/ 20);
for (Rectangle EmmaInArray : Emma) {
game.batch.draw(FleetTexture, EmmaInArray.x, EmmaInArray.y);
}
for(Rectangle ShootingInArray : Shooting){
game.batch.draw(ShootingTexture, ShootingInArray.x, ShootingInArray.y);
ShootingInArray.y +=10;
}
game.batch.end();
// process user input
if (Gdx.input.isTouched()) {
Vector3 touchPos = new Vector3();
touchPos.set(Gdx.input.getX(), Gdx.input.getY(), 0);
camera.unproject(touchPos);
Player.x = touchPos.x - 64 / 2;
}
if (Gdx.input.isKeyPressed(Keys.LEFT))
Player.x -= 400 * Gdx.graphics.getDeltaTime();
if (Gdx.input.isKeyPressed(Keys.RIGHT))
Player.x += 400 * Gdx.graphics.getDeltaTime();
// make sure the Player stays within the screen bounds
if (Player.x < 0)
Player.x = 0;
if (Player.x > 800 - 64)
Player.x = 800 - 64;
// check if we need to create a new EmmaInArray
if (TimeUtils.nanoTime() - EmmaSpawnTime > 100000000){
spawnEmma();
}
if(TimeUtils.nanoTime() - ShootingTime > 100000000){
spawnShooting();
}
// move the Emma, remove any that are beneath the bottom edge of
// the screen or that hit the Player. In the later case we play back
// a sound effect as well.
Iterator<Rectangle> EmmaIterator = Emma.iterator();
while (EmmaIterator.hasNext()) {
Rectangle EmmaInArray = EmmaIterator.next();
EmmaInArray.y -= 200 * Gdx.graphics.getDeltaTime();
if (EmmaInArray.y + 64 < 0){
EmmaIterator.remove();
}
Iterator<Rectangle> ShootingIterator = Shooting.iterator();
while(ShootingIterator.hasNext()){
Rectangle ShootingInArray = ShootingIterator.next();
// ShootingInArray.y += 200 * Gdx.graphics.getDeltaTime();
if(ShootingInArray.y > 480){
ShootingIterator.remove();
}
if(EmmaInArray.overlaps(ShootingInArray)){
ShootingIterator.remove();
EmmaIterator.remove();
}
if (Player.overlaps(EmmaInArray)) {
EmmaKilled++;
game.setScreen(game.HS);
// dropSound.play();
如果我注释掉EmmaIterator.remove();它运行良好,没有注释它在撞击时崩溃。
为什么这次崩溃不是正确的方法呢?我是否需要以某种方式同时检测到命中?当显然屏幕上还有敌人时,阵列如何处于负1?
EmmaIterator.remove();
}
}
虽然这不是我设置的方式,但代码仍然可以运行而没有问题。我遇到了同样的问题,而不是检测到玩家的敌人碰撞,我有2支枪检查碰撞。这对我来说似乎是一个大问题,这就是为什么我说我做错了但文档很轻,所以我来到这里。
}
}
@Override
public void resize(int width, int height) {
}
@Override
public void show() {
// start the playback of the background music
// when the screen is shown
//rainMusic.play();
}
@Override
public void hide() {
}
@Override
public void pause() {
}
@Override
public void resume() {
}
@Override
public void dispose() {
FleetTexture.dispose();
PlayerTexture.dispose();
ShootingTexture.dispose();
// dropSound.dispose();
// rainMusic.dispose();
}
}
答案 0 :(得分:0)
除非使用多线程,否则不可能完全同时发生任何事情。您的代码中存在许多可能的拼写错误,但有一个会破坏它:
Rectangle var1_holder = iter.next();
对iter的相同引用是在应该使用它的第一个块和第二个块中,它应该使用iter1。您应该考虑使用匹配的变量名称,例如
Iterator<Rectangle> iter3 = var3.iterator();
如果您必须将数字作为唯一的区别特征。
答案 1 :(得分:0)
notostraca是对的。但是为了使它更清楚,我将向你展示一个用于碰撞的for循环的例子。它不会造成任何伤害,我希望它会让你更清楚
int v2 = var2.size();
for (int i = 0; i < v2; i++) {
if (object.getBounds().overlaps(var2.get(i).getBounds())) {
var2.remove(i);
v2--;
//in this line u might use break; if u know that just one object
//from var2 array can hit at a time
}
}