gpt4 book ai didi

java - JTree 和 JButtons - 鼠标悬停在 Button 上时渲染错误

转载 作者:太空宇宙 更新时间:2023-11-04 07:52:04 25 4
gpt4 key购买 nike

我在使用 JTree 和 JButton 时遇到问题似乎当进入编辑模式并将鼠标悬停在 TreeCell 上的按钮上时,它会在按钮内渲染树的某些部分。即使从一个按钮拖动到同一行中的另一个按钮,它也会将一个按钮呈现在另一个按钮之上。

这是一个简短的 self 解释示例,您可以复制粘贴以了解我的意思。

import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.util.EventObject;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTree;
import javax.swing.UIManager;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.DefaultTreeCellEditor;
import javax.swing.tree.DefaultTreeCellRenderer;


public class MyProblemWithTree {

public static void main(String...args) {
JFrame frame = new JFrame("Panel");
JScrollPane scroll = new JScrollPane();

DefaultMutableTreeNode node = new DefaultMutableTreeNode("Root");

DefaultMutableTreeNode nodeChild = new DefaultMutableTreeNode("childcaretaker1");
nodeChild.add(new DefaultMutableTreeNode("child1"));
nodeChild.add(new DefaultMutableTreeNode("child2"));

node.add(nodeChild);


final JTree tree = new JTree(node);

tree.setCellRenderer(new MyTreeCellRenderer());
tree.setEditable(true);
tree.setCellEditor(new MyTreeCellEditor(tree));

tree.addMouseMotionListener(new MouseMotionListener() {

@Override
public void mouseMoved(MouseEvent e) {
// TODO Auto-generated method stub
if (tree.getRowForLocation(e.getX(), e.getY()) != -1)
{
tree.startEditingAtPath(tree.getPathForLocation(e.getX(), e.getY()));
}
}

@Override
public void mouseDragged(MouseEvent arg0) {
// TODO Auto-generated method stub

}
});

scroll.setViewportView(tree);
frame.add(scroll);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.pack();
frame.setVisible(true);
}
}
class MyTreeCellEditor extends DefaultTreeCellEditor {

JPanel leafPanel;
JLabel colorIcon;
PlayButton play;
PauseButton pause;
JLabel name;

public MyTreeCellEditor(JTree tree) {
super(tree, (MyTreeCellRenderer)tree.getCellRenderer());
leafPanel = new JPanel(new FlowLayout());
colorIcon = new JLabel(UIManager.getIcon("OptionPane.informationIcon"));
play = new PlayButton();
pause = new PauseButton();
name = new JLabel();

play.addActionListener(new ActionListener() {

@Override
public void actionPerformed(ActionEvent arg0) {
// TODO Auto-generated method stub
System.out.println("Playbutton klickt");
}
});

leafPanel.add(colorIcon);
leafPanel.add(name);
leafPanel.add(pause);
leafPanel.add(play);
}


@Override
public Component getTreeCellEditorComponent(JTree tree, Object value,
boolean selected, boolean expanded, boolean leaf, int row) {

name.setText((String)((DefaultMutableTreeNode)value).getUserObject());
pause.setVisible(!leaf);
return leafPanel;
}

@Override
public boolean isCellEditable(EventObject arg0) {
return true;
}
}
class MyTreeCellRenderer extends DefaultTreeCellRenderer {
private static final long serialVersionUID = 3691823996133806942L;

JPanel leafPanel;
JLabel colorIcon;
PlayButton play;
PauseButton pause;
JLabel name;

DefaultTreeCellRenderer defaultRenderer = new DefaultTreeCellRenderer();

Color backgroundSelectionColor;
Color backgroundNonSelectionColor;


public MyTreeCellRenderer() {
leafPanel = new JPanel(new FlowLayout());
colorIcon = new JLabel(UIManager.getIcon("OptionPane.informationIcon"));
play = new PlayButton();
pause = new PauseButton();
name = new JLabel();

leafPanel.add(colorIcon);
leafPanel.add(name);
leafPanel.add(pause);
leafPanel.add(play);

backgroundSelectionColor = new Color(200,200,255,50);
backgroundNonSelectionColor = new Color(0,0,0,0);
}

@Override
public Component getTreeCellRendererComponent(JTree tree, Object value, boolean selected, boolean expanded, boolean leaf, int row, boolean hasFocus) {
name.setText((String)((DefaultMutableTreeNode) value).getUserObject());
if (selected) {
leafPanel.setBackground(backgroundSelectionColor);
} else {
leafPanel.setBackground(backgroundNonSelectionColor);
}
leafPanel.setEnabled(tree.isEnabled());
pause.setVisible(!leaf);
return leafPanel;
}
}

class PlayButton extends JButton{
private static final long serialVersionUID = 550654173835539853L;

Dimension size = new Dimension(140,28);

public PlayButton() {
setIcon(UIManager.getIcon("OptionPane.informationIcon"));
setPressedIcon(UIManager.getIcon("OptionPane.errorIcon"));
setBackground(new Color(0,0,0,0));
setBorderPainted(false);
setPreferredSize(size);
setMaximumSize(size);
setMinimumSize(size);
}
}
class PauseButton extends JButton{
private static final long serialVersionUID = -5877843953696256070L;

Dimension size = new Dimension(140,28);

public PauseButton() {
setIcon(UIManager.getIcon("OptionPane.warningIcon"));
setPressedIcon(UIManager.getIcon("OptionPane.questionIcon"));
setBackground(new Color(0,0,0,0));
setBorderPainted(false);
setPreferredSize(size);
setMaximumSize(size);
setMinimumSize(size);
}
}

即使我删除了这部分。我必须单击一个单元格才能进入编辑模式,我仍然可以通过用鼠标离开单元格并返回来获得效果。

        public void mouseMoved(MouseEvent e) {
// TODO Auto-generated method stub
if (tree.getRowForLocation(e.getX(), e.getY()) != -1)
{
tree.startEditingAtPath(tree.getPathForLocation(e.getX(), e.getY()));
}
}

我已经花了 4 天时间进行 JTree 定制。但这真的让我很困惑,我如何通过输入按钮来停止渲染。

最佳答案

我不知道如何解决这个问题,但使用 invokeLatersetRowHeight() 会有所帮助。

public static void main(String... args) {
EventQueue.invokeLater(new Runnable() {

@Override
public void run() {
JFrame frame = new JFrame("Panel");
...
tree.setRowHeight(icon.getIconHeight());
...
frame.setVisible(true);
}
});
}

关于java - JTree 和 JButtons - 鼠标悬停在 Button 上时渲染错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14277414/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com