2012-09-24 27 views
2

拼写检查我有一个Eclipse插件RCP应用程序,我想用一个拼写检查上一个SWT浏览器窗口小部件。只是检查,看是否有人知道如何实现这个或者如果有一些内置的。如何在SWT应用程序

+0

Eclipse有嵌入式拼写检查。它基本上只是检查你的话(在评论中)与它存储在某个地方的单词列表。 – SJuan76

+0

让我怎么在我的应用程序使用此拼写检查器。我如何实例化它。 – Will

+0

我不知道你想要做的拼写检查在浏览器或文本编辑器?要对浏览器进行拼写检查,您可以在浏览器上执行拼写检查Java脚本。 –

回答

0

@ tm.sauron这是相当长的时间以前,所以我不得不通过一个旧的项目看。如果我没记错的话,我最终创造了我自己的。我创建了一个对话框,当我在我的富文本编辑器中单击拼写检查图标时会打开。我将把代码粘贴到对话框和实际的拼写检查器类中。希望你能看到我在做什么并弄清楚。

import java.io.IOException; 
import java.net.URISyntaxException; 
import java.util.ArrayList; 
import java.util.Collection; 
import java.util.HashMap; 
import java.util.LinkedList; 
import java.util.Queue; 
import java.util.regex.Pattern; 

import org.eclipse.epf.richtext.IRichText; 
import org.eclipse.jface.dialogs.MessageDialog; 
import org.eclipse.swt.SWT; 
import org.eclipse.swt.events.FocusAdapter; 
import org.eclipse.swt.events.FocusEvent; 
import org.eclipse.swt.events.KeyAdapter; 
import org.eclipse.swt.events.KeyEvent; 
import org.eclipse.swt.events.SelectionAdapter; 
import org.eclipse.swt.events.SelectionEvent; 
import org.eclipse.swt.graphics.Point; 
import org.eclipse.swt.layout.GridData; 
import org.eclipse.swt.layout.GridLayout; 
import org.eclipse.swt.widgets.Button; 
import org.eclipse.swt.widgets.Composite; 
import org.eclipse.swt.widgets.Control; 
import org.eclipse.swt.widgets.Display; 
import org.eclipse.swt.widgets.Label; 
import org.eclipse.swt.widgets.List; 
import org.eclipse.swt.widgets.Shell; 
import org.eclipse.swt.widgets.Text; 

public class SpellCheckerDialog extends BaseDialog { 

    private SpellChecker spellChecker; 
    private Queue<String> misspelledWords = new LinkedList<String>(); 
    private Text wrongWord; 
    private List suggestedWords; 
    private Button ignoreButton; 
    private Button changeButton; 
    private IgnoreButtonListener ignoreButtonListener = new IgnoreButtonListener(); 
    private ChangeButtonListener changeButtonListener = new ChangeButtonListener(); 
    private ModifiedChangeButtonListener modifiedChangeButtonListener = new ModifiedChangeButtonListener(); 
    private ModifiedIgnoreButtonListener modifiedIgnoreButtonListener = new ModifiedIgnoreButtonListener(); 
    private String oldWrongWord; 
    private int currentWord = 1; 
    private int totalWords; 
    private IRichText richText; 
    private String noHTMLString; 

    public SpellCheckerDialog(Shell parent, IRichText richText) { 
     super(parent); 
     setShellStyle(SWT.DIALOG_TRIM | SWT.MODELESS | getDefaultOrientation()); 

     this.richText = richText; 

     if (richText != null) { 
      /* Instantiate spell checker */ 
      try { 
       spellChecker = new SpellChecker(); 
       findMisspelledWords(); 
      } catch (URISyntaxException e) { 
       MessageDialog.openInformation(Display.getDefault().getActiveShell(), "Dictionary file for rich text editor not found", e.getMessage()); 
       e.printStackTrace(); 
      } catch (IOException e) { 
       MessageDialog.openInformation(Display.getDefault().getActiveShell(), "Dictionary file for rich text editor not found", e.getMessage()); 
       e.printStackTrace(); 
      } 
     } 
    } 

