how to draw rectangle on java applet using mouse drag event

21,329

homework?

basically what you need to do is:

  1. on mouse down keep the mouse-down coordinates and repaint
  2. on mouse move keep current mouse coordinates and repaint
  3. on mouse up, nullify the mouse-down coordinates to indicate there is no rect, and repaint.
  4. on paint, draw background and then rect between mousedown and cur-mouse coordinates.

if you don't want to keep a background image, you can do a trick with the Graphics xor function, drawing the same rect twice will erase the old rect, so you can use it to restore the old image straight on the graphics object.

Edit: code xor usage sample:

public void paint(Graphics g)
{
   g.setXORMode(Color.black);
   // draw old rect if there is one. this will erase it
   // draw new rect, this will draw xored
   g.setDrawMode(); // restore normal draw mode
}

Xor has the an interesting property:

xor(xor(x)) = x

so xoring the same pixel twice restores it's original color.

Share:
21,329
Rohini Kumar
Author by

Rohini Kumar

Updated on January 18, 2020

Comments

  • Rohini Kumar
    Rohini Kumar over 4 years

    i am using java. i want to draw rectangle based on mousedrag event. if user dragging the mouse, then the rectangle on the applet should increase or decrease basing on current mouse coordinates. i have the following code.

    in the following code i am using [b]SelectionArea[/b] class which extends a canvas on which i am performing drawing operation. i am using [b]image[/b] variable in this class for double buffering to reduce flickering and to save the applet's previous state(i.e drawing content of applet)

    but the code is working fine if i draw first rectangle. if i start to draw second rectangle the previously drawn rectangle is disappearing. i want the previously drawn rectangle to be on the screen

    can any one tell me how to solve this.

    import java.awt.*;
    import java.applet.Applet;
    import java.awt.event.*;
    
    /* 
     * This displays a framed area.  When the user drags within
     * the area, this program displays a rectangle extending from
     * where the user first pressed the mouse button to the current
     * cursor location.
     */
    
    public class RectangleDemo extends Applet {
    SelectionArea drawingPanel;
    Label label;
    
    public void init() {
        GridBagLayout gridBag = new GridBagLayout();
        GridBagConstraints c = new GridBagConstraints();
    
        setLayout(gridBag);
    
        drawingPanel = new SelectionArea(this);
        c.fill = GridBagConstraints.BOTH;
        c.weighty = 1.0;
        c.gridwidth = GridBagConstraints.REMAINDER; //end row
        gridBag.setConstraints(drawingPanel, c);
        add(drawingPanel);
    
        label = new Label("Drag within the framed area.");
        c.fill = GridBagConstraints.HORIZONTAL;
        c.weightx = 1.0;
        c.weighty = 0.0;
        gridBag.setConstraints(label, c);
        add(label);
        drawingPanel.setVisible(true);
    
        validate();
    }
    
    public void paint(Graphics g){
        drawingPanel.repaint();
    }
    
    public void update(Graphics g){
        paint(g);
    }         
    

    }

    class SelectionArea extends Canvas implements ActionListener, MouseListener,    MouseMotionListener{
    Rectangle currentRect;
    RectangleDemo controller;
    //for double buffering
    Image image;
    Graphics offscreen;
    public SelectionArea(RectangleDemo controller) {
        super();
        this.controller = controller;
        addMouseListener(this);
        addMouseMotionListener(this);        
    }
    
    public void actionPerformed(ActionEvent ae){
        repaintoffscreen();
    }
    
    public void repaintoffscreen(){
        image = createImage(this.getWidth(), this.getHeight());
        offscreen = image.getGraphics();
        Dimension d = getSize();
        if(currentRect != null){
            Rectangle box = getDrawableRect(currentRect, d);            
    
            //Draw the box outline.
            offscreen.drawRect(box.x, box.y, box.width - 1, box.height - 1);  
            //repaint();
        }
    }
    
    public void mouseEntered(MouseEvent me) {}
    public void mouseExited(MouseEvent me){ }
    public void mouseClicked(MouseEvent me){}
    public void mouseMoved(MouseEvent me){}
    
    public void mousePressed(MouseEvent me) {        
        currentRect = new Rectangle(me.getX(), me.getY(), 0, 0);
        repaintoffscreen();        
    }
    
    public void mouseDragged(MouseEvent me) {
        System.out.println("here in dragged()");
        currentRect.setSize(me.getX() - currentRect.x, me.getY() - currentRect.y);
        repaintoffscreen();    
        repaint();
    }
    
    public void mouseReleased(MouseEvent me) {
        currentRect.setSize(me.getX() - currentRect.x, me.getY() - currentRect.y);
        repaintoffscreen();  
        repaint();
    }
    
    public void update(Graphics g){
        paint(g);
    }
    
    public void paint(Graphics g) {
        g.drawImage(image, 0, 0, this);
    }
    
    Rectangle getDrawableRect(Rectangle originalRect, Dimension drawingArea) {
        int x = originalRect.x;
        int y = originalRect.y;
        int width = originalRect.width;
        int height = originalRect.height;
    
        //Make sure rectangle width and height are positive.
        if (width < 0) {
            width = 0 - width;
            x = x - width + 1;
            if (x < 0) {
                width += x;
                x = 0;
            }
        }
        if (height < 0) {
            height = 0 - height;
            y = y - height + 1;
            if (y < 0) {
                height += y;
                y = 0;
            }
        }
    
        //The rectangle shouldn't extend past the drawing area.
        if ((x + width) > drawingArea.width) {
            width = drawingArea.width - x;
        }
        if ((y + height) > drawingArea.height) {
            height = drawingArea.height - y;
        }
    
        return new Rectangle(x, y, width, height);
    }
    

    }

    also if i run this code on full screen mode then i am seeing that the rectangle is appering on screen only after i released the mouse. but i want the rectangle to be on the screen while dragging the mouse and it should change it's dimension according to the current mouse coordinates. can any one help me pls.

  • Rohini Kumar
    Rohini Kumar almost 15 years
    thanks omry, this is not an homework. ok can u give me a code sample on how to work with Grphics xOR function. thanks for help
  • Rohini Kumar
    Rohini Kumar almost 15 years
    hi coobird, thanks for reply. i want to extend my code to draw other symbols like oval,line also. so can i have a common object that i can store in the list? can u tell me what fields that i can put in the object so that i can use this object for drawing previously drawn symbols in the repaintoffscreenmethod(). thanks