basictableui.java
来自「linux下建立JAVA虚拟机的源码KAFFE」· Java 代码 · 共 1,330 行 · 第 1/4 页
JAVA
1,330 行
* @param eventIsTab true if TAB was pressed, false if ENTER pressed */ void advanceMultipleSelection (ListSelectionModel firstModel, int firstMin, int firstMax, ListSelectionModel secondModel, int secondMin, int secondMax, boolean reverse, boolean eventIsTab) { // If eventIsTab, all the "firsts" correspond to columns, otherwise, to rows // "seconds" correspond to the opposite int firstLead = firstModel.getLeadSelectionIndex(); int secondLead = secondModel.getLeadSelectionIndex(); int numFirsts = eventIsTab ? table.getModel().getColumnCount() : table.getModel().getRowCount(); int numSeconds = eventIsTab ? table.getModel().getRowCount() : table.getModel().getColumnCount(); // check if we have to wrap the "firsts" around, going to the other side if ((firstLead == firstMax && !reverse) || (reverse && firstLead == firstMin)) { firstModel.addSelectionInterval(reverse ? firstMax : firstMin, reverse ? firstMax : firstMin); // check if we have to wrap the "seconds" if ((secondLead == secondMax && !reverse) || (reverse && secondLead == secondMin)) secondModel.addSelectionInterval(reverse ? secondMax : secondMin, reverse ? secondMax : secondMin); // if we're not wrapping the seconds, we have to find out where we // are within the secondModel and advance to the next cell (or // go back to the previous cell if reverse == true) else { int[] secondsSelected; if (eventIsTab && table.getRowSelectionAllowed() || !eventIsTab && table.getColumnSelectionAllowed()) secondsSelected = eventIsTab ? table.getSelectedRows() : table.getSelectedColumns(); else { // if row selection is not allowed, then the entire column gets // selected when you click on it, so consider ALL rows selected secondsSelected = new int[numSeconds]; for (int i = 0; i < numSeconds; i++) secondsSelected[i] = i; } // and now find the "next" index within the model int secondIndex = reverse ? secondsSelected.length - 1 : 0; if (!reverse) while (secondsSelected[secondIndex] <= secondLead) secondIndex++; else while (secondsSelected[secondIndex] >= secondLead) secondIndex--; // and select it - updating the lead selection index secondModel.addSelectionInterval(secondsSelected[secondIndex], secondsSelected[secondIndex]); } } // We didn't have to wrap the firsts, so just find the "next" first // and select it, we don't have to change "seconds" else { int[] firstsSelected; if (eventIsTab && table.getColumnSelectionAllowed() || !eventIsTab && table.getRowSelectionAllowed()) firstsSelected = eventIsTab ? table.getSelectedColumns() : table.getSelectedRows(); else { // if selection not allowed, consider ALL firsts to be selected firstsSelected = new int[numFirsts]; for (int i = 0; i < numFirsts; i++) firstsSelected[i] = i; } int firstIndex = reverse ? firstsSelected.length - 1 : 0; if (!reverse) while (firstsSelected[firstIndex] <= firstLead) firstIndex++; else while (firstsSelected[firstIndex] >= firstLead) firstIndex--; firstModel.addSelectionInterval(firstsSelected[firstIndex], firstsSelected[firstIndex]); secondModel.addSelectionInterval(secondLead, secondLead); } } /** * A helper method for the key bindings. Used because the actions * for TAB, SHIFT-TAB, ENTER, and SHIFT-ENTER are very similar. * * Selects the next (previous if SHIFT pressed) column (TAB) or row (ENTER) * in the table, changing the current selection. All cells in the table * are eligible, not just the ones that are currently selected. * @param firstModel the ListSelectionModel for columns (TAB) or rows * (ENTER) * @param firstMax the last index in firstModel * @param secondModel the ListSelectionModel for rows (TAB) or columns * (ENTER) * @param secondMax the last index in secondModel * @param reverse true if SHIFT was pressed for the event */ void advanceSingleSelection (ListSelectionModel firstModel, int firstMax, ListSelectionModel secondModel, int secondMax, boolean reverse) { // for TABs, "first" corresponds to columns and "seconds" to rows. // the opposite is true for ENTERs int firstLead = firstModel.getLeadSelectionIndex(); int secondLead = secondModel.getLeadSelectionIndex(); // if we are going backwards subtract 2 because we later add 1 // for a net change of -1 if (reverse && (firstLead == 0)) { // check if we have to wrap around if (secondLead == 0) secondLead += secondMax + 1; secondLead -= 2; } // do we have to wrap the "seconds"? if (reverse && (firstLead == 0) || !reverse && (firstLead == firstMax)) secondModel.setSelectionInterval((secondLead + 1)%(secondMax + 1), (secondLead + 1)%(secondMax + 1)); // if not, just reselect the current lead else secondModel.setSelectionInterval(secondLead, secondLead); // if we are going backwards, subtract 2 because we add 1 later // for net change of -1 if (reverse) { // check for wraparound if (firstLead == 0) firstLead += firstMax + 1; firstLead -= 2; } // select the next "first" firstModel.setSelectionInterval ((firstLead + 1)%(firstMax + 1), (firstLead + 1)%(firstMax + 1)); } } protected void installListeners() { if (focusListener == null) focusListener = createFocusListener(); table.addFocusListener(focusListener); if (keyListener == null) keyListener = createKeyListener(); table.addKeyListener(keyListener); if (mouseInputListener == null) mouseInputListener = createMouseInputListener(); table.addMouseListener(mouseInputListener); table.addMouseMotionListener(mouseInputListener); if (propertyChangeListener == null) propertyChangeListener = new PropertyChangeHandler(); table.addPropertyChangeListener(propertyChangeListener); } protected void uninstallDefaults() { // TODO: this method used to do the following which is not // quite right (at least it breaks apps that run fine with the // JDK): // // table.setFont(null); // table.setGridColor(null); // table.setForeground(null); // table.setBackground(null); // table.setSelectionForeground(null); // table.setSelectionBackground(null); // // This would leave the component in a corrupt state, which is // not acceptable. A possible solution would be to have component // level defaults installed, that get overridden by the UI defaults // and get restored in this method. I am not quite sure about this // though. / Roman Kennke } protected void uninstallKeyboardActions() { // TODO: Implement this properly. } protected void uninstallListeners() { table.removeFocusListener(focusListener); table.removeKeyListener(keyListener); table.removeMouseListener(mouseInputListener); table.removeMouseMotionListener(mouseInputListener); table.removePropertyChangeListener(propertyChangeListener); propertyChangeListener = null; } public void installUI(JComponent comp) { table = (JTable)comp; installDefaults(); installKeyboardActions(); installListeners(); } public void uninstallUI(JComponent c) { uninstallListeners(); uninstallKeyboardActions(); uninstallDefaults(); } /** * Paints a single cell in the table. * * @param g The graphics context to paint in * @param row The row number to paint * @param col The column number to paint * @param bounds The bounds of the cell to paint, assuming a coordinate * system beginning at <code>(0,0)</code> in the upper left corner of the * table * @param rend A cell renderer to paint with */ void paintCell(Graphics g, int row, int col, Rectangle bounds, TableCellRenderer rend) { Component comp = table.prepareRenderer(rend, row, col); rendererPane.paintComponent(g, comp, table, bounds); } /** * Paint the associated table. */ public void paint(Graphics gfx, JComponent ignored) { int ncols = table.getColumnCount(); int nrows = table.getRowCount(); if (nrows == 0 || ncols == 0) return; Rectangle clip = gfx.getClipBounds(); // Determine the range of cells that are within the clip bounds. Point p1 = new Point(clip.x, clip.y); int c0 = table.columnAtPoint(p1); if (c0 == -1) c0 = 0; int r0 = table.rowAtPoint(p1); if (r0 == -1) r0 = 0; Point p2 = new Point(clip.x + clip.width, clip.y + clip.height); int cn = table.columnAtPoint(p2); if (cn == -1) cn = table.getColumnCount() - 1; int rn = table.rowAtPoint(p2); if (rn == -1) rn = table.getRowCount() - 1; TableColumnModel cmodel = table.getColumnModel(); int [] widths = new int[cn+1]; for (int i = c0; i <=cn ; i++) { widths[i] = cmodel.getColumn(i).getWidth(); } Rectangle bounds = table.getCellRect(r0, c0, false); bounds.height = table.getRowHeight()+table.getRowMargin(); // The left boundary of the area being repainted. int left = bounds.x; // The top boundary of the area being repainted. int top = bounds.y; // The bottom boundary of the area being repainted. int bottom; // The cell height. int height = bounds.height; // paint the cell contents Color grid = table.getGridColor(); for (int r = r0; r <= rn; ++r) { for (int c = c0; c <= cn; ++c) { bounds.width = widths[c]; paintCell(gfx, r, c, bounds, table.getCellRenderer(r, c)); bounds.x += widths[c]; } bounds.y += height; bounds.x = left; } bottom = bounds.y; // paint vertical grid lines if (grid != null && table.getShowVerticalLines()) { Color save = gfx.getColor(); gfx.setColor(grid); int x = left; for (int c = c0; c <= cn; ++c) { gfx.drawLine(x, top, x, bottom); x += widths[c]; } gfx.setColor(save); } // paint horizontal grid lines if (grid != null && table.getShowHorizontalLines()) { Color save = gfx.getColor(); gfx.setColor(grid); int y = top; for (int r = r0; r <= rn; ++r) { gfx.drawLine(left, y, p2.x, y); y += height; } gfx.setColor(save); } }}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?