//---------------------------------------------------------------------------- // COMPONENT NAME: LPEX Editor // // © Copyright IBM Corporation 2006, 2007 // All Rights Reserved. // // DESCRIPTION: // MatchesCommand - sample user-defined command (matches) //---------------------------------------------------------------------------- package com.ibm.lpex.samples; import java.util.HashSet; import java.util.Iterator; import com.ibm.lpex.core.LpexCommand; import com.ibm.lpex.core.LpexDocumentLocation; import com.ibm.lpex.core.LpexView; /** * Sample command <b>matches</b> - highlight find-text matches in the document. * This command extends {@link FindsCommand} to determine, and also highlight, the * occurrences in the document of either <b>findText.findText</b> or the * specified text string. It is a "findText all" which highlights the results * rather than filtering the view. * * <p>Here is the MatchesCommand <a href="doc-files/MatchesCommand.java.html">source * code</a>.</p> * * <p>To run this sample: * <ul> * <li>Define this user command via an editor preference page, where available, * or from the editor command line: * <pre>set commandClass.matches com.ibm.lpex.samples.MatchesCommand</pre></li> * <li>Run it from the editor command line: * <pre>matches [<i>text</i>]</pre></li> * </ul></p> * * When called with <code>?</code> as a parameter, the command displays its syntax * on the message line. It also clears any existing matches. * * @see com.ibm.lpex.samples All the samples */ public class MatchesCommand extends FindsCommand { // choose an unlikely style character for the match marks // (TODO create parameter to return an unassigned styleAttributes character!?) private static final char _matchStyleChar = '`'; // use a yellow background to highlight the matches private static final String _matchStyle = "-1 -1 -1 255 255 0"; // set of match marks private HashSet<String> _marks = new HashSet<String>(); // "findText" command stuff private int _foundTextLength; private LpexCommand _oldFindTextCommand; private LpexCommand _findTextCommand = new LpexCommand() { public boolean doCommand(LpexView lpexView, String parameters) { return doFindTextCommand(lpexView, parameters); }}; /** * Runs this command. * Highlights the find-text matches on the current screen. */ public boolean doCommand(LpexView lpexView, String parameters) { if (lpexView == null) { return true; } if ("?".equals(parameters.trim())) // command help { lpexView.doCommand("set messageText Syntax: matches [<text>]"); clearMatches(lpexView); return true; } // ensure the mark highlight character style is still defined lpexView.doCommand("set styleAttributes." + _matchStyleChar + ' ' + _matchStyle); // in order to get found-text's length for each match (which may differ each time // in the case of regular expression), temporarily extend the "findText" command // in this view so we can query the emphasisLength after each find _oldFindTextCommand = lpexView.defineCommand("findText", _findTextCommand); // System.out.println(" class="+lpexView.query("commandClass.findText")); // clear any old matches clearMatches(lpexView); // do the searching doFinds(lpexView, parameters); // restore the original "findText" command in this view lpexView.defineCommand("findText", _oldFindTextCommand); // System.out.println(" class="+lpexView.query("commandClass.findText")); return true; } /** * Implementation of the temporarily redefined "findText" command. */ boolean doFindTextCommand(LpexView lpexView, String parameters) { boolean rc; if (_oldFindTextCommand != null) { rc = _oldFindTextCommand.doCommand(lpexView, parameters); } else { rc = lpexView.doDefaultCommand("findText " + parameters); } _foundTextLength = lpexView.queryInt("emphasisLength"); return rc; } /** * Clear all the match marks from a previous run. */ void clearMatches(LpexView lpexView) { if (!_marks.isEmpty()) { Iterator<String> iterator = _marks.iterator(); while (iterator.hasNext()) { String markId = iterator.next(); lpexView.doCommand("set mark.#" + markId + " clear"); } _marks.clear(); } } /** * Returns the basic parameters for the "findText" command we'll use. * Overrides FindsCommand's in order to drop the noEmphasis option - * we need emphasisLength for the match mark. */ String basicFindTextParms() { return "quiet noBeep noWrap "; } /** * Notification from #doFinds() of a successful find. * Overrides FindsCommand's in order to set a match mark. */ void found(LpexView lpexView, LpexDocumentLocation loc) { lpexView.doCommand("set mark. " + loc.element + ' ' + loc.position + ' ' + loc.element + ' ' + (loc.position + _foundTextLength -1)); String markId = lpexView.query("markId."); lpexView.doCommand("set markHighlight.#" + markId + " on"); lpexView.doCommand("set markStyle.#" + markId + ' ' + _matchStyleChar); _marks.add(markId); } }