    @Override 
    protected Control createDialogArea(Composite parent) { 
     Composite composite = (Composite) super.createDialogArea(parent); 
     composite.setLayout(new GridLayout(2, false)); 
     composite.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true)); 

     /* Not in dictionary label */ 
     new Label(composite, SWT.NONE).setText("Not in Dictionary:"); 
     new Label(composite, SWT.NONE); 

     /* Current Misspelled Word */ 
     wrongWord = new Text(composite, SWT.MULTI | SWT.BORDER | SWT.WRAP | SWT.V_SCROLL); 
     GridData gd = new GridData(SWT.FILL, SWT.FILL, true, true); 
     gd.heightHint = 75; 
     gd.minimumHeight = 75; 
     wrongWord.setLayoutData(gd); 
     wrongWord.addKeyListener(new WrongWordKeyListener()); 
     wrongWord.addFocusListener(new WrongWordFocusListener()); 

     /* Ignore Button Actions */ 
     GridData buttonCompositeGridData = new GridData(SWT.FILL, SWT.FILL, false, true); 
     buttonCompositeGridData.widthHint = 125; 
     Composite topButtonActionsComposite = new Composite(composite, SWT.NONE); 
     topButtonActionsComposite.setLayout(new GridLayout()); 
     topButtonActionsComposite.setLayoutData(buttonCompositeGridData); 
     ignoreButton = new Button(topButtonActionsComposite, SWT.PUSH); 
     ignoreButton.setText("Ignore"); 
     ignoreButton.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false)); 
     ignoreButton.addSelectionListener(ignoreButtonListener); 

     /* Suggestions label */ 
     new Label(composite, SWT.NONE).setText("Suggestions:"); 
     new Label(composite, SWT.NONE); 

     /* Suggested Words */ 
     suggestedWords = new List(composite, SWT.BORDER | SWT.V_SCROLL | SWT.SINGLE); 
     suggestedWords.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true)); 

     /* Change Button Actions */ 
     Composite bottomButtonActionsComposite = new Composite(composite, SWT.NONE); 
     bottomButtonActionsComposite.setLayout(new GridLayout()); 
     bottomButtonActionsComposite.setLayoutData(buttonCompositeGridData); 
     changeButton = new Button(bottomButtonActionsComposite, SWT.PUSH); 
     changeButton.setText("Change"); 
     changeButton.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false)); 
     changeButton.addSelectionListener(changeButtonListener); 

     startSpellChecking(); 
     return composite; 
    } 

    private void startSpellChecking() { 
     if (!misspelledWords.isEmpty()) { 
      super.getShell().setText("Spell Checker (" + currentWord + "/" + totalWords + ")"); 
      String firstWord = misspelledWords.poll(); 
      HashMap<Integer, String> suggestions = spellChecker.suggestions(firstWord); 

      /* get order of suggestions */ 
      java.util.List<Integer> sortedKeys = asSortedList(suggestions.keySet()); 

      wrongWord.setText(firstWord); 

      suggestedWords.removeAll(); 
      for (Integer i : sortedKeys) { 
       suggestedWords.add(suggestions.get(i)); 
      } 

      /* if there are no suggestions */ 
      if (suggestions.size() == 0) { 
       suggestedWords.add("No Suggestions"); 
       changeButton.setEnabled(false); 
      } else { 
       changeButton.setEnabled(true); 
      } 

      suggestedWords.select(0); 
      currentWord++; 
     } else { 
      MessageDialog.openInformation(Display.getDefault().getActiveShell(), "No Misspellings", "There were no more misspelled words found."); 
      super.close(); 
     } 
    } 

    private void findMisspelledWords() { 
     misspelledWords.clear(); 

     /* Get all words in textfield */ 
     String[] cleanWords = cleanText(richText.getText()); 
     for(String w:cleanWords){ 
      System.out.println(w); 
     } 

     for (String word : cleanWords) { 
      if (!word.equals(" ") && !word.isEmpty()) { 
       if (!spellChecker.isInDictionary(word)) { 
        misspelledWords.add(word); 
       } 
      } 
     } 
     totalWords = misspelledWords.size(); 
    } 

    /** 
    * removes html content, new line characters, white spaces at the beginning 
    * or end of words, punctuation or non-letters, makes lowercase because that 
    * is what the dictionary works with 
    * 
    * @param text 
    * @return 
    */ 
    private String[] cleanText(String text) { 
     /* Remove html */ 
     noHTMLString = text.replaceAll("\\<.*?>", ""); 
     noHTMLString = noHTMLString.replaceAll("&.*?;", ""); 
     if (noHTMLString.contains("<")) { 
      int length = 0; 
      while (noHTMLString.length() != length) { 
       length = htmlTagRemoval(noHTMLString); 
      } 
      System.out.println("after manual removal noHTMLString: " + noHTMLString); 
     } 

     /* Remove New Lines */ 
     noHTMLString = noHTMLString.replaceAll("[\\t\\n\\r]", " "); 

     String[] allWords = noHTMLString.split(" "); 
     java.util.List<String> cleanedAllWords = new ArrayList<String>(); 

     for (String word : allWords) { 
      /* remove white spaces */ 
      word = word.trim(); 
      /* remove non letters */ 
      if (!containsOnlyLetters(word)) { 
       word = removeNonLetters(word); 
      } 
      cleanedAllWords.add(word); 
     } 

     /* Make all lowercase */ 
     for (int i = 0; i < cleanedAllWords.size(); i++) { 
      cleanedAllWords.set(i, cleanedAllWords.get(i).toLowerCase()); 
     } 

     return cleanedAllWords.toArray(new String[cleanedAllWords.size()]); 
    } 

    private int htmlTagRemoval(String string) { 
     int i = 0; 
     Integer start = null, end = null; 
     for (i = 0; i < string.length(); i++) { 
      if (string.toCharArray()[i] == '<') { 
       start = i; 
      } 
      if (start != null && string.toCharArray()[i] == '>') { 
       end = i; 
       noHTMLString = string.replace(string.subSequence(start, end + 1), ""); 
       break; 
      } 
     } 
     return i; 
    } 

    private boolean containsOnlyLetters(String s) { 
     if (Pattern.matches("[a-zA-Z]+", s)) { 
      return true; 
     } else { 
      return false; 
     } 
    } 

    private String removeNonLetters(String s) { 
     StringBuffer sb = new StringBuffer(); 

     for (int i = 0; i < s.length(); i++) { 
      if (Character.isLetter(s.charAt(i)) || s.charAt(i) == '\'') { 
       sb = sb.append(s.charAt(i)); 
      } 
     } 
     return sb.toString(); 
    } 

    private class WrongWordKeyListener extends KeyAdapter { 
     @Override 
     public void keyReleased(KeyEvent e) { 

      /* 
      * Disable suggested words and change ignore button to undo button 
      * and the change button listener 
      */ 
      suggestedWords.setEnabled(false); 

      ignoreButton.setEnabled(true); 
      ignoreButton.setText("Undo Edit"); 
      ignoreButton.removeSelectionListener(ignoreButtonListener); 
      ignoreButton.addSelectionListener(modifiedIgnoreButtonListener); 

      changeButton.setEnabled(true); 
      changeButton.removeSelectionListener(changeButtonListener); 
      changeButton.addSelectionListener(modifiedChangeButtonListener); 

      wrongWord.removeKeyListener(this); 

     } 
    } 

    /** 
    * This stors the old word incase the user wants to undo the edit later. 
    * 
    * @author Will 
    * 
    */ 
    private class WrongWordFocusListener extends FocusAdapter { 
     @Override 
     public void focusGained(FocusEvent e) { 
      oldWrongWord = wrongWord.getText(); 
      super.focusGained(e); 
     } 
    } 

    private class IgnoreButtonListener extends SelectionAdapter { 
     @Override 
     public void widgetSelected(SelectionEvent e) { 
      // go to next word 
      startSpellChecking(); 
     } 
    } 

    private class ChangeButtonListener extends SelectionAdapter { 
     @Override 
     public void widgetSelected(SelectionEvent e) { 
      String newWord = suggestedWords.getSelection()[0]; 

      // change old word 
      String correctedChanges = richText.getText().replace(wrongWord.getText(), newWord); 
      richText.setText(correctedChanges); 

      // next word 
      startSpellChecking(); 

     } 
    } 

    /** 
    * This is used when the user manually edits the misspelled word and changes 
    * it 
    * 
    * @author Will 
    * 
    */ 
    private class ModifiedChangeButtonListener extends SelectionAdapter { 
     @Override 
     public void widgetSelected(SelectionEvent e) { 
      String newWord = wrongWord.getText(); 

      // change old word 
      String correctedChanges = richText.getText().replace(oldWrongWord, newWord); 
      richText.setText(correctedChanges); 

      ignoreButton.setText("Ignore"); 
      ignoreButton.removeSelectionListener(modifiedIgnoreButtonListener); 
      ignoreButton.addSelectionListener(ignoreButtonListener); 

      changeButton.removeSelectionListener(modifiedChangeButtonListener); 
      changeButton.addSelectionListener(changeButtonListener); 

      suggestedWords.setEnabled(true); 

      wrongWord.addKeyListener(new WrongWordKeyListener()); 

      // next word 
      startSpellChecking(); 

     } 
    } 

    /** 
    * This is used when the user manually edits the misspelled word and wants 
    * to undo changes 
    * 
    * @author Will 
    * 
    */ 
    private class ModifiedIgnoreButtonListener extends SelectionAdapter { 
     @Override 
     public void widgetSelected(SelectionEvent e) { 
      /* 
      * rename ignore button, fix listeners on both buttons, enable 
      * suggested words, undo edit, add modify listener back 
      */ 
      ignoreButton.setText("Ignore"); 
      ignoreButton.removeSelectionListener(modifiedIgnoreButtonListener); 
      ignoreButton.addSelectionListener(ignoreButtonListener); 

      changeButton.removeSelectionListener(modifiedChangeButtonListener); 
      changeButton.addSelectionListener(changeButtonListener); 

      suggestedWords.setEnabled(true); 

      wrongWord.setText(oldWrongWord); 
      wrongWord.addKeyListener(new WrongWordKeyListener()); 

      if (suggestedWords.getItem(0).equals("No Suggestions")) { 
       changeButton.setEnabled(false); 
      } 

     } 
    } 

    private static <T extends Comparable<? super T>> java.util.List<T> asSortedList(Collection<T> c) { 
     java.util.List<T> list = new ArrayList<T>(c); 
     java.util.Collections.sort(list); 
     java.util.Collections.reverse(list); 
     return list; 
    } 

    @Override 
    protected Control createButtonBar(Composite parent) { 
     return null; 
    } 

    @Override 
    protected Point getInitialSize() { 
     Point size = super.getInitialSize(); 
     size.x = 500; 
     size.y = 350; 
     return size; 
    } 
} 

