⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 abstractsearchdialog.java

📁 具有不同语法高亮的编辑器实例
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
/*
 * 04/08/2004
 *
 * AbstractSearchDialog.java - Base class for all search dialogs
 *                             (find, replace, etc.).
 * Copyright (C) 2004 Robert Futrell
 * email@address.com
 * www.website.com
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
 */
package org.fife.ui.search;

import java.awt.Frame;
import java.awt.Point;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.util.ArrayList;
import java.util.ResourceBundle;
import java.util.Vector;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.swing.ActionMap;
import javax.swing.BorderFactory;
import javax.swing.BoxLayout;
import javax.swing.InputMap;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComponent;
import javax.swing.JDialog;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JRootPane;
import javax.swing.KeyStroke;
import javax.swing.border.Border;

import org.fife.RUtilities;
import org.fife.ui.MaxWidthComboBox;
import org.fife.ui.RButton;
import org.fife.ui.RComboBoxModel;


/**
 * Base class for all search dialogs (find, replace, find in files, etc.).
 * This class is not useful on its own; you should use either FindDialog
 * or ReplaceDialog, or extend this class to create your own search
 * dialog.
 *
 * @author Robert Futrell
 * @version 0.1
 */
public class AbstractSearchDialog extends JDialog implements ActionListener {


	/**
	 * 
	 */
	private static final long serialVersionUID = -1628956085490808507L;

	public static final String MATCH_CASE_PROPERTY		= "SearchDialog.MatchCase";
	public static final String MATCH_WHOLE_WORD_PROPERTY	= "SearchDialog.MatchWholeWord";
	public static final String USE_REG_EX_PROPERTY		= "SearchDialog.UseRegularExpressions";


	// Conditions check boxes and the panel they go in.
	// This should be added in the actual layout of the search dialog.
	protected JCheckBox caseCheckBox;
	protected JCheckBox wholeWordCheckBox;
	protected JCheckBox regExpCheckBox;
	protected JPanel searchConditionsPanel;

	/**
	 * The combo box where the user enters the text for which to search.
	 */
	protected MaxWidthComboBox findTextComboBox;

	// Miscellaneous other stuff.
	protected JButton cancelButton;


/*****************************************************************************/


	/**
	 * Constructor.  Does initializing for parts common to all search
	 * dialogs.
	 *
	 * @param owner The window that owns this search dialog.
	 * @param resources The resource bundle from which to get strings, etc.
	 * @param useRButtons If <code>true</code>, then
	 *        <code>org.fife.ui.RButton</code>s will be used for all buttons
	 *        defined here (currently just the Cancel button).  Otherwise,
	 *        regular <code>JButton</code>s are used.
	 */
	public AbstractSearchDialog(Frame owner, ResourceBundle resources,
										boolean useRButtons) {

		super(owner);

		// Make a panel containing the option checkboxes.
		searchConditionsPanel = new JPanel();
		searchConditionsPanel.setLayout(new BoxLayout(searchConditionsPanel, BoxLayout.Y_AXIS));
		caseCheckBox = RUtilities.createCheckBox(resources, "MatchCase", "MatchCaseMnemonic");
		caseCheckBox.setActionCommand("FlipMatchCaseValue");
		caseCheckBox.addActionListener(this);
		searchConditionsPanel.add(caseCheckBox);
		wholeWordCheckBox = RUtilities.createCheckBox(resources,
									"WholeWord", "WholeWordMnemonic");
		wholeWordCheckBox.setActionCommand("FlipWholeWordValue");
		wholeWordCheckBox.addActionListener(this);
		searchConditionsPanel.add(wholeWordCheckBox);
		regExpCheckBox = RUtilities.createCheckBox(resources, "RegEx", "RegExMnemonic");
		regExpCheckBox.setActionCommand("FlipRegularExpressionValue");
		regExpCheckBox.addActionListener(this);
		searchConditionsPanel.add(regExpCheckBox);

		// Initialize any text fields.
		findTextComboBox = new MaxWidthComboBox(new RComboBoxModel(), 200);
		findTextComboBox.setEditable(true);

		// Initialize other stuff.
		if (useRButtons==true) {
			cancelButton = new RButton(resources.getString("Cancel"));
		}
		else {
			cancelButton = new JButton(resources.getString("Cancel"));
		}
		cancelButton.setMnemonic((int)resources.getString("CancelMnemonic").charAt(0));
		cancelButton.setActionCommand("Cancel");
		cancelButton.addActionListener(this);
		
	}


/*****************************************************************************/


