001    /*
002     * Created on Dec 25, 2009
003     *
004     * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
005     * in compliance with the License. You may obtain a copy of the License at
006     *
007     * http://www.apache.org/licenses/LICENSE-2.0
008     *
009     * Unless required by applicable law or agreed to in writing, software distributed under the License
010     * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
011     * or implied. See the License for the specific language governing permissions and limitations under
012     * the License.
013     *
014     * Copyright @2009-2010 the original author or authors.
015     */
016    package org.fest.swing.data;
017    
018    import static java.lang.String.valueOf;
019    import static org.fest.swing.edt.GuiActionRunner.execute;
020    import static org.fest.swing.exception.ActionFailedException.actionFailure;
021    import static org.fest.util.Strings.concat;
022    
023    import javax.swing.JTable;
024    
025    import org.fest.swing.annotation.RunsInEDT;
026    import org.fest.swing.cell.JTableCellReader;
027    import org.fest.swing.edt.GuiQuery;
028    import org.fest.swing.exception.ActionFailedException;
029    
030    /**
031     * Understands lookup of a cell in the first selected row of a <code>{@link JTable}</code>.
032     * <p>
033     * Example:
034     * <pre>
035     * // import static org.fest.swing.data.TableCellInSelectedRow.row;
036     * <code>{@link TableCell}</code> cell = dialog.table("records").cell({@link TableCellInSelectedRow#selectedRow() selectedRow}().column(2));
037     * </pre>
038     * </p>
039     *
040     * @author Alex Ruiz
041     *
042     */
043    public class TableCellInSelectedRow implements TableCellFinder {
044    
045      /**
046       * Starting point for the creation of a <code>{@link TableCellInSelectedRow}</code>.
047       * <p>
048       * Example:
049       * <pre>
050       * // import static org.fest.swing.data.TableCellInSelectedRow.row;
051       * TableCellInSelectedRow cell = selectedRow().column(2);
052       * </pre>
053       * </p>
054       * @return the created builder.
055       */
056      public static TableCellBuilder selectedRow() { return new TableCellBuilder(); }
057    
058      /**
059       * Understands creation of <code>{@link TableCellInSelectedRow}</code>s.
060       *
061       * @author Alex Ruiz
062       */
063      public static class TableCellBuilder {
064    
065        /**
066         * Creates a new table cell finder.
067         * @param column the column index of the cell to find.
068         * @return the created finder.
069         */
070        public TableCellInSelectedRow column(int column) {
071          return new TableCellInSelectedRow(column);
072        }
073      }
074    
075      private final int column;
076    
077      protected TableCellInSelectedRow(int column) {
078        this.column = column;
079      }
080    
081      /**
082       * Finds a cell in the given <code>{@link JTable}</code> that belongs to the first selected row and has a matching
083       * column index.
084       * @param table the target <code>JTable</code>.
085       * @param cellReader knows how to read the contents of a cell in a <code>JTable</code>.
086       * @return the cell found, if any.
087       * @throws ActionFailedException if a matching cell could not be found.
088       */
089      public TableCell findCell(JTable table, JTableCellReader cellReader) {
090        int selectedRow = selectedRowOf(table);
091        if (selectedRow == -1) throw actionFailure("The given JTable does not have any selection");
092        return new TableCell(selectedRow, column);
093      }
094    
095      @RunsInEDT
096      private static int selectedRowOf(final JTable table) {
097        return execute(new GuiQuery<Integer>() {
098          protected Integer executeInEDT() {
099            return table.getSelectedRow();
100          }
101        });
102      }
103    
104      @Override public String toString() {
105        return concat(getClass().getName(), "[column=", valueOf(column), "]");
106      }
107    }