package abbot.tester; import java.awt.*; import javax.swing.*; import abbot.i18n.Strings; import abbot.script.ArgumentParser; /** Provide actions and assertions for a {@link JList} component. The {@link JList} substructure is a "row", and {@link JListLocation} provides different identifiers for a row. <ul> <li>Select an item by index <li>Select an item by value (its string representation) </ul> Note that {@link JList} uses "index" and "value" in its API. For convenience, the <code>JListTester</code> API also provides "row" and "item" as synonyms for "index". @see JListLocation */ // TODO multi-select // Putting "Location" into ComponentTester removes the need for any subclass // to duplicate click, click(mods), click(mods, count), as well as make // specific methods unnecessary. public class JListTester extends JComponentTester { /** Convert the value in the list at the given index into a reasonable string representation, or null if one can not be obtained. */ static String valueToString(JList list, int index) { Object value = list.getModel().getElementAt(index); Component cr = list.getCellRenderer(). getListCellRendererComponent(list, value, index, false, false); String string = null; if (cr instanceof javax.swing.JLabel) { string = ((javax.swing.JLabel)cr).getText(); if (string != null) string = string.trim(); if (!"".equals(string) && !ArgumentParser.isDefaultToString(string)) return string; } string = ArgumentParser.toString(value); return string == ArgumentParser.DEFAULT_TOSTRING ? null : string; } /** JList doesn't provide direct access to its contents, so make up for * that oversight. */ public Object getElementAt(JList list, int index) { return list.getModel().getElementAt(index); } /** Return the size of the given list. */ public int getSize(JList list) { return list.getModel().getSize(); } /** Return an array of strings that represents the list's contents. */ public String[] getContents(JList list) { ListModel model = list.getModel(); String[] values = new String[model.getSize()]; for (int i=0;i < values.length;i++) { values[i] = model.getElementAt(i).toString(); } return values; } /** Select the given index. Equivalent to actionSelectRow(c, new JListLocation(index)). */ public void actionSelectIndex(Component c, int index) { actionSelectRow(c, new JListLocation(index)); } /** Select the first item in the list matching the given String representation of the item.<p> Equivalent to actionSelectRow(c, new JListLocation(item)). */ public void actionSelectItem(Component c, String item) { actionSelectRow(c, new JListLocation(item)); } /** Select the first value in the list matching the given String representation of the value.<p> Equivalent to actionSelectRow(c, new JListLocation(value)). */ public void actionSelectValue(Component c, String value) { actionSelectRow(c, new JListLocation(value)); } /** Select the given row. Does nothing if the index is already * selected. */ public void actionSelectRow(Component c, JListLocation location) { JList list = (JList)c; int index = location.getIndex(list); if (index < 0 || index >= list.getModel().getSize()) { String msg = Strings.get("tester.JList.invalid_index", new Object[] { new Integer(index) }); throw new ActionFailedException(msg); } if (list.getSelectedIndex() != index) { super.actionClick(c, location); } } /** Parse the String representation of a JListLocation into the actual JListLocation object. */ public ComponentLocation parseLocation(String encoded) { return new JListLocation().parse(encoded); } /** Return the value, row, or coordinate location. */ public ComponentLocation getLocation(Component c, Point p) { JList list = (JList)c; int index = list.locationToIndex(p); String value = valueToString(list, index); if (value != null) { return new JListLocation(value); } else if (index != -1) { return new JListLocation(index); } return new JListLocation(p); } }