Полный источник находится на Github по адресу this address.Почему мое нарисованное изображение мерцает на JPanel?
У меня есть JPanel, в котором я рисую фон и спрайт игрока. Логика и перекраска находятся в отдельных временных масштабах. Вот соответствующий код:
static long logicSleep = (long) (1e9/120);
static long drawSleep = (long) (1e9/60);
static long startTime;
static long logicTime, drawTime;
public static void main(String[] args) {
startTime = System.nanoTime();
while (keys[KeyEvent.VK_ESCAPE] == false) {
if (System.nanoTime() > logicTime + startTime) {
player.logic();
logicTime += logicSleep;
}
if (System.nanoTime() > drawTime + startTime) {
sheet.repaint();
drawTime += drawSleep;
}
}
System.exit(0);
}
Таким образом, логика работает каждые 1/120 секунды, а рисунок проходит каждые 1/60 секунды. Это работает по назначению. Однако изображение мерцает так часто. Это не разрывает экран, так как у меня есть Java 8, и мой монитор обновляется на частоте 60 Гц (не говоря уже о том, как по умолчанию включена двойная буферизация на jpanels). Мерцание кажется резким изменением положения, хотя фактическое положение символа на экране влияет только на один кадр.
Вот мой заказ JPanel класс:
static class Sheet extends JPanel {
@Override
public void paintComponent(Graphics g1) {
super.paintComponent(g1);
Graphics2D g = (Graphics2D) g1;
g.translate((int) -(player.xPos + player.sprites[0].getWidth()/2 - getWidth()/2),
(int) -(player.yPos + player.sprites[0].getHeight()/2 - getHeight()/2));
g.drawImage(map, 0, 0, null);
g.drawImage(player.sprites[player.spriteNum], (int) player.xPos, (int) player.yPos, null);
g.drawImage(foreground, 0, 0, null);
}
}
мне удалось это исправить, изменив логику сна для запуска каждые 1/180 секунды, но мне интересно, почему это происходит с логикой работает в определенные временные рамки. Это также происходит с обновлением логики каждые 1/240 секунд.
TL; DR: Мой спрайт мерцает из-за моей логики и я не знаю почему.
использовать метод 'setDoubleBuffered (истинный),' на ваших JPanel – WalterM
@WalterM: не нужно делать, и на самом деле это не поможет, так как JPanels уже двойной буферизации по умолчанию, ** но * * Вы рисуете краску, а не paintComponent? Вы должны рисовать последний (paintComponent), а не первый (краска). Вы не показываете нам свой графический код, поэтому здесь трудно помочь.Лучше всего для вас создать и показать [mcve]. –
@HovercraftFullOfEels Отредактировано для наглядности. – GingerDeadshot