Question

I am currently making a pain program and have encountered into a problem when I am attempting to make g2D alpha-friendly. The problem is, that as soon as the paint method is refreshed, it draws on what the user drew, as well as GUI components that the user has hovered over. This is the code in the pain method:

    public void paintComponent(Graphics comp)
{
    Graphics2D board = (Graphics2D) comp;

    AlphaComposite ac=AlphaComposite.getInstance(AlphaComposite.SRC_OVER,0.5f);
    Composite oldComp=board.getComposite();
    board.setComposite(ac); //used composite as a suggestion found on stackover flow; 
                                //did not work.

    for(int i = 0; i < al.size(); i++)
    {
        board.setColor(cl.get(i));
        board.setStroke(new BasicStroke(tl.get(i),lineEnd.get(i),juncture.get(i)));
        board.draw((Shape) al.get(i));

    }
    board.setComposite(oldComp);

}

Picture of what it looks like:

I have a feeling that the absolute position of the drawing board is in the left hand corner, so it draws it on as you update the paint method. I do not know how to solve that though. Here is my code for the setup of the drawing board if you need it:

    public Container(String name, String text, String text2) 
{
    addMouseListener(mouseListener);
    addMouseMotionListener(this);
    setBorder(BorderFactory.createLineBorder(Color.black));

}

and in the main JFrame:

items[0].addActionListener(new ActionListener(){
        public void actionPerformed(ActionEvent e) { 
            JTextField name = new JTextField();
            JTextField width = new JTextField();
            JTextField height = new JTextField();
            final JComponent[] inputs = new JComponent[] { new JLabel("Creating new image: please fill in the required text fields."), new JLabel("Name: "), name, new JLabel("Width: "), width, new JLabel("Height: "), height};
            name.addAncestorListener( new RequestFocusListener() );
            JOptionPane.showMessageDialog(null, inputs, "New Image", JOptionPane.PLAIN_MESSAGE);
            Container cont = new Container(name.getText(), width.getText(), height.getText());
            addContainer(cont);
            cont.setPreferredSize(new Dimension(Integer.parseInt(width.getText()),Integer.parseInt(height.getText())));

            JScrollPane scroll = new JScrollPane();
            JPanel pane = new JPanel();
            pane.add(cont);
            scroll.setViewportView(pane);
            pane.setBackground(Color.lightGray);
            tabbed.addTab(name.getText(), scroll); 
            setCursor("pen");
            } 
        });

Thanks for your help!

EDIT:

Here are the array lists:

static ArrayList<Shape> al = new ArrayList<Shape>();
static ArrayList<Color> cl = new ArrayList<Color>();
static ArrayList<Integer> tl = new ArrayList<Integer>();
static ArrayList<Integer> lineEnd = new ArrayList<Integer>();
static ArrayList<Integer> juncture = new ArrayList<Integer>();
Was it helpful?

Solution

Basically, you've broken the paint chain.

When a paint cycle runs, a top level method is called (typically paint), which then calls a chain of events to perform the actual painting.

Each element in the chain does a particular job and builds on each other, failure to honour this chain will cause you problems.

Generally, the Graphics context for a window is a shared resource, meaning that during any given paint cycle, all the components that are painted share the same Graphics context

To fix the initial problem of " it draws on what the user drew, as well as GUI components that the user has hovered over", you need to call super.paintComponent, for example...

public void paintComponent(Graphics comp) {
    super.paintComponent(comp);
    Graphics2D board = (Graphics2D) comp;

This will clear the Graphics context from what was painted to it previous.

paintComponent should remain protected as the should no reason to allow anybody else to ever call it directly.

Take a look at Performing Custom Painting and Painting in AWT and Swing for more details

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top