Pergunta

Eu quero ter um jogo onde a vista vai se movimentar como o mouse atinge a borda exterior da janela (semelhante a muitos jogos RTS). Eu li que há uma sobrecarga significativa quando se utiliza o MouseMotionListener.

Existe talvez uma maneira de ter um segundo componente transparente dentro da janela de jogo (JPanel) que não afeta jogo-jogo, mas irá registrar quando as folhas do mouse o componente interno via MouseAdapter.mouseEntered () / mouseExited ()?

boolean mouseOnScreen;
boolean mouseWithinInnerComponent; //is (10 <= mouse.x <= screenWidth - 10) && (10 <= mouse.y <= screenHeight)

if(mouseOnScreen && !mouseWithinInnerComponent)
{
    //do something...
}

Eu estou em uma perda para saber como determinar qual o limite da tela foi cruzada sem ter que ter quatro dos componentes acima mencionados sobrepostos nos cantos para formar uma borda ao redor da tela, que pode detectar se o mouse é a qualquer borda ou canto . Este Imagino a ser bastante caro (ter que verificar cada componente durante a execução do jogo) ...

boolean mouseOnScreen;
boolean mouseWithinTopComponent; //is (0 <= mouse.y <= 10)
boolean mouseWithinBottomComponent; //is (screenHeight - 10 <= mouse.y <= screenHeight)
boolean mouseWithinLeftComponent; //is (0 <= mouse.x <= 10)
boolean mouseWithinRightComponent; //is (screenWidth - 10 <= mouse.x <= screenWidth)

if(mouseOnScreen)
{
    if(!mouseWithinBottomComponent)
    {
        //move view up
    }
    if(!mouseWithinTopComponent)
    {
        //move view down
    }
    if(!mouseWithinLeftComponent)
    {
        //move view right
    }
    if(!mouseWithinRightComponent)
    {
        //move view left
    }
}

Exatamente quanto sobrecarga existe com MouseMotionListener? Será que este ou um método semelhante, talvez, ser mais eficiente se as detecções só precisa ser feita ao longo das fronteiras de uma janela jogo?

NOTA:. Isso será usado no modo de janela, bem como possível aplicação em tela cheia

Foi útil?

Solução

Eu tenho implementado a mesma coisa que você precisa usar um MouseMotionListener. Eu não sou realmente certo porque você acha que vai adicionar uma sobrecarga ... Se você adicionar um e simplesmente pedir cada um dos seus métodos para imprimir no console (que é lento) e mova o mouse ao redor, você vai ver que é muito mal-humorado do ponto de vista do usuário.

Meu implementação consiste em 4 partes principais:. Um painel de rolagem, regiões retangulares, um temporizador e um MouseMotionListener

Em primeiro lugar, eu criei um painel, chamado AutoScrollPane, que se estende JScollPane. Mesmo que seja um JScrollPane, você pode ocultar as barras de rolagem. Isso me permite funcionalidade de alavancagem para mover uma janela em torno de um mapa ou semelhante, como em um jogo RTS como você diz.

Em segundo lugar, para as regiões de rolagem, eu realmente tenho 8: n, ne, e, se, s, sw, w e nw (ou seja, "norte", Nordeste", etc.), com as diagonais permitindo diagonal scrolling eu implementá-los simplesmente como Rectangles Eles não são desenhados na tela ou qualquer coisa -... I apenas instanciar 8 retângulos na minha classe de tamanho adequado e com coordenadas que correspondem às regiões da janela eu realmente permitir que minha janela para ser redimensionada, então eu redimensionar os retângulos se necessário.

Em terceiro lugar, eu tenho um temporizador que pode ser ligado e desligado. Quando ele está ligado, cada "tick" gera um Runnable. Este trabalho Runnable's é para rolar visor do painel na direção apropriada de uma certa distância. Cada Runnable é entregue à fila de eventos Swing.

Finalmente, tenho um MouseMotionListener. É o trabalho é para rato interceptar entrar, sair, e eventos de movimentação. Cada vez que recebe um evento, ele verifica a localização atual do mouse e se cruza um dos retângulos. Com base no qual retângulo, ele escolhe uma direção para rolar. Ele mantém o controle sobre se o mouse estava em uma região de rolagem do evento anterior ou não. Com base nessas informações que sabe se ele deve começar a rolagem, interromper a rolagem, ou simplesmente deixar o que está acontecendo continuar. Eu queria que meu deslocamento para parar se o mouse vai para fora do painel, assim, o uso da saída / enter eventos. De qualquer forma, para começar a rolar, o ouvinte salva fora da direção e distância de deslocamento e diz o temporizador para começar. Quando é hora para interromper a rolagem (como quando o mouse sai uma região de rolagem), ele informa o temporizador para parar.

Demorou um pouco para escolher a granularidade temporizador direita e distância de rolagem para rolagem suave, mas ela não funciona muito bem. Espero que este esboço fornece alguma ajuda.

Outras dicas

Eu acho que foi Martin Fowler que desposada que a otimização prematura é a raiz de todo o mal no desenvolvimento de software. Por que não tentar o MouseMotionListener e só pensar em otimização se você achar que isso afeta o desempenho do jogo.

Não há nada de errado com um MouseMotionListener Quando você lê sobre a sobrecarga que era provavelmente um específico exmaple

Qualquer coisa que você pode fazer em qualquer linguagem de programação pode ser feito ruim ou errado.

Se você prestar atenção ao que você faz no seu ouvinte tudo deve ser fino

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top