这里是拼写检查类:

import java.io.BufferedReader; 
import java.io.File; 
import java.io.FileReader; 
import java.io.IOException; 
import java.net.URISyntaxException; 
import java.net.URL; 
import java.util.ArrayList; 
import java.util.Collections; 
import java.util.HashMap; 
import java.util.regex.Matcher; 
import java.util.regex.Pattern; 

import org.eclipse.core.runtime.FileLocator; 
import org.eclipse.epf.richtext.RichTextPlugin; 
import org.osgi.framework.Bundle; 

class SpellChecker { 

    private final HashMap<String, Integer> nWords = new HashMap<String, Integer>(); 

    public SpellChecker() throws URISyntaxException, IOException { 
     Bundle bundle = RichTextPlugin.getDefault().getBundle(); 
     URL fileURL = bundle.getEntry("files/dictionary.txt"); 
     File file = null; 
     file = new File(FileLocator.resolve(fileURL).toURI()); 

     BufferedReader in = new BufferedReader(new FileReader(file)); 
     Pattern p = Pattern.compile("\\w+"); 
     for (String temp = ""; temp != null; temp = in.readLine()) { 
      Matcher m = p.matcher(temp.toLowerCase()); 
      while (m.find()) 
       nWords.put((temp = m.group()), nWords.containsKey(temp) ? nWords.get(temp) + 1 : 1); 
     } 
     in.close(); 
    } 

