1. /*
  2. * @(#)DefaultSwatchChooserPanel.java 1.24 03/01/23
  3. *
  4. * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
  5. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
  6. */
  7. package javax.swing.colorchooser;
  8. import javax.swing.*;
  9. import javax.swing.border.*;
  10. import javax.swing.event.*;
  11. import java.awt.*;
  12. import java.awt.image.*;
  13. import java.awt.event.*;
  14. import java.beans.PropertyChangeEvent;
  15. import java.beans.PropertyChangeListener;
  16. import java.io.Serializable;
  17. /**
  18. * The standard color swatch chooser.
  19. * <p>
  20. * <strong>Warning:</strong>
  21. * Serialized objects of this class will not be compatible with
  22. * future Swing releases. The current serialization support is
  23. * appropriate for short term storage or RMI between applications running
  24. * the same version of Swing. As of 1.4, support for long term storage
  25. * of all JavaBeans<sup><font size="-2">TM</font></sup>
  26. * has been added to the <code>java.beans</code> package.
  27. * Please see {@link java.beans.XMLEncoder}.
  28. *
  29. * @version 1.24 01/23/03
  30. * @author Steve Wilson
  31. */
  32. class DefaultSwatchChooserPanel extends AbstractColorChooserPanel {
  33. SwatchPanel swatchPanel;
  34. RecentSwatchPanel recentSwatchPanel;
  35. MouseListener mainSwatchListener;
  36. MouseListener recentSwatchListener;
  37. private static String recentStr = UIManager.getString("ColorChooser.swatchesRecentText");
  38. public DefaultSwatchChooserPanel() {
  39. super();
  40. }
  41. public String getDisplayName() {
  42. return UIManager.getString("ColorChooser.swatchesNameText");
  43. }
  44. /**
  45. * Provides a hint to the look and feel as to the
  46. * <code>KeyEvent.VK</code> constant that can be used as a mnemonic to
  47. * access the panel. A return value <= 0 indicates there is no mnemonic.
  48. * <p>
  49. * The return value here is a hint, it is ultimately up to the look
  50. * and feel to honor the return value in some meaningful way.
  51. * <p>
  52. * This implementation looks up the value from the default
  53. * <code>ColorChooser.swatchesMnemonic</code>, or if it
  54. * isn't available (or not an <code>Integer</code>) returns -1.
  55. * The lookup for the default is done through the <code>UIManager</code>:
  56. * <code>UIManager.get("ColorChooser.swatchesMnemonic");</code>.
  57. *
  58. * @return KeyEvent.VK constant identifying the mnemonic; <= 0 for no
  59. * mnemonic
  60. * @see #getDisplayedMnemonicIndex
  61. * @since 1.4
  62. */
  63. public int getMnemonic() {
  64. return getInt("ColorChooser.swatchesMnemonic", -1);
  65. }
  66. /**
  67. * Provides a hint to the look and feel as to the index of the character in
  68. * <code>getDisplayName</code> that should be visually identified as the
  69. * mnemonic. The look and feel should only use this if
  70. * <code>getMnemonic</code> returns a value > 0.
  71. * <p>
  72. * The return value here is a hint, it is ultimately up to the look
  73. * and feel to honor the return value in some meaningful way. For example,
  74. * a look and feel may wish to render each
  75. * <code>AbstractColorChooserPanel</code> in a <code>JTabbedPane</code>,
  76. * and further use this return value to underline a character in
  77. * the <code>getDisplayName</code>.
  78. * <p>
  79. * This implementation looks up the value from the default
  80. * <code>ColorChooser.rgbDisplayedMnemonicIndex</code>, or if it
  81. * isn't available (or not an <code>Integer</code>) returns -1.
  82. * The lookup for the default is done through the <code>UIManager</code>:
  83. * <code>UIManager.get("ColorChooser.swatchesDisplayedMnemonicIndex");</code>.
  84. *
  85. * @return Character index to render mnemonic for; -1 to provide no
  86. * visual identifier for this panel.
  87. * @see #getMnemonic
  88. * @since 1.4
  89. */
  90. public int getDisplayedMnemonicIndex() {
  91. return getInt("ColorChooser.swatchesDisplayedMnemonicIndex", -1);
  92. }
  93. public Icon getSmallDisplayIcon() {
  94. return null;
  95. }
  96. public Icon getLargeDisplayIcon() {
  97. return null;
  98. }
  99. /**
  100. * The background color, foreground color, and font are already set to the
  101. * defaults from the defaults table before this method is called.
  102. */
  103. public void installChooserPanel(JColorChooser enclosingChooser) {
  104. super.installChooserPanel(enclosingChooser);
  105. }
  106. protected void buildChooser() {
  107. JPanel superHolder = new JPanel(new BorderLayout());
  108. swatchPanel = new MainSwatchPanel();
  109. swatchPanel.getAccessibleContext().setAccessibleName(getDisplayName());
  110. recentSwatchPanel = new RecentSwatchPanel();
  111. recentSwatchPanel.getAccessibleContext().setAccessibleName(recentStr);
  112. mainSwatchListener = new MainSwatchListener();
  113. swatchPanel.addMouseListener(mainSwatchListener);
  114. recentSwatchListener = new RecentSwatchListener();
  115. recentSwatchPanel.addMouseListener(recentSwatchListener);
  116. JPanel mainHolder = new JPanel(new BorderLayout());
  117. Border border = new CompoundBorder( new LineBorder(Color.black),
  118. new LineBorder(Color.white) );
  119. mainHolder.setBorder(border);
  120. mainHolder.add(swatchPanel, BorderLayout.CENTER);
  121. superHolder.add( mainHolder, BorderLayout.CENTER );
  122. JPanel recentHolder = new JPanel( new BorderLayout() );
  123. recentSwatchPanel.addMouseListener(recentSwatchListener);
  124. recentHolder.setBorder(border);
  125. recentHolder.add(recentSwatchPanel, BorderLayout.CENTER);
  126. JPanel recentLabelHolder = new JPanel(new BorderLayout());
  127. recentLabelHolder.add(recentHolder, BorderLayout.CENTER);
  128. JLabel l = new JLabel(recentStr);
  129. l.setLabelFor(recentSwatchPanel);
  130. recentLabelHolder.add(l, BorderLayout.NORTH);
  131. JPanel recentHolderHolder = new JPanel(new CenterLayout());
  132. if (this.getComponentOrientation().isLeftToRight()) {
  133. recentHolderHolder.setBorder(new EmptyBorder(2,10,2,2));
  134. } else {
  135. recentHolderHolder.setBorder(new EmptyBorder(2,2,2,10));
  136. }
  137. recentHolderHolder.add(recentLabelHolder);
  138. superHolder.add( recentHolderHolder, BorderLayout.AFTER_LINE_ENDS );
  139. add(superHolder);
  140. }
  141. public void uninstallChooserPanel(JColorChooser enclosingChooser) {
  142. super.uninstallChooserPanel(enclosingChooser);
  143. swatchPanel.removeMouseListener(mainSwatchListener);
  144. recentSwatchPanel.removeMouseListener(recentSwatchListener);
  145. swatchPanel = null;
  146. recentSwatchPanel = null;
  147. mainSwatchListener = null;
  148. recentSwatchListener = null;
  149. removeAll(); // strip out all the sub-components
  150. }
  151. public void updateChooser() {
  152. }
  153. class RecentSwatchListener extends MouseAdapter implements Serializable {
  154. public void mousePressed(MouseEvent e) {
  155. Color color = recentSwatchPanel.getColorForLocation(e.getX(), e.getY());
  156. getColorSelectionModel().setSelectedColor(color);
  157. }
  158. }
  159. class MainSwatchListener extends MouseAdapter implements Serializable {
  160. public void mousePressed(MouseEvent e) {
  161. Color color = swatchPanel.getColorForLocation(e.getX(), e.getY());
  162. getColorSelectionModel().setSelectedColor(color);
  163. recentSwatchPanel.setMostRecentColor(color);
  164. }
  165. }
  166. }
  167. class SwatchPanel extends JPanel {
  168. protected Color[] colors;
  169. protected Dimension swatchSize;
  170. protected Dimension numSwatches;
  171. protected Dimension gap;
  172. public SwatchPanel() {
  173. initValues();
  174. initColors();
  175. setToolTipText(""); // register for events
  176. setOpaque(true);
  177. setBackground(Color.white);
  178. setRequestFocusEnabled(false);
  179. }
  180. public boolean isFocusTraversable() {
  181. return false;
  182. }
  183. protected void initValues() {
  184. }
  185. public void paintComponent(Graphics g) {
  186. g.setColor(getBackground());
  187. g.fillRect(0,0,getWidth(), getHeight());
  188. for (int row = 0; row < numSwatches.height; row++) {
  189. for (int column = 0; column < numSwatches.width; column++) {
  190. g.setColor( getColorForCell(column, row) );
  191. int x;
  192. if ((!this.getComponentOrientation().isLeftToRight()) &&
  193. (this instanceof RecentSwatchPanel)) {
  194. x = (numSwatches.width - column - 1) * (swatchSize.width + gap.width);
  195. } else {
  196. x = column * (swatchSize.width + gap.width);
  197. }
  198. int y = row * (swatchSize.height + gap.height);
  199. g.fillRect( x, y, swatchSize.width, swatchSize.height);
  200. g.setColor(Color.black);
  201. g.drawLine( x+swatchSize.width-1, y, x+swatchSize.width-1, y+swatchSize.height-1);
  202. g.drawLine( x, y+swatchSize.height-1, x+swatchSize.width-1, y+swatchSize.height-1);
  203. }
  204. }
  205. }
  206. public Dimension getPreferredSize() {
  207. int x = numSwatches.width * (swatchSize.width + gap.width) -1;
  208. int y = numSwatches.height * (swatchSize.height + gap.height) -1;
  209. return new Dimension( x, y );
  210. }
  211. protected void initColors() {
  212. }
  213. public String getToolTipText(MouseEvent e) {
  214. Color color = getColorForLocation(e.getX(), e.getY());
  215. return color.getRed()+", "+ color.getGreen() + ", " + color.getBlue();
  216. }
  217. public Color getColorForLocation( int x, int y ) {
  218. int column;
  219. if ((!this.getComponentOrientation().isLeftToRight()) &&
  220. (this instanceof RecentSwatchPanel)) {
  221. column = numSwatches.width - x / (swatchSize.width + gap.width) - 1;
  222. } else {
  223. column = x / (swatchSize.width + gap.width);
  224. }
  225. int row = y / (swatchSize.height + gap.height);
  226. return getColorForCell(column, row);
  227. }
  228. private Color getColorForCell( int column, int row) {
  229. return colors[ (row * numSwatches.width) + column ]; // (STEVE) - change data orientation here
  230. }
  231. }
  232. class RecentSwatchPanel extends SwatchPanel {
  233. protected void initValues() {
  234. swatchSize = UIManager.getDimension("ColorChooser.swatchesRecentSwatchSize");
  235. numSwatches = new Dimension( 5, 7 );
  236. gap = new Dimension(1, 1);
  237. }
  238. protected void initColors() {
  239. Color defaultRecentColor = UIManager.getColor("ColorChooser.swatchesDefaultRecentColor");
  240. int numColors = numSwatches.width * numSwatches.height;
  241. colors = new Color[numColors];
  242. for (int i = 0; i < numColors ; i++) {
  243. colors[i] = defaultRecentColor;
  244. }
  245. }
  246. public void setMostRecentColor(Color c) {
  247. System.arraycopy( colors, 0, colors, 1, colors.length-1);
  248. colors[0] = c;
  249. repaint();
  250. }
  251. }
  252. class MainSwatchPanel extends SwatchPanel {
  253. protected void initValues() {
  254. swatchSize = UIManager.getDimension("ColorChooser.swatchesSwatchSize");
  255. numSwatches = new Dimension( 31, 9 );
  256. gap = new Dimension(1, 1);
  257. }
  258. protected void initColors() {
  259. int[] rawValues = initRawValues();
  260. int numColors = rawValues.length / 3;
  261. colors = new Color[numColors];
  262. for (int i = 0; i < numColors ; i++) {
  263. colors[i] = new Color( rawValues[(i*3)], rawValues[(i*3)+1], rawValues[(i*3)+2] );
  264. }
  265. }
  266. private int[] initRawValues() {
  267. int[] rawValues = {
  268. 255, 255, 255, // first row.
  269. 204, 255, 255,
  270. 204, 204, 255,
  271. 204, 204, 255,
  272. 204, 204, 255,
  273. 204, 204, 255,
  274. 204, 204, 255,
  275. 204, 204, 255,
  276. 204, 204, 255,
  277. 204, 204, 255,
  278. 204, 204, 255,
  279. 255, 204, 255,
  280. 255, 204, 204,
  281. 255, 204, 204,
  282. 255, 204, 204,
  283. 255, 204, 204,
  284. 255, 204, 204,
  285. 255, 204, 204,
  286. 255, 204, 204,
  287. 255, 204, 204,
  288. 255, 204, 204,
  289. 255, 255, 204,
  290. 204, 255, 204,
  291. 204, 255, 204,
  292. 204, 255, 204,
  293. 204, 255, 204,
  294. 204, 255, 204,
  295. 204, 255, 204,
  296. 204, 255, 204,
  297. 204, 255, 204,
  298. 204, 255, 204,
  299. 204, 204, 204, // second row.
  300. 153, 255, 255,
  301. 153, 204, 255,
  302. 153, 153, 255,
  303. 153, 153, 255,
  304. 153, 153, 255,
  305. 153, 153, 255,
  306. 153, 153, 255,
  307. 153, 153, 255,
  308. 153, 153, 255,
  309. 204, 153, 255,
  310. 255, 153, 255,
  311. 255, 153, 204,
  312. 255, 153, 153,
  313. 255, 153, 153,
  314. 255, 153, 153,
  315. 255, 153, 153,
  316. 255, 153, 153,
  317. 255, 153, 153,
  318. 255, 153, 153,
  319. 255, 204, 153,
  320. 255, 255, 153,
  321. 204, 255, 153,
  322. 153, 255, 153,
  323. 153, 255, 153,
  324. 153, 255, 153,
  325. 153, 255, 153,
  326. 153, 255, 153,
  327. 153, 255, 153,
  328. 153, 255, 153,
  329. 153, 255, 204,
  330. 204, 204, 204, // third row
  331. 102, 255, 255,
  332. 102, 204, 255,
  333. 102, 153, 255,
  334. 102, 102, 255,
  335. 102, 102, 255,
  336. 102, 102, 255,
  337. 102, 102, 255,
  338. 102, 102, 255,
  339. 153, 102, 255,
  340. 204, 102, 255,
  341. 255, 102, 255,
  342. 255, 102, 204,
  343. 255, 102, 153,
  344. 255, 102, 102,
  345. 255, 102, 102,
  346. 255, 102, 102,
  347. 255, 102, 102,
  348. 255, 102, 102,
  349. 255, 153, 102,
  350. 255, 204, 102,
  351. 255, 255, 102,
  352. 204, 255, 102,
  353. 153, 255, 102,
  354. 102, 255, 102,
  355. 102, 255, 102,
  356. 102, 255, 102,
  357. 102, 255, 102,
  358. 102, 255, 102,
  359. 102, 255, 153,
  360. 102, 255, 204,
  361. 153, 153, 153, // fourth row
  362. 51, 255, 255,
  363. 51, 204, 255,
  364. 51, 153, 255,
  365. 51, 102, 255,
  366. 51, 51, 255,
  367. 51, 51, 255,
  368. 51, 51, 255,
  369. 102, 51, 255,
  370. 153, 51, 255,
  371. 204, 51, 255,
  372. 255, 51, 255,
  373. 255, 51, 204,
  374. 255, 51, 153,
  375. 255, 51, 102,
  376. 255, 51, 51,
  377. 255, 51, 51,
  378. 255, 51, 51,
  379. 255, 102, 51,
  380. 255, 153, 51,
  381. 255, 204, 51,
  382. 255, 255, 51,
  383. 204, 255, 51,
  384. 153, 244, 51,
  385. 102, 255, 51,
  386. 51, 255, 51,
  387. 51, 255, 51,
  388. 51, 255, 51,
  389. 51, 255, 102,
  390. 51, 255, 153,
  391. 51, 255, 204,
  392. 153, 153, 153, // Fifth row
  393. 0, 255, 255,
  394. 0, 204, 255,
  395. 0, 153, 255,
  396. 0, 102, 255,
  397. 0, 51, 255,
  398. 0, 0, 255,
  399. 51, 0, 255,
  400. 102, 0, 255,
  401. 153, 0, 255,
  402. 204, 0, 255,
  403. 255, 0, 255,
  404. 255, 0, 204,
  405. 255, 0, 153,
  406. 255, 0, 102,
  407. 255, 0, 51,
  408. 255, 0 , 0,
  409. 255, 51, 0,
  410. 255, 102, 0,
  411. 255, 153, 0,
  412. 255, 204, 0,
  413. 255, 255, 0,
  414. 204, 255, 0,
  415. 153, 255, 0,
  416. 102, 255, 0,
  417. 51, 255, 0,
  418. 0, 255, 0,
  419. 0, 255, 51,
  420. 0, 255, 102,
  421. 0, 255, 153,
  422. 0, 255, 204,
  423. 102, 102, 102, // sixth row
  424. 0, 204, 204,
  425. 0, 204, 204,
  426. 0, 153, 204,
  427. 0, 102, 204,
  428. 0, 51, 204,
  429. 0, 0, 204,
  430. 51, 0, 204,
  431. 102, 0, 204,
  432. 153, 0, 204,
  433. 204, 0, 204,
  434. 204, 0, 204,
  435. 204, 0, 204,
  436. 204, 0, 153,
  437. 204, 0, 102,
  438. 204, 0, 51,
  439. 204, 0, 0,
  440. 204, 51, 0,
  441. 204, 102, 0,
  442. 204, 153, 0,
  443. 204, 204, 0,
  444. 204, 204, 0,
  445. 204, 204, 0,
  446. 153, 204, 0,
  447. 102, 204, 0,
  448. 51, 204, 0,
  449. 0, 204, 0,
  450. 0, 204, 51,
  451. 0, 204, 102,
  452. 0, 204, 153,
  453. 0, 204, 204,
  454. 102, 102, 102, // seventh row
  455. 0, 153, 153,
  456. 0, 153, 153,
  457. 0, 153, 153,
  458. 0, 102, 153,
  459. 0, 51, 153,
  460. 0, 0, 153,
  461. 51, 0, 153,
  462. 102, 0, 153,
  463. 153, 0, 153,
  464. 153, 0, 153,
  465. 153, 0, 153,
  466. 153, 0, 153,
  467. 153, 0, 153,
  468. 153, 0, 102,
  469. 153, 0, 51,
  470. 153, 0, 0,
  471. 153, 51, 0,
  472. 153, 102, 0,
  473. 153, 153, 0,
  474. 153, 153, 0,
  475. 153, 153, 0,
  476. 153, 153, 0,
  477. 153, 153, 0,
  478. 102, 153, 0,
  479. 51, 153, 0,
  480. 0, 153, 0,
  481. 0, 153, 51,
  482. 0, 153, 102,
  483. 0, 153, 153,
  484. 0, 153, 153,
  485. 51, 51, 51, // eigth row
  486. 0, 102, 102,
  487. 0, 102, 102,
  488. 0, 102, 102,
  489. 0, 102, 102,
  490. 0, 51, 102,
  491. 0, 0, 102,
  492. 51, 0, 102,
  493. 102, 0, 102,
  494. 102, 0, 102,
  495. 102, 0, 102,
  496. 102, 0, 102,
  497. 102, 0, 102,
  498. 102, 0, 102,
  499. 102, 0, 102,
  500. 102, 0, 51,
  501. 102, 0, 0,
  502. 102, 51, 0,
  503. 102, 102, 0,
  504. 102, 102, 0,
  505. 102, 102, 0,
  506. 102, 102, 0,
  507. 102, 102, 0,
  508. 102, 102, 0,
  509. 102, 102, 0,
  510. 51, 102, 0,
  511. 0, 102, 0,
  512. 0, 102, 51,
  513. 0, 102, 102,
  514. 0, 102, 102,
  515. 0, 102, 102,
  516. 0, 0, 0, // ninth row
  517. 0, 51, 51,
  518. 0, 51, 51,
  519. 0, 51, 51,
  520. 0, 51, 51,
  521. 0, 51, 51,
  522. 0, 0, 51,
  523. 51, 0, 51,
  524. 51, 0, 51,
  525. 51, 0, 51,
  526. 51, 0, 51,
  527. 51, 0, 51,
  528. 51, 0, 51,
  529. 51, 0, 51,
  530. 51, 0, 51,
  531. 51, 0, 51,
  532. 51, 0, 0,
  533. 51, 51, 0,
  534. 51, 51, 0,
  535. 51, 51, 0,
  536. 51, 51, 0,
  537. 51, 51, 0,
  538. 51, 51, 0,
  539. 51, 51, 0,
  540. 51, 51, 0,
  541. 0, 51, 0,
  542. 0, 51, 51,
  543. 0, 51, 51,
  544. 0, 51, 51,
  545. 0, 51, 51,
  546. 51, 51, 51 };
  547. return rawValues;
  548. }
  549. }