Drawing lines in GUI with arrow keys using keylistener in Java -


i working on keylistener exercise java class, have been stuck past week. appreciate helpful suggestions. exercise is:

"write program draws line segments using arrow keys. line starts center of frame , draws toward east, north, west, or south when right-arrow key, up-arrow key, left-arrow key, or down-arrow key clicked."

through debugging figured out keylistener works point of getting drawcomponent(graphics g), draws when press down or right , works first couple times. here code:

import java.awt.*; import java.awt.event.*; import javax.swing.*;  @suppresswarnings("serial") public class eventprogrammingexercise8 extends jframe {      jpanel contentpane;     linepanel lines;     public static final int size_of_frame = 500;      public static void main(string[] args) {         eventqueue.invokelater(new runnable() {             public void run() {                 try {                     eventprogrammingexercise8 frame = new eventprogrammingexercise8();                     frame.setvisible(true);                 } catch (exception e) {                     e.printstacktrace();                 }             }         });     }      public eventprogrammingexercise8() {         settitle("eventexercise8");         setdefaultcloseoperation(jframe.exit_on_close);         setsize(size_of_frame, size_of_frame);         contentpane = new jpanel();         lines = new linepanel();         contentpane.add(lines);         setcontentpane(contentpane);         contentpane.setopaque(true);         lines.setopaque(true);          lines.setfocusable(true);         lines.addkeylistener(new arrowlistener());     }      private class linepanel extends jpanel {          private int x;         private int y;         private int x2;         private int y2;          public linepanel() {             x = getwidth() / 2;             y = getheight() / 2;             x2 = x;             y2 = y;         }          protected void paintcomponent(graphics g) {             g.drawline(x, y, x2, y2);             x = x2;             y = y2;         }          public void draweast() {             x2 += 5;             repaint();         }          public void drawwest() {             x2 -= 5;             repaint();         }          public void drawnorth() {             y2 -= 5;             repaint();         }          public void drawsouth() {             y2 += 5;             repaint();         }      }      private class arrowlistener extends keyadapter {          public void keypressed(keyevent e) {             int key = e.getkeycode();             if (key == keyevent.vk_right) {                 lines.draweast();             } else if (key == keyevent.vk_left) {                 lines.drawwest();             } else if (key == keyevent.vk_up) {                 lines.drawnorth();             } else {                 lines.drawsouth();             }         }      }  } 

thanks.

a few things jump out @ me...

public linepanel() {     x = getwidth() / 2;     y = getheight() / 2; 

this issue, because @ time construct class, it's size 0x0

apart fact haven't called super.paintcomponent breaks paint chain, seem think painting accumaltive...

protected void paintcomponent(graphics g) {     g.drawline(x, y, x2, y2);     x = x2;     y = y2; } 

painting in swing destructive. is, expected erase graphics context , rebuild output scratch. job paintcomponent clear graphics context ready painting, you've not called super.paintcomponent, breaking paint chain , opening number of ugly paint artifacts

calling setsize(size_of_frame, size_of_frame); on frame dangerous, makes no guarantee frames border insets, reduce viewable area available you.

this....

contentpane = new jpanel();  lines = new linepanel(); contentpane.add(lines); setcontentpane(contentpane); 

is not required, adds clutter code. it's hint going wrong code.

jpanel uses flowlayout default. flowlayout uses component's preferred size determine how best layout components. default preferred size of component 0x0

you use...

lines = new linepanel(); add(lines); 

instead or set contentpane use borderlayout help...

try adding lines.setborder(new lineborder(color.red)); add see get...

oddly, during testing, keylistener worked fine...

basically...

  • override getpreferredsize method of linepanel , return size of panel use.
  • use java.util.list maintain list of points need painted.
  • in paintcomponent method, use point list render lines. bit tricky, need 2 points , list may contain odd number of points, but's doable.
  • calculate start point either using preferred size or other means (like using componentlistener , monitoring componentresized method. becomes tricky component may resized number of times when first created , released screen , want ignore future events once have first point)

Comments

Popular posts from this blog

python - Subclassed QStyledItemDelegate ignores Stylesheet -

java - HttpClient 3.1 Connection pooling vs HttpClient 4.3.2 -

SQL: Divide the sum of values in one table with the count of rows in another -