2017-01-12 11 views
0

프레임을 생성하고 그래픽을 구현하는 클래스를 보유하는 MainApplication입니다.Keylistener가 작동하지만 의도 한 작업을 실행하지 않습니다. 왜?

MainApplication.java

import java.awt.*; 

public class MainApplication 
{ 
    public MainApplication() 
    { 
     Frame frame= new Frame("Test App"); 
     frame.add(new KeyTest()); 
     frame.setBackground(Color.RED); 
     frame.setLayout(null); 
     frame.setSize(700,750); 
     frame.setVisible(true); 
    } 
    public static void main(String args[]) 
    { 

     new MainApplication(); 

    } 
} 

이 클래스는 모든 그래픽 모양을 만들고 너무 모든 KeyListener를 구현합니다.

KeyTest.java

import java.awt.BasicStroke; 
import java.awt.Canvas; 
import java.awt.Color; 
import java.awt.Font; 
import java.awt.Graphics; 
import java.awt.Graphics2D; 
import java.awt.RenderingHints; 
import java.awt.Shape; 
import java.awt.Stroke; 
import java.awt.event.KeyEvent; 
import java.awt.event.KeyListener; 
import java.awt.geom.RoundRectangle2D; 

public class KeyTest extends Canvas { 


    /** 
    * 
    */ 
    private static final long serialVersionUID = 3L; 
    Graphics2D graphics2D; 
    Color color = Color.BLACK; 
    private static float borderThickness = 5; 
    Shape firstShape = new RoundRectangle2D.Double(20,40,300,50,10,10); 
    Shape secondShape = new RoundRectangle2D.Double(20,150,300,50,10,10); 
    public KeyTest() 
    { 
     setBackground(Color.RED); 
     setSize(700,750);    
    } 
    public void paint(Graphics graphics) 
    { 

     graphics2D = (Graphics2D)graphics; //TypeCasting to 2D 
     System.out.println("I am inside paint"); 

     //  Smoothening the corners 
     graphics2D.setRenderingHint(RenderingHints.KEY_ANTIALIASING, 
       RenderingHints.VALUE_ANTIALIAS_ON); 

     //  Apple border color 
     Stroke oldStroke = graphics2D.getStroke(); 
     graphics2D.setStroke(new BasicStroke(borderThickness)); 
     graphics2D.setColor(Color.WHITE); 

     //  Drawing a RoundedRectangle for Apple  
     graphics2D.draw(firstShape); 
     graphics2D.setStroke(oldStroke); 

     //  Setting the Background Color 
     graphics2D.setColor(Color.BLACK); 
     graphics2D.fill(firstShape); 


     //  Setting the font inside the shape 
     Font firstFont = new Font("Serif", Font.BOLD,35); 
     graphics2D.setFont(firstFont); 
     graphics2D.setColor(Color.WHITE); 
     graphics2D.drawString("Apple",30,80); 


     //  Pineapple border color 
     graphics2D.setStroke(new BasicStroke(borderThickness)); 
     graphics2D.setColor(Color.WHITE); 

     //  Drawing a RoundedRectangle for Pineapple  
     graphics2D.draw(secondShape); 
     graphics2D.setStroke(oldStroke); 

     //  Setting the Background Color 
     graphics2D.setColor(Color.BLACK); 
     graphics2D.fill(secondShape); 

     //  Setting the font inside the shape 
     Font secondFont = new Font("Serif", Font.BOLD,35); 
     graphics2D.setFont(secondFont); 
     graphics2D.setColor(Color.WHITE); 
     graphics2D.drawString("Pineapple",30,190); 

     addKeyListener(new KeyListener(){ 

      @Override 
      public void keyTyped(KeyEvent e) { 
       // TODO Auto-generated method stub 

      } 

      @Override 
      public void keyPressed(KeyEvent e) { 
       int keyCode = e.getKeyCode(); 

       System.out.println(keyCode); 
       System.out.println(KeyEvent.VK_UP); 
       if(keyCode==KeyEvent.VK_UP){ 
        System.out.println("Going to move up"); 
        move(firstShape); 

       } 
       if(keyCode==KeyEvent.VK_DOWN){ 
        System.out.println("Going to move down"); 
        move(secondShape); 

       } 
      } 

      @Override 
      public void keyReleased(KeyEvent e) { 
       // TODO Auto-generated method stub 

      }}); 
    } 
    public void move(Shape s){ 

     System.out.println("Check:"+s.getBounds2D()); 
     graphics2D.setColor(Color.GREEN); 
     graphics2D.fill(s); 
     System.out.println("moving out"); 
    } 
} 

