|
網誌存檔
熱門網志
|
|
|
Understanding the Caret and Highlighter Interfaces of Text Components The Caret and Highlighter interfaces are two aspects of text components that control the view of the current text. The Caret interface describes what`s usually referred to as the cursor: the location in the document where you can insert text. The Highlighter interface provides the basis for painting selected text. These two interfaces, their related interfaces, and their implementations are rarely altered. The text components simply use their default implementations with the DefaultCaret and DefaultHighlighter classes. Although you probably won`t alter the caret and highlighter behavior for a text component, you should know that many interrelated classes are working together. For the Highlighter interface, the predefined implementation is called DefaultHighlighter, which extends another implementation called LayeredHighlighter. The Highlighter also manages a collection of Highlighter.Highlight objects to designate highlighted sections. The DefaultHighlighter creates a DefaultHighlighter.HighlightPainter to paint highlighted sections of text. The HighlightPainter is an implementation of the Highlighter.HighlightPainter interface and extends the LayeredHighlighter.LayerPainter class. Each section to be painted is described by a Highlighter.Highlight, where the Highlighter manages the set. The actual HighlightPainter is created by the DefaultCaret implementation. To return to the concrete from the abstract, the Highlighter interface describes how to paint selected text within a text component. public interface Highlighter { // Properties public Highlighter.Highlight[ ] getHighlights() // Other Methods public Object addHighlight( int p0, int p1, Highlighter.HighlightPainter p) throws BadLocationException public void changeHighlight(Object tag, int p0, int p1) throws BadLocationException public void deinstall(JTextComponent component) public void install(JTextComponent component) public void paint(Graphics g) public void removeAllHighlights() public void removeHighlight(Object tag) } If you don`t like the color of the highlighted text, call either the setSelectionColor() or setSelectedTextColor() methods of JTextComponent. The Caret interface describes the current cursor, as well as several selection attributes. Of the Highlighter and Caret interfaces, the latter is the one that you`d actually use, although subclassing it isn`t necessary. public interface Caret { // Properties public int getBlinkRate() public void setBlinkRate(int newValue) public int getDot() public void setDot(int newValue) public Point getMagicCaretPosition() public void setMagicCaretPosition(Point newValue) public int getMark() public boolean isSelectionVisible() public void setSelectionVisible(boolean newValue) public boolean isVisible() public void setVisible(boolean newValue) // Listeners public void addChangeListener(ChangeListener l) public void removeChangeListener(ChangeListener l) // Other Methods public void deinstall(JTextComponent c) public void install(JTextComponent c) public void moveDot(int dot) public void paint(Graphics g) } The blinkRate represents the millisecond delay between the flashes of the caret. The dot property represents the cursor`s current position within the text component. To move the cursor to another position so that some text will be highlighted, call the moveDot(int newPosition) method. This sets the mark property to the old dot position and sets the new dot setting to the new position. Other than the self-explanatory visibility properties, the one remaining property is the magicCaretPosition property. This property deals with moving up and down lines of different lengths. For instance, in the three lines of text that follow this paragraph, imagine that the current cursor position is between the n and g on the first line. If you pressed the down arrow twice, you`d want the cursor to stay at the same horizontal position, instead of moving to the end of the shorter second line. It`s the magicCursorPosition property that retains this information, such that the cursor ends up being between the D and the o in the third line. Without the magic position retained, the cursor would fall in between the p and the word space of the last line. Friz Freleng Mel Blanc What`s up Doc? One useful instance of using the caret is finding the current screen location in response to a keystroke. That way, you can pop up a menu at the current cursor position. This would be similar to the Code Insights option in JBuilder or IntelliSense in Visual Studio, in which the tool helps you complete method calls by popping up a menu of methods to choose. Given the current dot location in the model, map it to the position in the view with the public Rectangle modelToView(int position) method of JTextComponent (which can throw a BadLocationException). Then, use the top-left corner of the Rectangle returned as the location to pop up the menu. The following program shows a JPopupMenu at the location where the period (".") key is pressed in the text field. import javax.swing.*; import javax.swing.text.*; import javax.swing.plaf.*; import java.awt.*; import java.awt.event.*; public class PopupSample { public static void main(String args[]) { Runnable runner = new Runnable() { public void run() { JFrame frame = new JFrame("Popup Example"); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); final JPopupMenu popup = new JPopupMenu(); JMenuItem menuItem1 = new JMenuItem("Option 1"); popup.add(menuItem1); JMenuItem menuItem2 = new JMenuItem("Option 2"); popup.add(menuItem2); final JTextField textField = new JTextField(); frame.add(textField, BorderLayout.NORTH); ActionListener actionListener = new ActionListener() { public void actionPerformed(ActionEvent actionEvent) { try { int dotPosition = textField.getCaretPosition(); Rectangle popupLocation = textField.modelToView(dotPosition); popup.show(textField, popupLocation.x, popupLocation.y); } catch (BadLocationException badLocationException) { System.err.println("Oops"); } } }; KeyStroke keystroke = KeyStroke.getKeyStroke(KeyEvent.VK_PERIOD, 0, false); textField.registerKeyboardAction(actionListener, keystroke, JComponent.WHEN_FOCUSED); frame.setSize(250, 150); frame.setVisible(true); } }; EventQueue.invokeLater(runner); } } When you run the code, it should look something like |
-------------------------------------------------
| 上一篇:框架—Framework | 下一篇:Struts 上傳多文件 |

