Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

CellRendererPane causes cursor flickering during drag and drop

95 views
Skip to first unread message

lemmi

unread,
Apr 27, 2011, 11:44:29 AM4/27/11
to
To: comp.lang.java.gui
Hi there,

I have a nasty bug that I worked on for a couple of days already and I
finally managed to isolate the problem. It seems that the use of a
CellRendererPane causes the mouse cursor to flicker during drag and
drop, but only if the "validate" flag is set to true. This effect
seems to happen on Windows only (Mac works fine). I am using Windows
XP. I have written a little standalone test case that you can find
below. Simply initiate a drag and drop sequence from one panel to
another and play around with the checkbox in the upper left corner. If
selected, the renderer component that draws the button will be
validated before its paint method gets called. When this happens the
cursor starts to flicker.

I would appreciate it very much if anyone could tell me how to get rid
of this problem. My renderer components are often quite complex and I
need to have them validated before calling them, so setting "validate"
to false does not work for me.

--Dirk
www.dlsc.com

package com.dlsc.test;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.dnd.DnDConstants;
import java.awt.dnd.DragGestureEvent;
import java.awt.dnd.DragGestureListener;
import java.awt.dnd.DragSource;
import java.awt.dnd.DragSourceDragEvent;
import java.awt.dnd.DragSourceDropEvent;
import java.awt.dnd.DragSourceEvent;
import java.awt.dnd.DragSourceListener;
import java.awt.dnd.DropTarget;
import java.awt.dnd.DropTargetDragEvent;
import java.awt.dnd.DropTargetDropEvent;
import java.awt.dnd.DropTargetEvent;
import java.awt.dnd.DropTargetListener;
import java.io.IOException;

import javax.swing.CellRendererPane;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.border.TitledBorder;


public class DnDTestFrame extends JFrame {
private JCheckBox checkBox = new JCheckBox("Cell renderer validates",
true);

public DnDTestFrame() {
super("DnDTest");

add(BorderLayout.NORTH, checkBox);
add(BorderLayout.WEST,new DnDTestPanel("Left", this));
add(BorderLayout.EAST,new DnDTestPanel("Right", this));
pack();
setVisible(true);
}

public boolean isValidating() {
return checkBox.isSelected();
}

/**
* @param args
*/
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
new DnDTestFrame();
}
});
}
}


class DnDTestPanel extends JPanel implements DragGestureListener,
DragSourceListener, DropTargetListener {

private String title;
private CellRendererPane rendererPane = new CellRendererPane();
private JButton rendererComp = new JButton("Renderer");
private DnDTestFrame frame;

public DnDTestPanel(String title, DnDTestFrame frame) {
this.title = title;
this.frame = frame;

setLayout(null);
add(rendererPane);

setBackground(Color.WHITE);
setPreferredSize(new Dimension(300, 300));
setBorder(new TitledBorder(title));
DragSource.getDefaultDragSource().createDefaultDragGestureRecognizer(
this, DnDConstants.ACTION_COPY_OR_MOVE, this);
new DropTarget(this, DnDConstants.ACTION_COPY_OR_MOVE, this);
}

@Override
protected void paintComponent(Graphics g) {
rendererPane.paintComponent(g, rendererComp, this, 20, 20, 100, 30,
frame.isValidating());
}

public void dragGestureRecognized(DragGestureEvent dge) {
dge.startDrag(null, new Transferable() {

public Object getTransferData(DataFlavor flavor)
throws UnsupportedFlavorException, IOException {
return null;
}

public DataFlavor[] getTransferDataFlavors() {
return new DataFlavor[] { DataFlavor.plainTextFlavor };
}

public boolean isDataFlavorSupported(DataFlavor flavor) {
return true;
}
});
}

// drag source
public void dragDropEnd(DragSourceDropEvent dsde) {
}

public void dragEnter(DragSourceDragEvent dsde) {
}

public void dragExit(DragSourceEvent dse) {
}

public void dragOver(DragSourceDragEvent dsde) {
}

public void dropActionChanged(DragSourceDragEvent dsde) {
}

// drop target
public void dragEnter(DropTargetDragEvent dtde) {
repaint();
}

public void dragExit(DropTargetEvent dte) {
repaint();
}

public void dragOver(DropTargetDragEvent dtde) {
repaint();
}

public void drop(DropTargetDropEvent dtde) {
}

public void dropActionChanged(DropTargetDragEvent dtde) {
}
}

---
* Synchronet * The Whitehouse BBS --- whitehouse.hulds.com --- check it out free usenet!
--- Synchronet 3.15a-Win32 NewsLink 1.92
Time Warp of the Future BBS - telnet://time.synchro.net:24

Roedy Green

unread,
Apr 12, 2008, 4:19:57 PM4/12/08
to
On Fri, 11 Apr 2008 10:41:39 -0700 (PDT), lemmi
<dlemm...@gmail.com> wrote, quoted or indirectly quoted someone who
said :

>I would appreciate it very much if anyone could tell me how to get rid
>of this problem.

Sometimes the problem is actually a bug in the video driver that fancy
code brings to the surface, like putting a hot compress on an
infection.

Try your code on a different Windows machine with a different video
card. See if there is an update for your video card from the
manufacturer.
--

Roedy Green Canadian Mind Products
The Java Glossary
http://mindprod.com

Roedy Green

unread,
Apr 12, 2008, 4:21:57 PM4/12/08
to
On Fri, 11 Apr 2008 10:41:39 -0700 (PDT), lemmi
<dlemm...@gmail.com> wrote, quoted or indirectly quoted someone who
said :

>DataFlavor.plainTextFlavor

this is deprecated.

Roedy Green

unread,
Apr 12, 2008, 4:31:42 PM4/12/08
to
On Fri, 11 Apr 2008 10:41:39 -0700 (PDT), lemmi
<dlemm...@gmail.com> wrote, quoted or indirectly quoted someone who
said :

>I have a nasty bug that I worked on for a couple of days already and I


>finally managed to isolate the problem.

I have compiled the program and run it on Windows Vista on an Acer
integrated Video card.

I notice a little box gets drawn to the bottom right of the cursor and
then erased as you move the cursor. I presume this is what you mean by
"flicker".

Presumably somebody is calling setCursor back and forth for two
different cursors.

You might try an IDE like IntelliJ Idea with its integrated debugger
to find out who is doing it and why.

Hats off to you for coming up with such a succinct SSCCE.
http://mindprod.com/jgloss/sscce.html

lemmi

unread,
Apr 14, 2008, 7:22:13 AM4/14/08
to
On 12 Apr., 22:19, Roedy Green <see_webs...@mindprod.com.invalid>
wrote:

>
> Try your code on a different Windows machine with a different video
> card.  See if there is an update for your video card from the
> manufacturer.

This has been tested on dozends of machines and they all show the same
problem. It even shows up on Macs running in a virtual machine
(Parallels), which means that it is pretty far away from the actual
hardware.

Dirk

lemmi

unread,
Apr 14, 2008, 7:23:40 AM4/14/08
to
> Presumably somebody is calling setCursor back and forth for two
> different cursors.

setCursor() is not being called. During a drag and drop operation the
cursor management seems to happen somewhere else but I don't know
where.

Dirk

lemmi

unread,
Apr 14, 2008, 9:01:27 AM4/14/08
to
On 14 Apr., 13:22, lemmi <dlemmerm...@gmail.com> wrote:
> problem. It even shows up on Macs running in a virtual machine
> (Parallels), which means that it is pretty far away from the actual
> hardware.
>

I meant "Macs running Winodws XP in a virtual machine environment".

Dirk

Roedy Green

unread,
Apr 14, 2008, 5:03:27 PM4/14/08
to
On Mon, 14 Apr 2008 04:23:40 -0700 (PDT), lemmi

<dlemm...@gmail.com> wrote, quoted or indirectly quoted someone who
said :

>setCursor() is not being called. During a drag and drop operation the


>cursor management seems to happen somewhere else but I don't know
>where.

At least on my hardware, it seems very likely the cursor is being
redrawn back and forth between two different forms. This implies
SOMEONE, perhaps deep in the bowels or in a UI LAF is calling
setCursor.

If I were you I would put a trap on setCursor and find out if and who
is calling it.

Also, If you can get a snapshot of the variant cursor, and if you can
recognise it, that might help track down who is setting it and where.

The queasy feeling I have about this is even after you track it down
and present it to Sun, they will say it is not a bug but a feature.

0 new messages