animation, threads, paintComponent


DevX Home    Today's Headlines   Articles Archive   Tip Bank   Forums   

Results 1 to 6 of 6

Thread: animation, threads, paintComponent

  1. #1
    Join Date
    Mar 2004
    Posts
    635

    animation, threads, paintComponent

    I have a class that extends jpanel. The panel is to show an animation. The animation can be something simple for now, such as watching an oval grow and shrink contuniously. This "visual" panel, when shown, I want to start a new thread that handles the animation and keeps it updating. When the user clicks a button, it'll switch to the visual panel and begin looping the animation. I'm just not sure what to do. I override the paintComponent() of the jpanel, but it doesn't update properly and locks up the application sometimes. I'm new to threads and haven't really messed with painting graphics before.

  2. #2
    Join Date
    Nov 2004
    Location
    Norway
    Posts
    1,560
    If u whant some answers u have to be specifi...
    eschew obfuscation

  3. #3
    Join Date
    Mar 2004
    Posts
    635
    I finished my java classes a year ago, this isn't homework. So you are allowed to show code if you can answer it. Ok, I'll restructure the question into a homework like assignment.

    Create a button.
    when the button is on, display a circle growing and shrinking in a jpanel.
    stop showing the animation when the button is clicked off.
    the animation should be in a seperate thread.

  4. #4
    Join Date
    Nov 2004
    Location
    Norway
    Posts
    1,560
    Here is the circles code, you are now cordially invited to modify it so it relocates its circle when you resize the frame

    Code:
    import javax.swing.*;
    import java.awt.*;
    import java.awt.event.*;
    
    
    /**
     * Draw circles
     */
    
    public class Circles extends JPanel implements Runnable, ActionListener {
      private boolean isDrawing=false;
      private Rectangle ovalRect=null;
      public Circles() {
      }
      /**
       * Make a jframe to put circles panel and a button panel in
       * @param args
       */
      public static void main(String[] args) {
        JFrame f=new JFrame("Circle"); // frame
        f.getContentPane().setLayout(new BorderLayout());
        JPanel btnPan=new JPanel(new FlowLayout(FlowLayout.CENTER)); //button panel
        JButton closeBtn=new JButton("Close");  // buttons
        JToggleButton offOnBtn=new JToggleButton("Make Circles",false);
        Circles cc = new Circles();  // make circles panel
        closeBtn.addActionListener(cc); // make circles panel a listener to the buttons
        offOnBtn.addActionListener(cc);
        // put it all together
        btnPan.add(closeBtn,null);
        btnPan.add(offOnBtn,null);
        f.getContentPane().add(cc,BorderLayout.CENTER);
        f.getContentPane().add(btnPan,BorderLayout.SOUTH);
        f.setBounds(20,20,400,300);
        f.setVisible(true);
      }
      private synchronized void setIsDrawing(boolean isDrawing) {
        this.isDrawing=isDrawing;
      }
      private synchronized boolean getIsDrawing() {
        return this.isDrawing;
      }
      /**
       * draw a white circle on darkgray background that grows to the edge of
       * the panel and back again.  If no drawing thread is running then just
       * draw the circle, if any, as it currently is.
       * @param g
       */
      public void update (Graphics g) {
        Color c=g.getColor();
        if (this.getIsDrawing() || ovalRect!=null) {
          g.setColor(Color.darkGray);
          g.fillRect(0,0,this.getSize().width,this.getSize().height);
          g.setColor(Color.white);
          g.drawOval(ovalRect.x,ovalRect.y,ovalRect.width,ovalRect.height);
          g.setColor(c);
        } else {
          g.setColor(Color.darkGray);
          g.fillRect(0,0,this.getSize().width,this.getSize().height);
        }
      }
      public void paint (Graphics g) {
        update(g);
      }
      /**
       * start w. a circle inside a square of 20x20 pixels centered on the panel
       */
      private void initiateOvalRect() {
        ovalRect=new Rectangle( (this.getSize().width/2)-10,
                                  (this.getSize().height/2)-10,
                                  20,20);
      }
      public void run() {
        initiateOvalRect();
        int increment=4; // 4 pixels increment, up or down in size
        while(getIsDrawing()) {
          try {
            Thread.currentThread().sleep(20); // 20 millisec between each increment
            this.repaint();
            // flipflop the increment value on boundary values
            if ((ovalRect.x <= increment/2 ||
                 ovalRect.y <= increment/2) ||
                 (ovalRect.x > (this.getSize().width/2)-10  ||
                  ovalRect.y > (this.getSize().height/2)-10) ){
              increment *=-1;
            }
            ovalRect.x -= increment/2;
            ovalRect.y -= increment/2;
            ovalRect.width += increment;
            ovalRect.height += increment;
          } catch (InterruptedException ie) {
            return;
          }
        }
        this.repaint();
      }
      /**
       * Handle buttons callback
       * @param e
       */
      public void actionPerformed(ActionEvent e) {
        String cmd=e.getActionCommand();
        if (cmd.equals("Close")) {
          setIsDrawing(false);
          System.exit(0);
        }
        if (cmd.equals("Make Circles")) {
          Thread drawer=new Thread(this);
          setIsDrawing(true); // set running flag for thread
          drawer.start(); // start thread
          ((JToggleButton)e.getSource()).setText("Stop Circles");
        } else if (cmd.equals("Stop Circles")) {
          setIsDrawing(false); // stop thread
          ((JToggleButton)e.getSource()).setText("Make Circles");
        }
      }
    }
    eschew obfuscation

  5. #5
    Join Date
    Mar 2004
    Posts
    635
    Thx, that's all I needed to see.
    I've been told that components use paintComponent() instead of paint(). So does repaint() just call both of them or what?

  6. #6
    Join Date
    Nov 2004
    Location
    Norway
    Posts
    1,560
    To be honest, I've never used any method called paintComponent, at least not for the 10 years I've coded
    java. The method is supposedly there to protect the graphics context from permanent changes, well I always restore the color and font of the Graphics before my drawing methods exit, and that has worked fine, but then I've never has to midify the clip rectangle or alter the transform.
    eschew obfuscation

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
HTML5 Development Center
 
 
FAQ
Latest Articles
Java
.NET
XML
Database
Enterprise
Questions? Contact us.
C++
Web Development
Wireless
Latest Tips
Open Source


   Development Centers

   -- Android Development Center
   -- Cloud Development Project Center
   -- HTML5 Development Center
   -- Windows Mobile Development Center