Страницы

Поиск по вопросам

четверг, 14 февраля 2019 г.

Проблема обработки пересечения Rectangle-ов (текстур)

Делаю простенькую игрушку. Логика заключается в том, что у левого края экрана стоит объект, назовем его человеком для удобства. У правого края хаотичным образом спавнятся другие объекты, для удобства, назовем их зомби. Человек убивает их из постоянно стреляющего автомата, "пули" которого при пересечении с "зомби" должны удалять "зомби" с экрана.
Проблема заключается в том, что эти "пули" просто пролетают мимо "зомби". То-есть, я не могу отследить пересечения рендеров "пуль" и "зомби".
Как я понял, проблема в многочисленном объявлении Rectangle-ов "зомби" и "пуль", что приводит к неразберихе в коде и той проблеме, что у меня, в частности. Есть ли возможность объявить его только 1 раз и потом всюду использовать? Если да, то как?
Кстати, просто объявить его на уровне на уровне класса, как тот же Rectangle человека не получается, ибо вылетает NullPointerException, со ссылкой на spawncrowd и spavbullet. Заранее спасибо_)
import com.badlogic.gdx.ApplicationAdapter; import com.badlogic.gdx.Gdx; import com.badlogic.gdx.Input; import com.badlogic.gdx.graphics.GL20; import com.badlogic.gdx.graphics.OrthographicCamera; import com.badlogic.gdx.graphics.Texture; import com.badlogic.gdx.graphics.g2d.SpriteBatch; import com.badlogic.gdx.math.MathUtils; import com.badlogic.gdx.math.Vector3; import com.badlogic.gdx.utils.Array; import com.badlogic.gdx.utils.TimeUtils; import com.badlogic.gdx.math.Rectangle; import java.util.Iterator; public class MyGdxGame extends ApplicationAdapter { OrthographicCamera camera; SpriteBatch batch; Texture manImage, bulletImage, CrowdImage; Rectangle manRect; Vector3 touchPos; Array bulletsArray, CrowdElemArray;
long lastbultime, lastcrowdeltime; int counter_miss;
@Override public void create () {
camera = new OrthographicCamera(); camera.setToOrtho(false, 960, 540);
touchPos = new Vector3();
batch = new SpriteBatch();
manImage = new Texture("man.jpg"); bulletImage = new Texture("bullet.jpg"); CrowdImage = new Texture("Crowd.jpg");
manRect = new Rectangle(); manRect.x = 0; manRect.y = 540/2; manRect.height = 256; manRect.width = 256;
CrowdElemArray = new Array(); spawncrowdel(); bulletsArray = new Array(); spawnbullet(); }
public void spawncrowdel() { Rectangle CrowdelementRect = new Rectangle(); CrowdelementRect.y = MathUtils.random(0, 540-256); CrowdelementRect.x = 960; CrowdelementRect.height = 256; CrowdelementRect.width = 64; CrowdElemArray.add(CrowdelementRect); lastcrowdeltime = TimeUtils.nanoTime();
} public void spawnbullet() { Rectangle bulletRect = new Rectangle(); bulletRect.y = manRect.getY() + manRect.height/2; bulletRect.x = manRect.getX(); bulletRect.height = 256; bulletRect.width = 64; bulletsArray.add(bulletRect); lastbultime = TimeUtils.nanoTime();
}
@Override public void render () { Gdx.gl.glClearColor(0, 1, 0.5f, 1); Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
camera.update(); batch.setProjectionMatrix(camera.combined);
batch.begin();
batch.draw(manImage, manRect.x, manRect.y);
for (Rectangle CrowdelementRect: CrowdElemArray) batch.draw(CrowdImage, CrowdelementRect.x, CrowdelementRect.y); for (Rectangle bulletRect: bulletsArray) batch.draw(bulletImage, bulletRect.x, bulletRect.y);
batch.end();
// Сенсорное урправление if (Gdx.input.isTouched()){ touchPos.set(Gdx.input.getX(), Gdx.input.getY(), 0); camera.unproject(touchPos); manRect.y = (int) (touchPos.y - 128/2); }
if (Gdx.input.isKeyPressed(Input.Keys.UP)) manRect.y += 200 * Gdx.graphics.getDeltaTime(); if (Gdx.input.isKeyPressed(Input.Keys.DOWN)) manRect.y -= 200 * Gdx.graphics.getDeltaTime();
if (manRect.y < 0) manRect.y = 0; if (manRect.y > 540-256) manRect.y = 540-256;
//TODO Спавнинг зомби if (TimeUtils.nanoTime() - lastcrowdeltime > 2000000000) spawncrowdel(); //TODO Спавнинг пули if (TimeUtils.nanoTime() - lastbultime > 800000000) spawnbullet();
//TODO Движение зомби Iterator move = CrowdElemArray.iterator(); while (move.hasNext()){ Rectangle CrowdelementRect = new Rectangle(); CrowdelementRect = move.next(); CrowdelementRect.x -= 100 * Gdx.graphics.getDeltaTime(); if (CrowdelementRect.x <= 10) { counter_miss += 1; move.remove(); } if (CrowdelementRect.overlaps(manRect)) move.remove(); }
//TODO Движение пули Iterator movebul = bulletsArray.iterator(); Rectangle CrowdelementRect = new Rectangle(); while (movebul.hasNext()){ Rectangle bulletRect = movebul.next(); bulletRect.x += 100 * Gdx.graphics.getDeltaTime(); if (bulletRect.x > 960) { movebul.remove(); } if (bulletRect.overlaps(CrowdelementRect)) movebul.remove(); } } @Override public void dispose() { super.dispose(); CrowdImage.dispose(); manImage.dispose(); bulletImage.dispose(); batch.dispose(); }
} `
PS
Делал все по шаблону со "стартандроида".


Ответ

Решение взято отсюда. Человек решает аналогичную задачу через следующий код:
private void testCollision() { Iterator b = ball.iterator(); while(b.hasNext()) { Bullet balls = b.next(); Iterator i = enemy.iterator(); while(i.hasNext()) { Enemy enemies = i.next();
if ((Math.abs(balls.x - enemies.x) <= (balls.width + enemies.width) / 2f) && (Math.abs(balls.y - enemies.y) <= (balls.height + enemies.height) / 2f)) { i.remove(); b.remove(); } } } }
когда-то пробовал сам - у меня работало.

Комментариев нет:

Отправить комментарий