    public boolean isInDictionary(String word){ 
     return nWords.containsKey(word) ? true : false; 
    } 

    private final ArrayList<String> edits(String word) { 
     ArrayList<String> result = new ArrayList<String>(); 
     for (int i = 0; i < word.length(); ++i) 
      result.add(word.substring(0, i) + word.substring(i + 1)); 
     for (int i = 0; i < word.length() - 1; ++i) 
      result.add(word.substring(0, i) + word.substring(i + 1, i + 2) + word.substring(i, i + 1) + word.substring(i + 2)); 
     for (int i = 0; i < word.length(); ++i) 
      for (char c = 'a'; c <= 'z'; ++c) 
       result.add(word.substring(0, i) + String.valueOf(c) + word.substring(i + 1)); 
     for (int i = 0; i <= word.length(); ++i) 
      for (char c = 'a'; c <= 'z'; ++c) 
       result.add(word.substring(0, i) + String.valueOf(c) + word.substring(i)); 
     return result; 
    } 

    public final String correct(String word) { 
     if (nWords.containsKey(word)) 
      return word; 
     ArrayList<String> list = edits(word); 
     HashMap<Integer, String> candidates = new HashMap<Integer, String>(); 
     for (String s : list) 
      if (nWords.containsKey(s)) 
       candidates.put(nWords.get(s), s); 
     if (candidates.size() > 0) 
      return candidates.get(Collections.max(candidates.keySet())); 
     for (String s : list) 
      for (String w : edits(s)) 
       if (nWords.containsKey(w)) 
        candidates.put(nWords.get(w), w); 
     return candidates.size() > 0 ? candidates.get(Collections.max(candidates.keySet())) : word; 
    } 

    public final HashMap<Integer, String> suggestions(String word) { 
     if (nWords.containsKey(word)) { 
      HashMap<Integer, String> wordMap = new HashMap<Integer, String>(); 
      wordMap.put(1, word); 
      return wordMap; 
     } 
     ArrayList<String> list = edits(word); 
     HashMap<Integer, String> candidates = new HashMap<Integer, String>(); 
     for (String s : list) 
      if (nWords.containsKey(s)) 
       candidates.put(nWords.get(s), s); 
     if (candidates.size() > 0) 
      return candidates; 
     for (String s : list) 
      for (String w : edits(s)) 
       if (nWords.containsKey(w)) 
        candidates.put(nWords.get(w), w); 
     return candidates; 
    } 

} 
相关问题