Почему я не могу заставить свой красный шар остановиться на синей коробке с помощью robot.getPixelColor? - PullRequest
1 голос
/ 29 мая 2019

Название.Интерфейс GUI выглядит следующим образом: GUI Puzzle Ball

Приведенный ниже код предназначен для моей задачи таймера, отвечающей за управление движением мяча вниз, вызываемой:

timerscheduleAtFixedRate (moveDown, 0, 20);

При каждом нажатии клавиши со стрелкой шар должен непрерывно двигаться в этом направлении, пока не встретит квадрат.Я знаю, что использую .cancel () прямо сейчас, но я намерен исправить это с помощью временной паузы TimerTask.

Не добавляя ничего к значениям X или Y, шар никогда не останавливается.(Я должен упомянуть, что когда он достигает дна, он зацикливается на вершине) Выводимые цвета, похоже, меняются, когда не меняются значения X или Y.Например, при (0,360) в первый раз выводимый цвет равен (208,208,208), а в следующий раз при (0,360) выводимый цвет равен (240,240,240).

При добавлении того, что, как я думал, это остановитсяпрямо на краю ящика, Y + 51, он все еще не останавливается.Единственный обнаруженный цвет - это (208, 208, 208), который является серым.

Если я добавил и Y + 51, и X + 25, шар все равно никогда не останавливается, и выводится только серый.Обратите внимание, что я изменил скорость на 1, и это не имеет значения.

Теперь, по счастливой случайности, я обнаружил, что, если я добавлю 80 к Y и 25 к X, он остановится прямона краю коробки.

Я также обнаружил, что если я добавлю 25 к Y и 25 к X для TimerTask, ответственного за перемещение шара вверх (скорость отрицательна), шар остановится на расстоянии 1 пиксельот края коробки.

   public void run() {
      try {
            Robot robot = new Robot();
            int y = ball.positionY + 80;
            int x = ball.positionX + 25;

            System.out.println(ball.positionX);
            System.out.println(ball.positionY);

            color = robot.getPixelColor(x, y);

            System.out.println("Red   = " + color.getRed());
            System.out.println("Green = " + color.getGreen());
            System.out.println("Blue  = " + color.getBlue());

        } catch (AWTException e) {

            e.printStackTrace();

        }

        if((color.getRed() == 0) && (color.getGreen() == 0) && (color.getBlue() == 255)){

            moveDown.cancel();
            moving = false;

        }

        else{

        ball.positionY += 5;

        if (ball.positionY > 670) {

            ball.positionY = 0;

        }
        }

        ball.repaint();
    }

Кто-нибудь знает, что на самом деле происходит?Я пока не смог выяснить направление вправо / влево, так как, похоже, не существует шаблона.

1 Ответ

0 голосов
/ 29 мая 2019

Робот не является надежным способом обнаружения ваших квадратов. Двойная буферизация может означать, что ваши пиксели на самом деле не отображаются.

Поскольку ваш собственный код рисует квадраты, сохраняйте координаты этих квадратов в закрытом поле и используйте их для проверки на столкновение вместо проверки цвета пикселей:

private final Collection<Rectangle> squares = new ArrayList<>();

// ...

    if (squares.stream().anyMatch(sq -> sq.contains(x, y))) {
        moveDown.cancel();
        moving = false;
    } else {
        ball.positionY += 5;
        if (ball.positionY > 670) {
            ball.positionY = 0;
        }
    }

Также следует помнить, что Swing небезопасен для использования несколькими потоками . Вы должны использовать javax.swing.Timer вместо java.util.Timer, поскольку он правильно выполняет свои задачи в потоке диспетчеризации событий AWT.

...