/** * @(#)DefaultColorSliderModel.java * * Copyright (c) 2008 The authors and contributors of JHotDraw. * You may not use, copy or modify this file, except in compliance with the * accompanying license terms. */ package org.jhotdraw.color; import java.awt.Color; import java.awt.color.ColorSpace; import java.awt.color.ICC_ColorSpace; import java.util.LinkedList; import javax.swing.*; import javax.swing.event.*; /** * DefaultColorSliderModel. * * @author Werner Randelshofer * @version $Id$ */ public class DefaultColorSliderModel extends AbstractColorSlidersModel { private static final long serialVersionUID = 1L; protected ColorSpace colorSpace; /** * JSlider's associated to this model. */ protected LinkedList<JSlider> sliders = new LinkedList<>(); /** * Components of the color model. */ protected DefaultBoundedRangeModel[] componentModels; /** Creates a color slider model with an ICC sRGB color space. */ public DefaultColorSliderModel() { setColorSpace(ICC_ColorSpace.getInstance(ICC_ColorSpace.CS_sRGB)); } /** Creates a color slider model with the specified color space. */ public DefaultColorSliderModel(ColorSpace sys) { setColorSpace(sys); } @Override public void setColorSpace(ColorSpace newValue) { ColorSpace oldValue = colorSpace; colorSpace = newValue; componentModels = new DefaultBoundedRangeModel[colorSpace.getNumComponents()]; for (int i = 0; i < componentModels.length; i++) { componentModels[i] = new DefaultBoundedRangeModel(); if ((colorSpace.getMaxValue(i)-colorSpace.getMinValue(i))>=10f) { componentModels[i].setMinimum((int)colorSpace.getMinValue(i)); componentModels[i].setMaximum((int)colorSpace.getMaxValue(i)); } else { componentModels[i].setMinimum((int)(colorSpace.getMinValue(i)*100f)); componentModels[i].setMaximum((int)(colorSpace.getMaxValue(i)*100f)); } final int componentIndex = i; componentModels[i].addChangeListener( new ChangeListener() { @Override public void stateChanged(ChangeEvent e) { fireColorChanged(componentIndex); fireStateChanged(); } }); } } /** * Configures a JSlider for this model. * If the JSlider is already configured for another model, * it is unconfigured first. */ @Override public void configureSlider(int componentIndex, JSlider slider) { if (slider.getClientProperty("colorSliderModel") != null) { ((DefaultColorSliderModel) slider.getClientProperty("colorSliderModel")).unconfigureSlider(slider); } if (!(slider.getUI() instanceof ColorSliderUI)) { slider.setUI((ColorSliderUI) ColorSliderUI.createUI(slider)); } slider.setModel(getBoundedRangeModel(componentIndex)); slider.putClientProperty("colorSliderModel", this); slider.putClientProperty("colorComponentIndex", componentIndex); addColorSlider(slider); } /** * Unconfigures a JSlider from this model. */ @Override public void unconfigureSlider(JSlider slider) { if (slider.getClientProperty("colorSliderModel") == this) { // XXX - This creates a NullPointerException ?? //slider.setUI((SliderUI) UIManager.getUI(slider)); slider.setModel(new DefaultBoundedRangeModel()); slider.putClientProperty("colorSliderModel", null); slider.putClientProperty("colorComponentIndex", null); removeColorSlider(slider); } } /** * Returns the bounded range model of the specified color componentIndex. */ @Override public DefaultBoundedRangeModel getBoundedRangeModel(int componentIndex) { return componentModels[componentIndex]; } /** * Returns the value of the specified color componentIndex. */ public int getSliderValue(int componentIndex) { return componentModels[componentIndex].getValue(); } /** * Sets the value of the specified color componentIndex. */ public void setSliderValue(int componentIndex, int value) { componentModels[componentIndex].setValue(value); } public void addColorSlider(JSlider slider) { sliders.add(slider); } public void removeColorSlider(JSlider slider) { sliders.remove(slider); } protected void fireColorChanged(int componentIndex) { Integer index = componentIndex; Color value = getColor(); for (JSlider slider : sliders) { slider.putClientProperty("colorComponentChange", index); slider.putClientProperty("colorComponentValue", value); } } @Override public ColorSpace getColorSpace() { return colorSpace; } @Override public int getComponentCount() { return colorSpace.getNumComponents(); } @Override public Color getColor() { float[] c = new float[getComponentCount()]; int i = 0; for (DefaultBoundedRangeModel brm : componentModels) { c[i] = (brm.getValue() - brm.getMinimum()) / (float) (brm.getMaximum() - brm.getMinimum()) * (colorSpace.getMaxValue(i) - colorSpace.getMinValue(i)) + colorSpace.getMinValue(i); i++; } try { return ColorUtil.toColor(colorSpace, c); } catch (IllegalArgumentException e) { for (i = 0; i < c.length; i++) { System.err.println(i + "=" + c[i]+" "+colorSpace.getMinValue(i)+".."+colorSpace.getMaxValue(i)); } throw e; } } @Override public int getInterpolatedRGB(int i, float componentValue) { float[] c = new float[Math.max(3,getComponentCount())]; int j = 0; for (DefaultBoundedRangeModel brm : componentModels) { c[j] = ((brm.getValue() - brm.getMinimum()) / (float) (brm.getMaximum() - brm.getMinimum())) * (colorSpace.getMaxValue(j) - colorSpace.getMinValue(j)) + colorSpace.getMinValue(j); j++; } c[i] = componentValue; return ColorUtil.CStoRGB24(colorSpace, c,c); } @Override public void setComponent(int i, float newValue) { BoundedRangeModel brm = componentModels[i]; brm.setValue((int) (((newValue - colorSpace.getMinValue(i))// / (colorSpace.getMaxValue(i) - colorSpace.getMinValue(i)))// * (brm.getMaximum() - brm.getMinimum())) + brm.getMinimum()); } @Override public float getComponent(int i) { BoundedRangeModel brm = componentModels[i]; return (brm.getValue() - brm.getMinimum()) // / (float) (brm.getMaximum() - brm.getMinimum())// * (colorSpace.getMaxValue(i) - colorSpace.getMinValue(i))// + colorSpace.getMinValue(i); } @Override public void setColor(Color newValue) { float[] c = ColorUtil.fromColor(colorSpace, newValue); int i = 0; for (DefaultBoundedRangeModel brm : componentModels) { brm.setValue(// (int) (((c[i] - colorSpace.getMinValue(i))// / (colorSpace.getMaxValue(i) - colorSpace.getMinValue(i))) // * (brm.getMaximum() - brm.getMinimum()) + brm.getMinimum())); i++; } } @Override public float[] getComponents() { float[] c = new float[getComponentCount()]; for (int i = 0; i < c.length; i++) { BoundedRangeModel brm = componentModels[i]; c[i] = (brm.getValue() - brm.getMinimum()) // / (float) (brm.getMaximum() - brm.getMinimum())// * (colorSpace.getMaxValue(i) - colorSpace.getMinValue(i))// + colorSpace.getMinValue(i); } return c; } }