JColorChooser的:保存/恢复色板面板最近的颜色(JColorChooser: Save/

2019-06-24 21:34发布

我使用的是在JColorChooser的应用程序中的各个地方。 可以有可调用的JColorChooser的面板的多个实例。
在选择器的“色板”面板的“最近”色的区域,其中仅中JColorChooser的每个实例中仍然存在。 我想(一)在我所有的挑肥拣瘦相同的“最近”的色彩在我的应用程序,以及(b)将颜色保存到磁盘 ,以便这些颜色生存关闭并重新启动应用程序。
(至少(A)可以通过使用同一个选择器实例遍布整个应用程序来解决,但apears麻烦,因为我需要非常小心连接changelisteners,并添加/删除选择器面板/从各种对话。)

我没有找到,让我设定(恢复)这些“最近的”颜色选择器面板中的任何方法。 所以对我来说,这似乎是实现这一目标的唯一途径是:

  • 序列化和保存/恢复整个选择器(选配面板?)或
  • 从头开始创建自己的选取器面板

这是正确的,还是我失去了一些东西?

BTW:我也想检测在选配双击,但似乎很难找到我的鼠标侦听器连接到正确的地方。 我真的需要深入的选择器面板的内部结构做到这一点? (不,它不工作,以检测在同一颜色的第二次点击,因为如果被点击不同的颜色变化侦听器只触发。)

Answer 1:

正如你注意到没有,没有公共的API来访问DefaultSwatchChooserPanel最近的颜色,甚至是面板本身不能访问。

正如你需要一些逻辑/豆持有反正重置最近的颜色(加上扩展鼠标交互),滚动你自己是要走的路。 对于一些指导,看一看样本面板(咳...... C&P你需要什么,并修改你做什么不是)的实施。 基本上,像

// a bean that keeps track of the colors
public static class ColorTracker extends AbstractBean {

    private List<Color> colors = new ArrayList<>();

    public void addColor(Color color) {
        List<Color> old = getColors();
        colors.add(0, color);
        firePropertyChange("colors", old, getColors());
    }

    public void setColors(List<Color> colors) {
        List<Color> old = getColors();
        this.colors = new ArrayList<>(colors);
        firePropertyChange("colors", old, getColors());
    }

    public List<Color> getColors() {
        return new ArrayList<>(colors);
    }
}

// a custom SwatchChooserPanel which takes and listens to the tracker changes
public class MySwatchChooserPanel ... {

   ColorTracker tracker;

   public void setColorTracker(....) {
       // uninstall old tracker 
       ....
       // install new tracker
       this.tracker = tracker;
       if (tracker != null) 
           tracker.addPropertyChangeListener(.... );
       updateRecentSwatchPanel()
   }

   /** 
    * A method updating the recent colors in the swatchPanel
    * This is called whenever necessary, specifically after building the panel,
    * on changes of the tracker, from the mouseListener
    */
   protected void updateRecentSwatchPanel() {
       if (recentSwatchPanel == null) return;
       recentSwatchPanel.setMostRecentColors(tracker != null ? tracker.getColors() : null);
   }

// the mouseListener which updates the tracker and triggers the doubleClickAction
// if available
class MainSwatchListener extends MouseAdapter implements Serializable {
    @Override
    public void mousePressed(MouseEvent e) {
        if (!isEnabled())
            return;
        if (e.getClickCount() == 2) {
            handleDoubleClick(e);
            return;
        }

        Color color = swatchPanel.getColorForLocation(e.getX(), e.getY());
        setSelectedColor(color);
        if (tracker != null) {
            tracker.addColor(color);
        } else {
            recentSwatchPanel.setMostRecentColor(color);
        }
    }

    /**
     * @param e
     */
    private void handleDoubleClick(MouseEvent e) {
        if (action != null) {
            action.actionPerformed(null);
        }
    }
}


} 

// client code can install the custom panel on a JFileChooser, passing in a tracker
private JColorChooser createChooser(ColorTracker tracker) {
    JColorChooser chooser = new JColorChooser();
    List<AbstractColorChooserPanel> choosers = 
            new ArrayList<>(Arrays.asList(chooser.getChooserPanels()));
    choosers.remove(0);
    MySwatchChooserPanel swatch = new MySwatchChooserPanel();
    swatch.setColorTracker(tracker);
    swatch.setAction(doubleClickAction);
    choosers.add(0, swatch);
    chooser.setChooserPanels(choosers.toArray(new AbstractColorChooserPanel[0]));
    return chooser;
}

至于给DoubleClick处理:提升swatchChooser所采取的措施,并调用从MouseListener的适当的行动。



Answer 2:

您可以使用JColorChooser.createDialog方法-参数之一是JColorChooser 。 使用的静态实例JColorChooser ,并使其成为Dialog modal -这样一来,仅显示在一个时间一个颜色选择。

createDialog方法也需要ActionListeners作为确定和取消按钮参数。 因此,真的没有管理听众。 当然,这不会保留应用程序的调用最近的颜色,只是坚持当前的应用程序最近的颜色。



Answer 3:

下面是使用反射解决方法 - 它会工作提供了底层的实现不会改变。 假设你有一个JColorChooser的,请将您最近的颜色,它是这样的:

    final JColorChooser chooser = new JColorChooser(Color.white);

    for (AbstractColorChooserPanel p : chooser.getChooserPanels()) {

        if (p.getClass().getSimpleName().equals("DefaultSwatchChooserPanel")) {

            Field recentPanelField = p.getClass().getDeclaredField("recentSwatchPanel");
            recentPanelField.setAccessible(true);

            Object recentPanel = recentPanelField.get(p);

            Method recentColorMethod = recentPanel.getClass().getMethod("setMostRecentColor", Color.class);
            recentColorMethod.setAccessible(true);

            recentColorMethod.invoke(recentPanel, Color.BLACK);
            recentColorMethod.invoke(recentPanel, Color.RED);

            //add more colors as desired

            break;
        }

    }


文章来源: JColorChooser: Save/restore recent colors in Swatches panel