내 콘솔 출력 명확하게 보여줍니다 내 키 리스너 작동하지만 내가 그것을 할 의도 작업을 실행하지.

콘솔 출력

나는 페인트

확인 이동하기 위해가는 내부입니다 : java.awt.geom.Rectangle2D $ 더블 [X = 20.0, y를 = W, 40.0 = 300.0 단, h =]

50.0

체크를 움직이려고 이사 : $ java.awt.geom.Rectangle2D 더블 [X = 20.0, Y, W = 300, 150.0를 =.

The Output which am getting now

The output I expect when I press DOWN ARROW Button

The Output I expect when I press UP ARROW Button

,536 : 0, H = 50.0]

OUTPUT 이사 지금은 무엇입니까

아웃풋 .. (IMAGE 1)

내가 화살표 버튼을 누를 때 예상 출력 (IMAGE 2)

내가 화살표 버튼을 누를 때 예상 아웃풋 (IMAGE 3)

+0

아마도 프레임에서 다시 칠하기/새로 고침을 트리거해야합니다. 힌트 : 질문에 ** 모든 ** 이미지를 포함시키지 않아도됩니다. – GhostCat

+0

'paint' 메소드 안에'KeyListener'를 추가하는 것이 전혀 좋지 않습니다. – Berger

+0

외부에 추가하면 목적을 달성하지 못했습니다. 그 이유는'paint' 메소드 안에 추가했기 때문입니다. –

답변

2

먼저 paint이 호출 될 때마다 추가로 등록되므로 을 paint 메서드 내부에 추가하면 안됩니다.

ComponentGraphics 개체를 저장하고 그 위에 그림을 그려 넣지 마십시오. 컨트롤 외부에 많은 문제가 발생할 수 있습니다 (예 : 다른 AWT UI 작업에 의해 지워질 수 있음).).

유일한 Graphics 개체는 paint에 수신되는 인스턴스이며 paint 메서드의 범위에만 해당됩니다.다음 코드에서

그래서이 :

  • addKeyListenerpaint 외부에서 이동되었습니다.
  • 키 수신기 은 Shape의 인덱스를 가진 move을 호출합니다.
  • move 방법 은받은 색인에 따라 Shape을 강조 표시하고 repaint을 호출합니다.
  • Graphics2D 개체는 이 외부와 관련이 없으므로 paint에 대한 로컬 변수로 설정됩니다.
  • paintHighlightedShapeGraphics2D 객체가 매개 변수
  • paint 방법은 이제 매개 변수로 전달의 Graphics2D 개체와 paintHighlightedShape를 호출로받은에서 강조 표시된 Shape 그림에 대한 책임이 있습니다. main 방법은 목적을 테스트하기 위해 KeyTest에 추가 된 것을

주, 그것의 내용은 메인 클래스에 가야한다.

셰이프를 강조 표시하려는 경우 Shape 배열을 사용할 수 있으며 move에 전달 된 인덱스는 Shape 배열 인덱스 일 수 있습니다.

마지막으로 사물을 최적화하기 위해 일반 모양을 강조 표시 한 경우 그리지 않아야합니다. 어쨌든 녹색 모양으로 숨겨지기 때문입니다. 강조 표시된 모양에 따라 일반 모양 또는 녹색 모양을 그리는 drawShape(Graphics2D, Shape) 메서드를 만드는 것이 좋습니다. paint 메서드에서이 메서드를 호출하면 모든 모양이 반복됩니다.

import java.awt.BasicStroke; 
import java.awt.Canvas; 
import java.awt.Color; 
import java.awt.Font; 
import java.awt.Frame; 
import java.awt.Graphics; 
import java.awt.Graphics2D; 
import java.awt.RenderingHints; 
import java.awt.Shape; 
import java.awt.Stroke; 
import java.awt.event.KeyEvent; 
import java.awt.event.KeyListener; 
import java.awt.geom.RoundRectangle2D; 

public class KeyTest extends Canvas { 

    /** 
    * 
    */ 
    private static final long serialVersionUID = 3L; 
    Color color = Color.BLACK; 
    private static float borderThickness = 5; 
    Shape firstShape = new RoundRectangle2D.Double(20, 40, 300, 50, 10, 10); 
    Shape secondShape = new RoundRectangle2D.Double(20, 150, 300, 50, 10, 10); 

    Shape highlightedShape; 

