Painting in swing. repaint doesn't work.

Discussion in 'Java' started by Kgbol, Jun 16, 2007.

  1. Kgbol

    Kgbol Guest

    Hi, today I hve a problem with painting. I created a class Szescian
    that extends JPanel and implements Runnable. I want that class to
    paint a square that moves. I move it using a thread. The problem is
    that when i use repaint in the thread the screen doesn't repaints( the
    compiler doesn't jump tu paintComponent(gDC) method) Here is how i
    create this object in the class with frame

    private Szecian s1;

    //COnstructor
    public Main(){
    .........
    s1 = new Szescian();
    s1.setLocation(0,0);
    s1.setOpaque(true);
    s1.setVisible(true);
    s1.setSize(panelSzescian.getSize());;
    s1.setOpaque(true);
    panelSzescian.add(s1); // a JPanel to which i add s1
    s1.uruchom(); //start the thread
    .........
    }

    and here is my Szescian class:

    import java.awt.*;
    import java.awt.event.*;
    import javax.swing.*;
    import javax.swing.event.*;
    import java.io.*;
    import javax.imageio.*;

    public class Szescian extends JPanel implements Runnable{
    public int x,y;
    public Rectangle rect;
    public Szescian(){
    x=0; y=0;
    rect = new Rectangle(0,0,getWidth(), getHeight());
    }

    public void run(){
    for(int i=0; i<50; i++)
    {
    x=i; y=i;

    System.out.println(i);

    try
    {
    Thread.sleep(100);
    }
    catch(InterruptedException e){e.printStackTrace();}
    // repaint(rect);
    repaint();

    }
    }

    protected void paintComponent(Graphics gDC)
    {
    // podwojne buforowanie
    super.paintComponent( gDC );
    Image img = createImage(getWidth(), getHeight());
    Graphics g = img.getGraphics();
    g.setColor(Color.yellow);
    g.drawRect(x,y,20,20);
    g.fillRect(x,y,20,20);
    //gDC.drawImage(img,0,0,getWidth(), getHeight(),this);//
    wyswietla obraz z bufora
    gDC.drawImage(img,0,0,this);
    }

    protected void paintBorder(){

    }
    protected void paintChildren(){

    }

    public void uruchom(){
    Runnable r = new Szescian();
    Thread t = new Thread(r);
    t.start();
    }
    }
     
    Kgbol, Jun 16, 2007
    #1
    1. Advertising

  2. Kgbol

    SadRed Guest

    On Jun 17, 7:40 am, Kgbol <> wrote:
    > Hi, today I hve a problem with painting. I created a class Szescian
    > that extends JPanel and implements Runnable. I want that class to
    > paint a square that moves. I move it using a thread. The problem is
    > that when i use repaint in the thread the screen doesn't repaints( the
    > compiler doesn't jump tu paintComponent(gDC) method) Here is how i
    > create this object in the class with frame
    >
    > private Szecian s1;
    >
    > //COnstructor
    > public Main(){
    > ........
    > s1 = new Szescian();
    > s1.setLocation(0,0);
    > s1.setOpaque(true);
    > s1.setVisible(true);
    > s1.setSize(panelSzescian.getSize());;
    > s1.setOpaque(true);
    > panelSzescian.add(s1); // a JPanel to which i add s1
    > s1.uruchom(); //start the thread
    > ........
    >
    > }
    >
    > and here is my Szescian class:
    >
    > import java.awt.*;
    > import java.awt.event.*;
    > import javax.swing.*;
    > import javax.swing.event.*;
    > import java.io.*;
    > import javax.imageio.*;
    >
    > public class Szescian extends JPanel implements Runnable{
    > public int x,y;
    > public Rectangle rect;
    > public Szescian(){
    > x=0; y=0;
    > rect = new Rectangle(0,0,getWidth(), getHeight());
    > }
    >
    > public void run(){
    > for(int i=0; i<50; i++)
    > {
    > x=i; y=i;
    >
    > System.out.println(i);
    >
    > try
    > {
    > Thread.sleep(100);
    > }
    > catch(InterruptedException e){e.printStackTrace();}
    > // repaint(rect);
    > repaint();
    >
    > }
    > }
    >
    > protected void paintComponent(Graphics gDC)
    > {
    > // podwojne buforowanie
    > super.paintComponent( gDC );
    > Image img = createImage(getWidth(), getHeight());
    > Graphics g = img.getGraphics();
    > g.setColor(Color.yellow);
    > g.drawRect(x,y,20,20);
    > g.fillRect(x,y,20,20);
    > //gDC.drawImage(img,0,0,getWidth(), getHeight(),this);//
    > wyswietla obraz z bufora
    > gDC.drawImage(img,0,0,this);
    > }
    >
    > protected void paintBorder(){
    >
    > }
    > protected void paintChildren(){
    >
    > }
    >
    > public void uruchom(){
    > Runnable r = new Szescian();
    > Thread t = new Thread(r);
    > t.start();
    > }
    >
    > }

    Your 's1' and 'r' are completely different objects.
    Very bad design.
    You should radically refactor it.
    Panel should be simply a panel.
    Don't make it to be an executable/runnable!
     
    SadRed, Jun 17, 2007
    #2
    1. Advertising

  3. Kgbol

    Twisted Guest

    On Jun 16, 8:34 pm, SadRed <> wrote:
    > > s1 = new Szescian();
    > > s1.setLocation(0,0);
    > > s1.setOpaque(true);
    > > s1.setVisible(true);
    > > s1.setSize(panelSzescian.getSize());;
    > > s1.setOpaque(true);
    > > panelSzescian.add(s1); // a JPanel to which i add s1
    > > s1.uruchom(); //start the thread


    > > public void uruchom(){
    > > Runnable r = new Szescian();
    > > Thread t = new Thread(r);
    > > t.start();
    > > }

    >
    > > }

    >
    > Your 's1' and 'r' are completely different objects.


    This much is true. The uruchom method should just do:
    (new Thread(this)).start();

    I guess the OP's intent with this design is to have a component that
    auto-updates on a timer. There should really be some facility for
    terminating the thread later on when the component no longer needs
    updating. I suppose the component can detect in the run loop or paint
    method if it's been told to deactivate or is no longer visible or
    whatever; maybe handling that is planned but unimplemented by the OP
    yet, or omitted from the code posted here to save space. Right now it
    looks like it updates only fifty times and then stops anyway, which is
    really odd, but that may again be temporary until a more robust system
    is in place to determine when to stop the updating. I suppose the code
    we've seen is a test to get the updating working first, and then
    refine into the final code later.

    The more usual design would probably be to have an external Runnable
    calling repaint on a set of components registered with it as needing
    automatic updating. I'm not sure also of the effect of calling repaint
    from arbitrary threads. I checked the JComponent docs and it doesn't
    say that it should be done on the event-dispatch thread, at least not
    in the repaint method descriptions themselves. If so you'd need to use
    a SwingUtilities.invokeLater on a runnable that calls repaint once on
    the component.

    Another thing to consider is whether the compiler or JVM is choking on
    identifiers with too high a consonant-to-vowel ratio. ;)
     
    Twisted, Jun 17, 2007
    #3
  4. Kgbol

    Kgbol Guest

    Ok, now this works fine, thanks very much. I was creating my thread
    wrong. Funny is taht it was based on an example from a book:) It
    should be as you said.

    (new Thread(this)).start();

    This program is just for testing how to paint in swing. Could you
    explain me also, why in "run()" method i can only use methods and
    variables from the class that run method is used in.
     
    Kgbol, Jun 17, 2007
    #4
  5. Kgbol

    Lew Guest

    Kgbol wrote:
    >
    > This program is just for testing how to paint in swing. Could you
    > explain me also, why in "run()" method i can only use methods and
    > variables from the class that run method is used in.


    That's not strictly true - you can access an object's accessible methods and
    variables via a reference to that object even if that object is of a different
    class than the caller.

    You can eliminate the explicit object reference (class reference for statics)
    only when the reference is 'this' (respectively, the class of 'this').

    Within any call via a referenced object, this or otherwise, you can only
    invoke the methods defined for the type of that object. That is fundamental Java.

    How is the system supposed to know that a call like
    foo( something );

    is supposed to use the foo() from another class? Of course it can only use
    methods from the class making the call, because that call is equivalent to
    this.foo( something );
    .. You are limited to methods defined in the class for 'this'.

    This is very basic Java syntax and semantics.

    --
    Lew
     
    Lew, Jun 17, 2007
    #5
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. stan k.
    Replies:
    1
    Views:
    9,808
    Babu Kalakrishnan
    Nov 7, 2003
  2. Jesse Pavel

    Swing Menu Painting, 2D Demo

    Jesse Pavel, Feb 15, 2004, in forum: Java
    Replies:
    2
    Views:
    832
    Jesse Pavel
    Feb 18, 2004
  3. matt

    Swing Painting Problems

    matt, Mar 28, 2007, in forum: Java
    Replies:
    2
    Views:
    373
  4. Evan

    Swing painting problems

    Evan, Mar 8, 2008, in forum: Java
    Replies:
    1
    Views:
    425
    Peter Duniho
    Mar 8, 2008
  5. Replies:
    10
    Views:
    8,604
    Roedy Green
    Apr 11, 2009
Loading...

Share This Page