I was looking at the Java Platform source code, and I became very confused very quickly. Not because I didn't understand the code (okay, there were parts I didn't understand), but because I didn't see anything different about lists than any other component. With a null layout manager, almost all components but lists will manually position just fine, but I saw no evidence to make lists the exception. If you dare, here is the class List for your analysis:
[tt][ignore]
package java.awt;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.FocusListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.awt.peer.ListPeer;
import java.io.IOException;
import java.i

bjectInputStream;
import java.i

bjectOutputStream;
import javax.accessibility.Accessible;
import javax.accessibility.AccessibleContext;
import javax.accessibility.AccessibleRole;
import javax.accessibility.AccessibleSelection;
import javax.accessibility.AccessibleState;
import javax.accessibility.AccessibleStateSet;
// Referenced classes of package java.awt:
// Component, ItemSelectable, HeadlessException, GraphicsEnvironment,
// Toolkit, AWTEventMulticaster, AWTEvent, Dimension,
// Point, Color, Cursor, Font,
// FontMetrics, Rectangle
public class List extends Component
implements ItemSelectable, Accessible
{
java.util.Vector items;
int rows;
boolean multipleMode;
int selected[];
int visibleIndex;
transient ActionListener actionListener;
transient ItemListener itemListener;
private static final String base = "list";
private static int nameCounter = 0;
private static final long serialVersionUID = 0xd224b95e612d798bL;
static final int DEFAULT_VISIBLE_ROWS = 4;
private int listSerializedDataVersion;
protected class AccessibleAWTList extends Component.AccessibleAWTComponent
implements AccessibleSelection, ItemListener, ActionListener
{
protected class AccessibleAWTListChild extends Component.AccessibleAWTComponent
implements Accessible
{
public AccessibleContext getAccessibleContext()
{
return this;
}
public AccessibleRole getAccessibleRole()
{
return AccessibleRole.LIST_ITEM;
}
public AccessibleStateSet getAccessibleStateSet()
{
AccessibleStateSet accessiblestateset = super.getAccessibleStateSet();
if(parent.isIndexSelected(indexInParent))
accessiblestateset.add(AccessibleState.SELECTED);
return accessiblestateset;
}
public java.util.Locale getLocale()
{
return parent.getLocale();
}
public int getAccessibleIndexInParent()
{
return indexInParent;
}
public int getAccessibleChildrenCount()
{
return 0;
}
public Accessible getAccessibleChild(int i)
{
return null;
}
public Color getBackground()
{
return parent.getBackground();
}
public void setBackground(Color color)
{
parent.setBackground(color);
}
public Color getForeground()
{
return parent.getForeground();
}
public void setForeground(Color color)
{
parent.setForeground(color);
}
public Cursor getCursor()
{
return parent.getCursor();
}
public void setCursor(Cursor cursor)
{
parent.setCursor(cursor);
}
public Font getFont()
{
return parent.getFont();
}
public void setFont(Font font)
{
parent.setFont(font);
}
public FontMetrics getFontMetrics(Font font)
{
return parent.getFontMetrics(font);
}
public boolean isEnabled()
{
return parent.isEnabled();
}
public void setEnabled(boolean flag)
{
parent.setEnabled(flag);
}
public boolean isVisible()
{
return false;
}
public void setVisible(boolean flag)
{
parent.setVisible(flag);
}
public boolean isShowing()
{
return false;
}
public boolean contains(Point point)
{
return false;
}
public Point getLocationOnScreen()
{
return null;
}
public Point getLocation()
{
return null;
}
public void setLocation(Point point)
{
}
public Rectangle getBounds()
{
return null;
}
public void setBounds(Rectangle rectangle)
{
}
public Dimension getSize()
{
return null;
}
public void setSize(Dimension dimension)
{
}
public Accessible getAccessibleAt(Point point)
{
return null;
}
public boolean isFocusTraversable()
{
return false;
}
public void requestFocus()
{
}
public void addFocusListener(FocusListener focuslistener)
{
}
public void removeFocusListener(FocusListener focuslistener)
{
}
private List parent;
private int indexInParent;
public AccessibleAWTListChild(int i)
{
parent = List.this;
setAccessibleParent(List.this);
indexInParent = i;
}
}
public void actionPerformed(ActionEvent actionevent)
{
}
public void itemStateChanged(ItemEvent itemevent)
{
}
public AccessibleStateSet getAccessibleStateSet()
{
AccessibleStateSet accessiblestateset = super.getAccessibleStateSet();
if(isMultipleMode())
accessiblestateset.add(AccessibleState.MULTISELECTABLE);
return accessiblestateset;
}
public AccessibleRole getAccessibleRole()
{
return AccessibleRole.LIST;
}
public Accessible getAccessibleAt(Point point)
{
return null;
}
public int getAccessibleChildrenCount()
{
return getItemCount();
}
public Accessible getAccessibleChild(int i)
{
label0:
{
Accessible accessible;
synchronized(List.this)
{
if(i < getItemCount())
break label0;
accessible = null;
}
return accessible;
}
AccessibleAWTListChild accessibleawtlistchild = new AccessibleAWTListChild(i);
list;
JVM INSTR monitorexit ;
return accessibleawtlistchild;
exception;
throw exception;
}
public AccessibleSelection getAccessibleSelection()
{
return this;
}
public int getAccessibleSelectionCount()
{
return getSelectedIndexes().length;
}
public Accessible getAccessibleSelection(int i)
{
label0:
{
Accessible accessible;
synchronized(List.this)
{
int j = getAccessibleSelectionCount();
if(i > 0 && i < j)
break label0;
accessible = null;
}
return accessible;
}
Accessible accessible1 = getAccessibleChild(getSelectedIndexes()
);
list;
JVM INSTR monitorexit ;
return accessible1;
exception;
throw exception;
}
public boolean isAccessibleChildSelected(int i)
{
return isIndexSelected(i);
}
public void addAccessibleSelection(int i)
{
select(i);
}
public void removeAccessibleSelection(int i)
{
deselect(i);
}
public void clearAccessibleSelection()
{
int ai[];
label0:
{
synchronized(List.this)
{
ai = getSelectedIndexes();
if(ai != null)
break label0;
}
return;
}
for(int i = ai.length; i >= 0; i--)
deselect(ai);
list;
JVM INSTR monitorexit ;
goto _L1
exception;
throw exception;
_L1:
}
public void selectAllAccessibleSelection()
{
synchronized(List.this)
{
for(int i = getItemCount() - 1; i >= 0; i--)
select(i);
}
}
public AccessibleAWTList()
{
addActionListener(this);
addItemListener(this);
}
}
public List()
throws HeadlessException
{
this(0, false);
}
public List(int i)
throws HeadlessException
{
this(i, false);
}
public List(int i, boolean flag)
throws HeadlessException
{
items = new java.util.Vector();
rows = 0;
multipleMode = false;
selected = new int[0];
visibleIndex = -1;
listSerializedDataVersion = 1;
GraphicsEnvironment.checkHeadless();
rows = i == 0 ? 4 : i;
multipleMode = flag;
}
String constructComponentName()
{
String s;
synchronized(getClass())
{
s = "list" + nameCounter++;
}
return s;
}
public void addNotify()
{
synchronized(getTreeLock())
{
if(peer == null)
peer = getToolkit().createList(this);
super.addNotify();
visibleIndex = -1;
}
}
public void removeNotify()
{
synchronized(getTreeLock())
{
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
selected = listpeer.getSelectedIndexes();
super.removeNotify();
}
}
public int getItemCount()
{
return countItems();
}
public int countItems()
{
return items.size();
}
public String getItem(int i)
{
return getItemImpl(i);
}
final String getItemImpl(int i)
{
return (String)items.elementAt(i);
}
public synchronized String[] getItems()
{
String as[] = new String[items.size()];
items.copyInto(as);
return as;
}
public void add(String s)
{
addItem(s);
}
public void addItem(String s)
{
addItem(s, -1);
}
public void add(String s, int i)
{
addItem(s, i);
}
public synchronized void addItem(String s, int i)
{
if(i < -1 || i >= items.size())
i = -1;
if(s == null)
s = "";
if(i == -1)
items.addElement(s);
else
items.insertElementAt(s, i);
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
listpeer.addItem(s, i);
}
public synchronized void replaceItem(String s, int i)
{
remove(i);
add(s, i);
}
public void removeAll()
{
clear();
}
public synchronized void clear()
{
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
listpeer.clear();
items = new java.util.Vector();
selected = new int[0];
}
public synchronized void remove(String s)
{
int i = items.indexOf(s);
if(i < 0)
{
throw new IllegalArgumentException("item " + s + " not found in list"
;
} else
{
remove(i);
return;
}
}
public void remove(int i)
{
delItem(i);
}
public void delItem(int i)
{
delItems(i, i);
}
public synchronized int getSelectedIndex()
{
int ai[] = getSelectedIndexes();
return ai.length != 1 ? -1 : ai[0];
}
public synchronized int[] getSelectedIndexes()
{
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
selected = listpeer.getSelectedIndexes();
return selected;
}
public synchronized String getSelectedItem()
{
int i = getSelectedIndex();
return i >= 0 ? getItem(i) : null;
}
public synchronized String[] getSelectedItems()
{
int ai[] = getSelectedIndexes();
String as[] = new String[ai.length];
for(int i = 0; i < ai.length; i++)
as = getItem(ai);
return as;
}
public Object[] getSelectedObjects()
{
return getSelectedItems();
}
public void select(int i)
{
ListPeer listpeer;
do
{
listpeer = (ListPeer)peer;
if(listpeer != null)
{
listpeer.select(i);
return;
}
synchronized(this)
{
boolean flag = false;
for(int j = 0; j < selected.length; j++)
{
if(selected[j] != i)
continue;
flag = true;
break;
}
if(!flag)
if(!multipleMode)
{
selected = new int[1];
selected[0] = i;
} else
{
int ai[] = new int[selected.length + 1];
System.arraycopy(selected, 0, ai, 0, selected.length);
ai[selected.length] = i;
selected = ai;
}
}
} while(listpeer != peer);
}
public synchronized void deselect(int i)
{
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
listpeer.deselect(i);
for(int j = 0; j < selected.length; j++)
if(selected[j] == i)
{
int ai[] = new int[selected.length - 1];
System.arraycopy(selected, 0, ai, 0, j);
System.arraycopy(selected, j + 1, ai, j, selected.length - (j + 1));
selected = ai;
return;
}
}
public boolean isIndexSelected(int i)
{
return isSelected(i);
}
public boolean isSelected(int i)
{
int ai[] = getSelectedIndexes();
for(int j = 0; j < ai.length; j++)
if(ai[j] == i)
return true;
return false;
}
public int getRows()
{
return rows;
}
public boolean isMultipleMode()
{
return allowsMultipleSelections();
}
public boolean allowsMultipleSelections()
{
return multipleMode;
}
public void setMultipleMode(boolean flag)
{
setMultipleSelections(flag);
}
public synchronized void setMultipleSelections(boolean flag)
{
if(flag != multipleMode)
{
multipleMode = flag;
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
listpeer.setMultipleSelections(flag);
}
}
public int getVisibleIndex()
{
return visibleIndex;
}
public synchronized void makeVisible(int i)
{
visibleIndex = i;
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
listpeer.makeVisible(i);
}
public Dimension getPreferredSize(int i)
{
return preferredSize(i);
}
public Dimension preferredSize(int i)
{
Dimension dimension;
synchronized(getTreeLock())
{
ListPeer listpeer = (ListPeer)peer;
dimension = listpeer == null ? super.preferredSize() : listpeer.preferredSize(i);
}
return dimension;
}
public Dimension getPreferredSize()
{
return preferredSize();
}
public Dimension preferredSize()
{
Dimension dimension;
synchronized(getTreeLock())
{
dimension = rows <= 0 ? super.preferredSize() : preferredSize(rows);
}
return dimension;
}
public Dimension getMinimumSize(int i)
{
return minimumSize(i);
}
public Dimension minimumSize(int i)
{
Dimension dimension;
synchronized(getTreeLock())
{
ListPeer listpeer = (ListPeer)peer;
dimension = listpeer == null ? super.minimumSize() : listpeer.minimumSize(i);
}
return dimension;
}
public Dimension getMinimumSize()
{
return minimumSize();
}
public Dimension minimumSize()
{
Dimension dimension;
synchronized(getTreeLock())
{
dimension = rows <= 0 ? super.minimumSize() : minimumSize(rows);
}
return dimension;
}
public synchronized void addItemListener(ItemListener itemlistener)
{
if(itemlistener == null)
{
return;
} else
{
itemListener = AWTEventMulticaster.add(itemListener, itemlistener);
newEventsOnly = true;
return;
}
}
public synchronized void removeItemListener(ItemListener itemlistener)
{
if(itemlistener == null)
{
return;
} else
{
itemListener = AWTEventMulticaster.remove(itemListener, itemlistener);
return;
}
}
public synchronized ItemListener[] getItemListeners()
{
return (ItemListener[])getListeners(java.awt.event.ItemListener.class);
}
public synchronized void addActionListener(ActionListener actionlistener)
{
if(actionlistener == null)
{
return;
} else
{
actionListener = AWTEventMulticaster.add(actionListener, actionlistener);
newEventsOnly = true;
return;
}
}
public synchronized void removeActionListener(ActionListener actionlistener)
{
if(actionlistener == null)
{
return;
} else
{
actionListener = AWTEventMulticaster.remove(actionListener, actionlistener);
return;
}
}
public synchronized ActionListener[] getActionListeners()
{
return (ActionListener[])getListeners(java.awt.event.ActionListener.class);
}
public java.util.EventListener[] getListeners(Class class1)
{
Object obj = null;
if(class1 == (java.awt.event.ActionListener.class))
obj = actionListener;
else
if(class1 == (java.awt.event.ItemListener.class))
obj = itemListener;
else
return super.getListeners(class1);
return AWTEventMulticaster.getListeners(((java.util.EventListener) (obj)), class1);
}
boolean eventEnabled(AWTEvent awtevent)
{
switch(awtevent.id)
{
case 1001: // Event.ACTION_EVENT
return (eventMask & 128L) != 0L || actionListener != null;
case 701: // Event.LIST_SELECT
return (eventMask & 512L) != 0L || itemListener != null;
}
return super.eventEnabled(awtevent);
}
protected void processEvent(AWTEvent awtevent)
{
if(awtevent instanceof ItemEvent)
{
processItemEvent((ItemEvent)awtevent);
return;
}
if(awtevent instanceof ActionEvent)
{
processActionEvent((ActionEvent)awtevent);
return;
} else
{
super.processEvent(awtevent);
return;
}
}
protected void processItemEvent(ItemEvent itemevent)
{
if(itemListener != null)
itemListener.itemStateChanged(itemevent);
}
protected void processActionEvent(ActionEvent actionevent)
{
if(actionListener != null)
actionListener.actionPerformed(actionevent);
}
protected String paramString()
{
return super.paramString() + ",selected=" + getSelectedItem();
}
public synchronized void delItems(int i, int j)
{
for(int k = j; k >= i; k--)
items.removeElementAt(k);
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
listpeer.delItems(i, j);
}
private void writeObject(ObjectOutputStream objectoutputstream)
throws IOException
{
synchronized(this)
{
ListPeer listpeer = (ListPeer)peer;
if(listpeer != null)
selected = listpeer.getSelectedIndexes();
}
objectoutputstream.defaultWriteObject();
AWTEventMulticaster.save(objectoutputstream, "itemL", itemListener);
AWTEventMulticaster.save(objectoutputstream, "actionL", actionListener);
objectoutputstream.writeObject(null);
}
private void readObject(ObjectInputStream objectinputstream)
throws ClassNotFoundException, IOException, HeadlessException
{
GraphicsEnvironment.checkHeadless();
objectinputstream.defaultReadObject();
Object obj;
while(null != (obj = objectinputstream.readObject()))
{
String s = ((String)obj).intern();
if("itemL" == s)
addItemListener((ItemListener)objectinputstream.readObject());
else
if("actionL" == s)
addActionListener((ActionListener)objectinputstream.readObject());
else
objectinputstream.readObject();
}
}
public AccessibleContext getAccessibleContext()
{
if(accessibleContext == null)
accessibleContext = new AccessibleAWTList();
return accessibleContext;
}
}
[/ignore][/tt]
Indeed. Anyway, thanks a lot!
***
Dammit Jim, I'm a programmer, not a doctor.