    public KeyTest() { 
     setBackground(Color.RED); 
     setSize(700, 750); 
    } 

    public static void main(final String[] args) { 
     Frame frame = new Frame("Test App"); 
     final KeyTest keyTest = new KeyTest(); 
     keyTest.addKeyListener(new KeyListener() { 

      @Override 
      public void keyTyped(final KeyEvent e) { 
       // TODO Auto-generated method stub 

      } 

      @Override 
      public void keyPressed(final KeyEvent e) { 
       int keyCode = e.getKeyCode(); 

       System.out.println(keyCode); 
       System.out.println(KeyEvent.VK_UP); 
       if (keyCode == KeyEvent.VK_UP) { 
        System.out.println("Going to move up"); 
        keyTest.move(1); 

       } 
       if (keyCode == KeyEvent.VK_DOWN) { 
        System.out.println("Going to move down"); 
        keyTest.move(2); 

       } 
      } 

      @Override 
      public void keyReleased(final KeyEvent e) { 
       // TODO Auto-generated method stub 

      } 
     }); 
     frame.add(keyTest); 
     frame.setBackground(Color.RED); 
     frame.setLayout(null); 
     frame.setSize(700, 750); 
     frame.setVisible(true); 
    } 

    public void paint(final Graphics graphics) { 

     Graphics2D graphics2D = (Graphics2D) graphics; //TypeCasting to 2D 
     System.out.println("I am inside paint"); 

     //  Smoothening the corners 
     graphics2D.setRenderingHint(RenderingHints.KEY_ANTIALIASING, 
       RenderingHints.VALUE_ANTIALIAS_ON); 

     //  Apple border color 
     Stroke oldStroke = graphics2D.getStroke(); 
     graphics2D.setStroke(new BasicStroke(borderThickness)); 
     graphics2D.setColor(Color.WHITE); 

     //  Drawing a RoundedRectangle for Apple 
     graphics2D.draw(firstShape); 
     graphics2D.setStroke(oldStroke); 

     //  Setting the Background Color 
     graphics2D.setColor(Color.BLACK); 
     graphics2D.fill(firstShape); 

     //  Setting the font inside the shape 
     Font firstFont = new Font("Serif", Font.BOLD, 35); 
     graphics2D.setFont(firstFont); 
     graphics2D.setColor(Color.WHITE); 
     graphics2D.drawString("Apple", 30, 80); 

     //  Pineapple border color 
     graphics2D.setStroke(new BasicStroke(borderThickness)); 
     graphics2D.setColor(Color.WHITE); 

     //  Drawing a RoundedRectangle for Pineapple 
     graphics2D.draw(secondShape); 
     graphics2D.setStroke(oldStroke); 

     //  Setting the Background Color 
     graphics2D.setColor(Color.BLACK); 
     graphics2D.fill(secondShape); 

     //  Setting the font inside the shape 
     Font secondFont = new Font("Serif", Font.BOLD, 35); 
     graphics2D.setFont(secondFont); 
     graphics2D.setColor(Color.WHITE); 
     graphics2D.drawString("Pineapple", 30, 190); 

     paintHighlightedShape(graphics2D); 

    } 

    private void paintHighlightedShape(final Graphics2D graphics2D) { 

     if (highlightedShape != null) { 

      graphics2D.setColor(Color.GREEN); 
      graphics2D.fill(highlightedShape); 

     } 
    } 

    public void move(final int shapeNumber) { 

     switch (shapeNumber) { 
     case 1: 
      highlightedShape = firstShape; 
      break; 
     case 2: 
      highlightedShape = secondShape; 
      break; 
     default: 

     } 

     System.out.println("Check:" + highlightedShape.getBounds2D()); 
     System.out.println("Moving shape : " + highlightedShape); 
     repaint(); 

     System.out.println("moving out"); 

    } 
} 
+1

이 대답은 페인트 방법과 Keylistener로 어려움을 겪을 때 발생하는 문제를 해결합니다. 고마워. –

+1

당신은 환영합니다 :) – Berger

+0

사실, 모양이 반드시 움직일 필요는 없습니다. 화살표 키를 누를 때마다 각 모양의 배경색을 검정색에서 녹색으로 변경하고 싶습니다. 즉 화살표 키를 눌러 선택하면 모양이 녹색으로 강조 표시됩니다. 2. repaint() 메서드를 사용하면 여러 도형을 페인트 할 때 깜박임이 발생합니다. 그러나 우리가 단지 2 개의 도형을 그릴 때 깜박 거리는 것은 없습니다. –