swingutilities2.java
来自「JAVA的一些源码 JAVA2 STANDARD EDITION DEVELO」· Java 代码 · 共 1,148 行 · 第 1/3 页
JAVA
1,148 行
* @param x X coordinate to draw the text at * @param y Y coordinate to draw the text at */ public static void drawString(JComponent c, Graphics g, String text, int x, int y) { // c may be null // All non-editable widgets that draw strings call into this // methods. By non-editable that means widgets like JLabel, JButton // but NOT JTextComponents. if ( text == null || text.length() <= 0 ) { //no need to paint empty strings return; } if (isPrinting(g)) { Graphics2D g2d = getGraphics2D(g); if (g2d != null) { TextLayout layout = new TextLayout(text, g2d.getFont(), DEFAULT_FRC); /* Use alternate print color if specified */ Color col = g2d.getColor(); if (col instanceof PrintColorUIResource) { g2d.setColor(((PrintColorUIResource)col).getPrintColor()); } layout.draw(g2d, x, y); g2d.setColor(col); return; } } // If we get here we're not printing if (drawTextAntialiased(c) && (g instanceof Graphics2D)) { Graphics2D g2 = (Graphics2D)g; Object oldAAValue = g2.getRenderingHint( RenderingHints.KEY_TEXT_ANTIALIASING); g2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON); g.drawString(text, x, y); g2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, oldAAValue); } else { g.drawString(text, x, y); } } /** * Draws the string at the specified location underlining the specified * character. * * @param c JComponent that will display the string, may be null * @param g Graphics to draw the text to * @param text String to display * @param underlinedIndex Index of a character in the string to underline * @param x X coordinate to draw the text at * @param y Y coordinate to draw the text at */ public static void drawStringUnderlineCharAt(JComponent c,Graphics g, String text, int underlinedIndex, int x,int y) { SwingUtilities2.drawString(c, g, text, x, y); if (underlinedIndex >= 0 && underlinedIndex < text.length() ) { // PENDING: this needs to change. FontMetrics fm = g.getFontMetrics(); int underlineRectX = x + SwingUtilities2.stringWidth(c, fm, text.substring(0,underlinedIndex)); int underlineRectY = y; int underlineRectWidth = fm.charWidth(text. charAt(underlinedIndex)); int underlineRectHeight = 1; g.fillRect(underlineRectX, underlineRectY + 1, underlineRectWidth, underlineRectHeight); } } /** * A variation of locationToIndex() which only returns an index if the * Point is within the actual bounds of a list item (not just in the cell) * and if the JList has the "List.isFileList" client property set. * Otherwise, this method returns -1. * This is used to make WindowsL&F JFileChooser act like native dialogs. */ public static int loc2IndexFileList(JList list, Point point) { int index = list.locationToIndex(point); if (index != -1) { Object bySize = list.getClientProperty("List.isFileList"); if (bySize instanceof Boolean && ((Boolean)bySize).booleanValue() && !pointIsInActualBounds(list, index, point)) { index = -1; } } return index; } /** * Returns true if the given point is within the actual bounds of the * JList item at index (not just inside the cell). */ private static boolean pointIsInActualBounds(JList list, int index, Point point) { ListCellRenderer renderer = list.getCellRenderer(); ListModel dataModel = list.getModel(); Object value = dataModel.getElementAt(index); Component item = renderer.getListCellRendererComponent(list, value, index, false, false); Dimension itemSize = item.getPreferredSize(); Rectangle cellBounds = list.getCellBounds(index, index); if (!item.getComponentOrientation().isLeftToRight()) { cellBounds.x += (cellBounds.width - itemSize.width); } cellBounds.width = itemSize.width; cellBounds.height = itemSize.height; return cellBounds.contains(point); } /** * Returns true if the given point is outside the preferredSize of the * item at the given row of the table. (Column must be 0). * Does not check the "Table.isFileList" property. That should be checked * before calling this method. * This is used to make WindowsL&F JFileChooser act like native dialogs. */ public static boolean pointOutsidePrefSize(JTable table, int row, int column, Point p) { if (table.convertColumnIndexToModel(column) != 0 || row == -1) { return true; } TableCellRenderer tcr = table.getCellRenderer(row, column); Object value = table.getValueAt(row, column); Component cell = tcr.getTableCellRendererComponent(table, value, false, false, row, column); Dimension itemSize = cell.getPreferredSize(); Rectangle cellBounds = table.getCellRect(row, column, false); cellBounds.width = itemSize.width; cellBounds.height = itemSize.height; // See if coords are inside // ASSUME: mouse x,y will never be < cell's x,y assert (p.x >= cellBounds.x && p.y >= cellBounds.y); if (p.x > cellBounds.x + cellBounds.width || p.y > cellBounds.y + cellBounds.height) { return true; } return false; } /** * Ignore mouse events if the component is null, not enabled, or the event * is not associated with the left mouse button. */ public static boolean shouldIgnore(MouseEvent me, JComponent c) { return c == null || !c.isEnabled() || !SwingUtilities.isLeftMouseButton(me); } /** * Request focus on the given component if it doesn't already have it * and <code>isRequestFocusEnabled()</code> returns true. */ public static void adjustFocus(JComponent c) { if (!c.hasFocus() && c.isRequestFocusEnabled()) { c.requestFocus(); } } /** * The following draw functions have the same semantic as the * Graphics methods with the same names. * * this is used for printing */ public static int drawChars(JComponent c, Graphics g, char[] data, int offset, int length, int x, int y) { if ( length <= 0 ) { //no need to paint empty strings return x; } int nextX = x + getFontMetrics(c, g).charsWidth(data, offset, length); if (isPrinting(g)) { Graphics2D g2d = getGraphics2D(g); if (g2d != null) { FontRenderContext deviceFontRenderContext = g2d. getFontRenderContext(); FontRenderContext frc = getFRC(c, null); if (frc.isAntiAliased() || frc.usesFractionalMetrics()) { frc = new FontRenderContext(frc.getTransform(), false, false); } if (frc != null && ! isFontRenderContextCompatible(deviceFontRenderContext, frc)) { TextLayout layout = new TextLayout(new String(data,offset,length), g2d.getFont(), frc); /* Use alternate print color if specified */ Color col = g2d.getColor(); if (col instanceof PrintColorUIResource) { g2d.setColor(((PrintColorUIResource)col).getPrintColor()); } layout.draw(g2d,x,y); g2d.setColor(col); return nextX; } } } // Assume we're not printing if we get here. if (drawTextAntialiased(c) && (g instanceof Graphics2D)) { Graphics2D g2 = (Graphics2D)g; Object oldAAValue = g2.getRenderingHint( RenderingHints.KEY_TEXT_ANTIALIASING); g2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON); g.drawChars(data, offset, length, x, y); g2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, oldAAValue); } else { g.drawChars(data, offset, length, x, y); } return nextX; } /* * see documentation for drawChars * returns the advance */ public static float drawString(JComponent c, Graphics g, AttributedCharacterIterator iterator, int x, int y) { float retVal; boolean isPrinting = isPrinting(g); Color col = g.getColor(); if (isPrinting) { /* Use alternate print color if specified */ if (col instanceof PrintColorUIResource) { g.setColor(((PrintColorUIResource)col).getPrintColor()); } } Graphics2D g2d = getGraphics2D(g); if (g2d == null) { g.drawString(iterator,x,y); //for the cases where advance //matters it should not happen retVal = x; } else { FontRenderContext frc; if (isPrinting) { frc = getFRC(c, null); if (frc.isAntiAliased() || frc.usesFractionalMetrics()) { frc = new FontRenderContext(frc.getTransform(), false, false); } } else if (drawTextAntialiased(c)) { frc = AA_FRC; } else { frc = g2d.getFontRenderContext(); } TextLayout layout = new TextLayout(iterator, frc); layout.draw(g2d, x, y); retVal = layout.getAdvance(); } if (isPrinting) { g.setColor(col); } return retVal; } /* * Checks if two given FontRenderContexts are compatible. * Compatible means no special handling needed for text painting */ public static boolean isFontRenderContextCompatible(FontRenderContext frc1, FontRenderContext frc2) { return (frc1 != null) ? frc1.equals(frc2) : frc2 == null; } /* * Tries it best to get Graphics2D out of the given Graphics * returns null if can not derive it. */ public static Graphics2D getGraphics2D(Graphics g) { if (g instanceof Graphics2D) { return (Graphics2D) g; } else if (g instanceof ProxyPrintGraphics) { return (Graphics2D)(((ProxyPrintGraphics)g).getGraphics()); } else { return null; } } /* * Returns FontRendedrContext associated with JComponent * see JComponent.getFontMetrics */ public static FontRenderContext getFontRenderContext(Component c) { if (c == null) { return DEFAULT_FRC; } else { return getFRC(null, c.getFontMetrics(c.getFont())); } } /* * returns true if the Graphics is print Graphics * false otherwise */ static boolean isPrinting(Graphics g) { return (g instanceof PrinterGraphics || g instanceof PrintGraphics); } /** * Determines whether the SelectedTextColor should be used for painting text * foreground for the specified highlight. * * Returns true only if the highlight painter for the specified highlight * is the swing painter (whether inner class of javax.swing.text.DefaultHighlighter * or com.sun.java.swing.plaf.windows.WindowsTextUI) and its background color * is null or equals to the selection color of the text component. * * This is a hack for fixing both bugs 4761990 and 5003294 */ public static boolean useSelectedTextColor(Highlighter.Highlight h, JTextComponent c) { Highlighter.HighlightPainter painter = h.getPainter(); String painterClass = painter.getClass().getName(); if (painterClass.indexOf("javax.swing.text.DefaultHighlighter") != 0 && painterClass.indexOf("com.sun.java.swing.plaf.windows.WindowsTextUI") != 0) { return false; } try { DefaultHighlighter.DefaultHighlightPainter defPainter = (DefaultHighlighter.DefaultHighlightPainter) painter; if (defPainter.getColor() != null && !defPainter.getColor().equals(c.getSelectionColor())) { return false; } } catch (ClassCastException e) { return false; } return true; } /** * LSBCacheEntry is used to cache the left side bearing (lsb) for * a particular <code>Font</code> and <code>FontRenderContext</code>. * This only caches characters that fall in the range * <code>MIN_CHAR_INDEX</code> to <code>MAX_CHAR_INDEX</code>. */ private static class LSBCacheEntry { // Used to indicate a particular entry in lsb has not been set. private static final byte UNSET = Byte.MAX_VALUE; // Used in creating a GlyphVector to get the lsb private static final char[] oneChar = new char[1]; private byte[] lsbCache; private Font font; private FontRenderContext frc; public LSBCacheEntry(FontRenderContext frc, Font font) { lsbCache = new byte[MAX_CHAR_INDEX - MIN_CHAR_INDEX]; reset(frc, font); } public void reset(FontRenderContext frc, Font font) { this.font = font; this.frc = frc;
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?