001 /* 002 * $Id: DefaultListRenderer.java 3286 2009-03-10 12:13:43Z kleopatra $ 003 * 004 * Copyright 2006 Sun Microsystems, Inc., 4150 Network Circle, 005 * Santa Clara, California 95054, U.S.A. All rights reserved. 006 * 007 * This library is free software; you can redistribute it and/or 008 * modify it under the terms of the GNU Lesser General Public 009 * License as published by the Free Software Foundation; either 010 * version 2.1 of the License, or (at your option) any later version. 011 * 012 * This library is distributed in the hope that it will be useful, 013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 015 * Lesser General Public License for more details. 016 * 017 * You should have received a copy of the GNU Lesser General Public 018 * License along with this library; if not, write to the Free Software 019 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 020 */ 021 package org.jdesktop.swingx.renderer; 022 023 024 import java.awt.Component; 025 026 import javax.swing.Icon; 027 import javax.swing.JList; 028 import javax.swing.ListCellRenderer; 029 030 031 /** 032 * Adapter to glue SwingX renderer support to core API. It has convenience 033 * constructors to create a LabelProvider, optionally configured with a 034 * StringValue and horizontal alignment. Typically, client code does not 035 * interact with this class except at instantiation time. 036 * <p> 037 * 038 * Note: core DefaultListCellRenderer shows either an icon or the element's 039 * toString representation, depending on whether or not the given value 040 * is of type icon or implementors. This renderer's empty/null provider 041 * constructor takes care of configuring the default provider with a converter 042 * which mimics that behaviour. When instantiating this renderer with 043 * any of the constructors which have converters as parameters, 044 * it's up to the client code to supply the appropriate converter, if needed: 045 * 046 * 047 * <pre><code> 048 * StringValue sv = new StringValue() { 049 * 050 * public String getString(Object value) { 051 * if (value instanceof Icon) { 052 * return ""; 053 * } 054 * return StringValue.TO_STRING.getString(value); 055 * } 056 * 057 * }; 058 * StringValue lv = new MappedValue(sv, IconValue.ICON); 059 * listRenderer = new DefaultListRenderer(lv, alignment); 060 * 061 * </code></pre> 062 * 063 * <p> 064 * 065 * 066 * @author Jeanette Winzenburg 067 * 068 * @see ComponentProvider 069 * @see StringValue 070 * @see IconValue 071 * @see MappedValue 072 * 073 * 074 */ 075 public class DefaultListRenderer extends AbstractRenderer 076 implements ListCellRenderer { 077 078 protected ListCellContext cellContext; 079 080 /** 081 * Instantiates a default list renderer with the default component 082 * provider. 083 * 084 */ 085 public DefaultListRenderer() { 086 this((ComponentProvider) null); 087 } 088 089 /** 090 * Instantiates a ListCellRenderer with the given ComponentProvider. 091 * If the provider is null, creates and uses a default. The default 092 * provider is of type <code>LabelProvider</code><p> 093 * 094 * Note: the default provider is configured with a custom StringValue 095 * which behaves exactly as core DefaultListCellRenderer: depending on 096 * whether or not given value is of type icon or implementors, it shows 097 * either the icon or the element's toString. 098 * 099 * @param componentProvider the provider of the configured component to 100 * use for cell rendering 101 */ 102 public DefaultListRenderer(ComponentProvider componentProvider) { 103 super(componentProvider); 104 this.cellContext = new ListCellContext(); 105 } 106 107 /** 108 * Instantiates a default table renderer with a default component controller 109 * using the given converter.<p> 110 * 111 * PENDING JW: how to guarantee core consistent icon handling? Leave to 112 * client code? 113 * 114 * @param converter the converter to use for mapping the content value to a 115 * String representation. 116 * 117 */ 118 public DefaultListRenderer(StringValue converter) { 119 this(new LabelProvider(converter)); 120 } 121 122 /** 123 * Instantiates a default list renderer with a default component 124 * controller using the given converter and horizontal 125 * alignment. 126 * 127 * PENDING JW: how to guarantee core consistent icon handling? Leave to 128 * client code? 129 * 130 * 131 * @param converter the converter to use for mapping the 132 * content value to a String representation. 133 * @param alignment the horizontal alignment. 134 */ 135 public DefaultListRenderer(StringValue converter, int alignment) { 136 this(new LabelProvider(converter, alignment)); 137 } 138 139 140 /** 141 * Instantiates a default list renderer with default component provider 142 * using both converters. 143 * 144 * @param stringValue the converter to use for the string representation 145 * @param iconValue the converter to use for the icon representation 146 */ 147 public DefaultListRenderer(StringValue stringValue, IconValue iconValue) { 148 this(new MappedValue(stringValue, iconValue)); 149 } 150 151 /** 152 * Instantiates a default list renderer with default component provider 153 * using both converters and the given alignment. 154 * 155 * @param stringValue the converter to use for the string representation 156 * @param iconValue the converter to use for the icon representation 157 * @param alignment the rendering component's horizontal alignment 158 */ 159 public DefaultListRenderer(StringValue stringValue, IconValue iconValue, 160 int alignment) { 161 this(new MappedValue(stringValue, iconValue), alignment); 162 } 163 164 // -------------- implements javax.swing.table.ListCellRenderer 165 /** 166 * 167 * Returns a configured component, appropriate to render the given 168 * list cell. 169 * 170 * @param list the <code>JList</code> to render on 171 * @param value the value to assign to the cell 172 * @param isSelected true if cell is selected 173 * @param cellHasFocus true if cell has focus 174 * @param index the row index (in view coordinates) of the cell to render 175 * @return a component to render the given list cell. 176 */ 177 public Component getListCellRendererComponent(JList list, Object value, 178 int index, boolean isSelected, boolean cellHasFocus) { 179 cellContext.installContext(list, value, index, 0, isSelected, 180 cellHasFocus, true, true); 181 Component comp = componentController.getRendererComponent(cellContext); 182 // fix issue #1040-swingx: memory leak if value not released 183 cellContext.replaceValue(null); 184 return comp; 185 } 186 187 /** 188 * {@inheritDoc} 189 */ 190 @Override 191 protected ComponentProvider createDefaultComponentProvider() { 192 return new LabelProvider(createDefaultStringValue()); 193 } 194 195 /** 196 * Creates and returns the default StringValue for a JList.<p> 197 * This is added to keep consistent with core list rendering which 198 * shows either the Icon (for Icon value types) or the default 199 * to-string for non-icon types. 200 * 201 * @return the StringValue to use by default. 202 */ 203 private StringValue createDefaultStringValue() { 204 StringValue sv = new StringValue() { 205 206 public String getString(Object value) { 207 if (value instanceof Icon) { 208 return ""; 209 } 210 return StringValues.TO_STRING.getString(value); 211 } 212 213 }; 214 return new MappedValue(sv, IconValues.ICON); 215 } 216 217 218 } 219 220