	/**
	 * Listens for actions in this search dialog.
	 */
	public void actionPerformed(ActionEvent e) {

		String actionCommand = e.getActionCommand();

		// They check/uncheck the "Match Case" checkbox on the Find dialog.
		if (actionCommand.equals("FlipMatchCaseValue")) {
			boolean matchCase = caseCheckBox.isSelected();
			firePropertyChange(MATCH_CASE_PROPERTY, !matchCase, matchCase);
		}

		// They check/uncheck the "Whole word" checkbox on the Find dialog.
		else if (actionCommand.equals("FlipWholeWordValue")) {
			boolean wholeWord = wholeWordCheckBox.isSelected();
			firePropertyChange(MATCH_WHOLE_WORD_PROPERTY, !wholeWord, wholeWord);
		}

		// They check/uncheck the "Regular expression" checkbox.
		else if (actionCommand.equals("FlipRegularExpressionValue")) {
			boolean useRegEx = regExpCheckBox.isSelected();
			firePropertyChange(USE_REG_EX_PROPERTY, !useRegEx, useRegEx);
		}

		// If they press the "Cancel" button.
		else if (actionCommand.equals("Cancel")) {
			setVisible(false);
		}

	}


/*****************************************************************************/


	/**
	 * Returns a titled border for panels on search dialogs.
	 *
	 * @param title The title for the border.
	 * @return The border.
	 */
	protected Border createTitledBorder(String title) {
		if (title!=null && title.charAt(title.length()-1)!=':')
			title += ":";
		return BorderFactory.createTitledBorder(title);
	}


/*****************************************************************************/


	/**
	 * Returns the text on the Cancel button.
	 *
	 * @return The text on the Cancel button.
	 * @see #setCancelButtonText
	 */
	public final String getCancelButtonText() {
		return cancelButton.getText();
	}


/*****************************************************************************/


	/**
	 * Returns the text for the "Match Case" check box.
	 *
	 * @return The text for the "Match Case" check box.
	 * @see #setMatchCaseCheckboxText
	 */
	public final String getMatchCaseCheckboxText() {
		return caseCheckBox.getText();
	}


/*****************************************************************************/


	/**
	 * Returns the text for the "Regular Expression" check box.
	 *
	 * @return The text for the "Regular Expression" check box.
	 * @see #setRegularExpressionCheckboxText
	 */
	public final String getRegularExpressionCheckboxText() {
		return regExpCheckBox.getText();
	}


/*****************************************************************************/


	/**
	 * Returns the text for the "Whole Word" check box.
	 *
	 * @return The text for the "Whole Word" check box.
	 * @see #setWholeWordCheckboxText
	 */
	public final String getWholeWordCheckboxText() {
		return wholeWordCheckBox.getText();
	}


/*****************************************************************************/


	/**
	 * Searches <code>searchIn</code> for an occurance of
	 * <code>searchFor</code> either forwards or backwards, matching case or
	 * not.
	 *
	 * @param searchFor The string to look for.
	 * @param searchIn The string to search in.
	 * @param startPos The position in <code>searchIn</code> at which to begin
	 *        searching.
	 * @param goForward Whether to search forward or backward in
	 *        <code>searchIn</code>.
	 * @param matchCase If <code>true</code>, do a case-sensitive search for
	 *        <code>searchFor</code>.
	 * @param lookForWholeWord If <code>true</code>, <code>searchFor</code>
	 *        occurances embedded in longer words in <code>searchIn</code>
	 *        don't count as matches.
	 * @return The starting position of a match, or <code>-1</code> if no match
	 *         was found.
	 * @see #getNextMatchPosImpl
	 * @see #getNextMatchPosRegEx
	 */
	public static final int getNextMatchPos(String searchFor, String searchIn,
					int startPos, boolean goForward, boolean matchCase,
					boolean lookForWholeWord) {

		// To speed up things a tad below if looking for a "whole word".
		int tempChange = 0;
		if (lookForWholeWord) {
			// If going FORWARD and we found a match that isn't a whole word,
			// we continue searching 2 characters AFTER the end of the
			// non-whole-word match, as that's the first position where a
			// whole-word match could possibly be.
			// If going BACKWARD and we found a match that isn't a whole
			// word, we continue searching (searchFor.length()+1) characters
			// before the beginning of the non-whole word match.  This is
			// because String.lastIndexOf() will return a match BEGINNING at
			// the specified location (e.g., "fatty".lastIndexOf("at", 1)
			// returns 1).
			tempChange = goForward ?	searchFor.length() + 1 :
								-(searchFor.length() + 1);
		}

		// Make our variables lower case if we're ignoring case.
		if (!matchCase) {
			return getNextMatchPosImpl(searchFor.toLowerCase(),
					searchIn.toLowerCase(), startPos, goForward, matchCase,
					lookForWholeWord, tempChange);
		}

		return getNextMatchPosImpl(searchFor, searchIn, startPos, goForward,
							matchCase, lookForWholeWord, tempChange);

	}


/*****************************************************************************/


	/**
	 * Actually does the work of matching; assumes searchFor and searchIn are
	 * already upper/lower-cased appropriately.<br>

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -