zoukankan      html  css  js  c++  java
  • Eclipse插件开发之Preference扩展点的学习

    Preferences展点及其使用心得

    本文学习参照文章“Preferences in the Eclipse Workbench UI”,除了实现流程外,更重要的是对例子中代码的学习

    在Eclipse中,选择window->preferences后打开preferences窗口,这个窗口是Eclipse所有设置项的集中地,同时也是我们自定义的插件进行设置的窗口。

    第一章:Preference概述

    Preference是一种数据,它存在于工作空间中,存储的是Eclipse工作的状态,使之保持一致性。Eclipse2.0提供了两种preference:UI preferences (the same as in 1.0) and Core Preferences。Preference并不涉及到当前工作空间中的任何资源,它应该被编辑器,视图或者其它的操作资源的对象所使用。一种资源实例对应的数据最好存储成一个属性。Preference对任何插件来说都是可用的,当然,先决条件是存在插件。通常的方法是你的插件上为你觉得可能被其他插件用到的Preference提供API, Preference的值存储在工作空间的.metadata/.plugins目录下面。

    每个插件都有自己的preference store(存储区),这是工作空间提供的。在下面的例子中(这个例子是在文件中查找错误的单词),我们将定义一个插件,使用它的preference store存储preference。在UI中当要使用插件的时候我们定义AbustractUIPlugin的子类。构造函数将在工作台中创建一个独立的允许容易访问的插件实例。我们实现方法initializeDefaultPreferences为preference设置默认值。首先为错误的单词定义了一个preference,另外一个是定义高量显示的颜色。每个preference的值与给定的key(键值对的存在形式)相对应。

    所有的preference应该都有默认值来保证在任何时候都有值。默认值也保证了UI能够提供一种方式重置preference的值回到初始设定,这是通过“Restore”button实现的。Preference的默认值在插件中也应该进行初始化,以便它在任何UI创建之前设置。  

    第二章:示例实现

                

      一个插件在工作区都会有它的参数存储区 ,在本例中,我们定义一个插件用它的参数存储区来作为我们的参数。因为要用到UI界面,我们把它实现为AbstractUIPlugin的子类---IabstractWorkbenchPlugin类, IabstractWorkbenchPlugin定义了一个方法,当preference第一次创建的时候,它会被调用。这个方法就是initializeDefaultPreferences。在这个方法中你应该把所有的值都设为默认值,才能够使用preference store。我们在PreferenceConverter中用helper方法设定默认的color,PreferenceConverter允许插件开发者设置和得到一些常见的存储类型的preference的值,例如FontData,Point等等。这个API提供是因为preference无论是存储还是读取都是String—以一种我们人可以理解的格式。这样来平衡的属性机制。我们那个稍微复杂的错误单词的preference在初始化的时候使用了预先设定的值因为在PreferenceConvertor中并没有提供API来存储和读取String数组。

    public class BadWordCheckerPlugin extends AbstractUIPlugin {
            //The shared instance.
            private static BadWordCheckerPlugin plugin;
     
            //The identifiers for the preferences 
            public static final String BAD_WORDS_PREFERENCE = "badwords";
            public static final String HIGHLIGHT_PREFERENCE = "highlight";
     
            //The default values for the preferences
            public static final String DEFAULT_BAD_WORDS = "bug;bogus;hack;";
            public static final int DEFAULT_HIGHLIGHT = SWT.COLOR_BLUE;
     
            public BadWordCheckerPlugin(IPluginDescriptor descriptor) {
                   super(descriptor);
                   plugin = this;
            }
     
            public static BadWordCheckerPlugin getDefault() {
                   return plugin;
            }
     
            /** 
             * Initializes a preference store with default preference values 
             * for this plug-in.
             */
            protected void initializeDefaultPreferences(IPreferenceStore store) {
                   store.setDefault(BAD_WORDS_PREFERENCE, DEFAULT_BAD_WORDS);
                   Color color= Display.getDefault().getSystemColor(DEFAULT_HIGHLIGHT);
                   PreferenceConverter.setDefault(store,  HIGHLIGHT_PREFERENCE, color.getRGB());
     
            }
    }

    xml中配置

    <extension point="org.eclipse.ui.preferencePages">

            <page id="BadWordsPreferencePage"

                name="Bad Words"

                class="org.eclipse.ui.articles.badwordchecker.BadWordsPreferencePage">

            </page>

           

            <page id="BadWordsColorPreferencePage"

                    name="Colors"

                          class="org.eclipse.ui.articles.badwordchecker.BadWordsColorPreferencePage"

                category="BadWordsPreferencePage">

            </page>

    </extension>

    是在页面中显示的名字, 是参数配置页面类,这个类必须实现IWorkbenchPreferencePage接口。 是页面中显示的包含关系(不用多解释)。

    第二个类:reference Page

    这个页面只是一个用JFace实现的简单页面,Eclipse中有个PreferencePage类—它实现了Preference 页面需要的大多数API,当点下确定键后,参数对话框的信息就会被保存。代码如下:

    package org.eclipse.ui.articles.badwordchecker;

    import org.eclipse.jface.preference.ColorFieldEditor;

    import org.eclipse.jface.preference.PreferencePage;

    import org.eclipse.swt.SWT;

    import org.eclipse.swt.layout.GridData;

    import org.eclipse.swt.layout.GridLayout;

    import org.eclipse.swt.widgets.Composite;

    import org.eclipse.swt.widgets.Control;

    import org.eclipse.ui.IWorkbench;

    import org.eclipse.ui.IWorkbenchPreferencePage;

    /**

     * The BadWordsColorPreferencePage is a preference page that

     * handles setting the colors used by the editors.

     */

    public class BadWordsColorPreferencePage

                  extends PreferencePage

                  implements IWorkbenchPreferencePage {

                  private ColorFieldEditor colorEditor;

                  /*

                   * @see PreferencePage#createContents(Composite)

                   */

                  @SuppressWarnings("deprecation")

                  protected Control createContents(Composite parent) {

                                Composite entryTable = new Composite(parent, SWT.NULL);

                                //Create a data that takes up the extra space in the dialog .

                                GridData data = new GridData(GridData.FILL_HORIZONTAL);

                                data.grabExcessHorizontalSpace = true;

                                entryTable.setLayoutData(data);

                                GridLayout layout = new GridLayout();

                                entryTable.setLayout(layout);

                               

                                Composite colorComposite = new Composite(entryTable,SWT.NONE);

                                colorComposite.setLayout(new GridLayout());

                               

                                //Create a data that takes up the extra space in the dialog.

                                colorComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));

                                colorEditor =

                                              new ColorFieldEditor(

                                                            BadWordCheckerPlugin.HIGHLIGHT_PREFERENCE,

                                                            "Highlight Color",

                                                            colorComposite);                                           

                                             

                               

                                //Set the editor up to use this page

                                colorEditor.setPreferencePage(this);

                                colorEditor.setPreferenceStore(getPreferenceStore());

                                colorEditor.load();

                                return entryTable;

                  }

                  /*

                   * @see IWorkbenchPreferencePage#init(IWorkbench)

                   */

                  public void init(IWorkbench workbench) {

                                //Initialize the preference store we wish to use

                                setPreferenceStore(BadWordCheckerPlugin.getDefault().getPreferenceStore());

                  }

                  /**

                   * Performs special processing when this page's Restore Defaults button has

                   * been pressed.

                   * Sets the contents of the color field to the default value in the preference

                   * store.

                   */

                  protected void performDefaults() {

                                colorEditor.loadDefault();

                  }

                  /**

                   * Method declared on IPreferencePage. Save the

                   * color preference to the preference store.

                   */

                  public boolean performOk() {

                                colorEditor.store();

                                return super.performOk();

                  }

    }

    运行效果如下图:

    第三个类:ad Words Preference Page

    下面将要用一个更复杂些的组件作为preference,并使它存储在preference store且在preference页面中可编辑。例子是:添加String数组的bad words preference。

    由于PreferenceConverter没有String数组的API,我们在BadWordCheckerPlugin中来实现。添加如下代码:

    /**
     * Return the bad words preference default.
     */
    public String[] getDefaultBadWordsPreference(){
            return convert(getPreferenceStore().getDefaultString(BAD_WORDS_PREFERENCE));
    }
     
    /**
     * Returns the bad words preference.
     */
    public String[] getBadWordsPreference() {
            return convert(getPreferenceStore().getString(BAD_WORDS_PREFERENCE));
    }
            
    /**
     * Converts PREFERENCE_DELIMITER delimited String to a String array.
     */
    private String[] convert(String preferenceValue) {
            StringTokenizer tokenizer =
                   new StringTokenizer(preferenceValue, PREFERENCE_DELIMITER);
            int tokenCount = tokenizer.countTokens();
            String[] elements = new String[tokenCount];
            for (int i = 0; i < tokenCount; i++) {
                   elements[i] = tokenizer.nextToken();
            }
     
            return elements;
    }
     
    /**
     * Sets the bad words preference.
     */
    public void setBadWordsPreference(String[] elements) {
            StringBuffer buffer = new StringBuffer();
            for (int i = 0; i < elements.length; i++) {
                   buffer.append(elements[i]);
                   buffer.append(PREFERENCE_DELIMITER);
            }
            getPreferenceStore().setValue(BAD_WORDS_PREFERENCE, buffer.toString());
    }

    BadWordsPreferencePage主要是实现界面和两个按键的响应。代码如下(可以仔细研究):

    package org.eclipse.ui.articles.badwordchecker;

    import org.eclipse.jface.preference.PreferencePage;

    import org.eclipse.swt.SWT;

    import org.eclipse.swt.events.SelectionAdapter;

    import org.eclipse.swt.events.SelectionEvent;

    import org.eclipse.swt.layout.GridData;

    import org.eclipse.swt.layout.GridLayout;

    import org.eclipse.swt.widgets.*;

    import org.eclipse.ui.IWorkbench;

    import org.eclipse.ui.IWorkbenchPreferencePage;

    public class BadWordsPreferencePage

                  extends PreferencePage

                  implements IWorkbenchPreferencePage {

                  //The list that displays the current bad words

                  private List badWordList;

                  //The newEntryText is the text where new bad words are specified

                  private Text newEntryText;

                  /*

                   * @see PreferencePage#createContents(Composite)

                   */

                  protected Control createContents(Composite parent) {

                                Composite entryTable = new Composite(parent, SWT.NULL);

                                //Create a data that takes up the extra space in the dialog .

                                GridData data = new GridData(GridData.FILL_HORIZONTAL);

                                data.grabExcessHorizontalSpace = true;

                                entryTable.setLayoutData(data);

                                GridLayout layout = new GridLayout();

                                entryTable.setLayout(layout);                                   

                                                           

                                //Add in a dummy label for spacing

                                new Label(entryTable,SWT.NONE);

                                badWordList = new List(entryTable, SWT.BORDER);

                                badWordList.setItems(BadWordCheckerPlugin.getDefault().getBadWordsPreference());

                                //Create a data that takes up the extra space in the dialog and spans both columns.

                                data = new GridData(GridData.FILL_BOTH);

                                badWordList.setLayoutData(data);

                               

                                Composite buttonComposite = new Composite(entryTable,SWT.NULL);

                               

                                GridLayout buttonLayout = new GridLayout();

                                buttonLayout.numColumns = 2;

                                buttonComposite.setLayout(buttonLayout);

                                //Create a data that takes up the extra space in the dialog and spans both columns.

                                data = new GridData(GridData.FILL_BOTH | GridData.VERTICAL_ALIGN_BEGINNING);

                                buttonComposite.setLayoutData(data);                    

                               

                                Button addButton = new Button(buttonComposite, SWT.PUSH | SWT.CENTER);

                                addButton.setText("Add to List"); //$NON-NLS-1$

                                addButton.addSelectionListener(new SelectionAdapter() {

                                              public void widgetSelected(SelectionEvent event) {

                                                            badWordList.add(newEntryText.getText(), badWordList.getItemCount());

                                              }

                                });

                               

                                newEntryText = new Text(buttonComposite, SWT.BORDER);

                                //Create a data that takes up the extra space in the dialog .

                                data = new GridData(GridData.FILL_HORIZONTAL);

                                data.grabExcessHorizontalSpace = true;

                                newEntryText.setLayoutData(data);

                               

                               

                                Button removeButton = new Button(buttonComposite, SWT.PUSH | SWT.CENTER);

                                removeButton.setText("Remove Selection"); //$NON-NLS-1$

                                removeButton.addSelectionListener(new SelectionAdapter() {

                                              public void widgetSelected(SelectionEvent event) {

                                                            badWordList.remove(badWordList.getSelectionIndex());

                                              }

                                });

                               

                                data = new GridData();

                                data.horizontalSpan = 2;

                                removeButton.setLayoutData(data);

                 

                                return entryTable;

                  }

                  /*

                   * @see IWorkbenchPreferencePage#init(IWorkbench)

                   */

                  public void init(IWorkbench workbench) {

                                //Initialize the preference store we wish to use

                                setPreferenceStore(BadWordCheckerPlugin.getDefault().getPreferenceStore());

                  }

                  /**

                   * Performs special processing when this page's Restore Defaults button has been pressed.

                   * Sets the contents of the nameEntry field to

                   * be the default

                   */

                  protected void performDefaults() {

                                badWordList.setItems(BadWordCheckerPlugin.getDefault().getDefaultBadWordsPreference());

                  }

                  /**

                   * Method declared on IPreferencePage. Save the

                   * author name to the preference store.

                   */

                  public boolean performOk() {

                                BadWordCheckerPlugin.getDefault().setBadWordsPreference

    (badWordList.getItems());

                                return super.performOk();

                  }

    }

    运行结果如下:

    第四:对参数值的应用

    通常,一个preference是向一个打开的editor或者view进行传值。这时,就需要通过IPropertyChangeListener对变化添加监听。IPropertyChangeListener类是对IProperyStore添加监听,当用户点击OK或者Apply时,监听会被触发。

    在这个例子中,我们实现了一个视图,用选定的颜色显示存在的bad words,这个视图通过IPropertyChangeListener更新显示的颜色。

       
       new IPropertyChangeListener() {
            public void propertyChange(PropertyChangeEvent event) {
                   if (event.getProperty().equals(BadWordCheckerPlugin.HIGHLIGHT_PREFERENCE)) {
                           //Update the colors by clearing the current color,
                           //updating the view and then disposing the old color.
                           Color oldForeground = foreground;
                           foreground = null;
                           setBadWordHighlights(text.getText());
                           oldForeground.dispose();
                   }
                   if (event.getProperty().equals(BadWordCheckerPlugin.BAD_WORDS_PREFERENCE))
                           //Only update the text if only the words have changed
                           setBadWordHighlights(text.getText());
            }
    };
       
       public void init(IViewSite site) throws PartInitException {
            super.init(site);
            site.getPage().addSelectionListener(...);
            BadWordCheckerPlugin
                   .getDefault()
                   .getPreferenceStore()
                   .addPropertyChangeListener(preferenceListener);}
       
       public void dispose() {
            getSite().getPage().removeSelectionListener(...);
            BadWordCheckerPlugin
                   .getDefault()
                   .getPreferenceStore()
                   .removePropertyChangeListener(preferenceListener);
            if (foreground != null)
                   foreground.dispose();
            super.dispose();
    }

    实现效果如下:

     

    具体类实现代码如下(好多代码还不懂,有待于学习):

    package org.eclipse.ui.articles.badwordchecker;

    import java.io.IOException;

    import java.io.InputStream;

    import org.eclipse.core.resources.IFile;

    import org.eclipse.core.resources.IResource;

    import org.eclipse.core.runtime.CoreException;

    import org.eclipse.core.runtime.IAdaptable;

    import org.eclipse.jface.preference.PreferenceConverter;

    import org.eclipse.jface.util.IPropertyChangeListener;

    import org.eclipse.jface.util.PropertyChangeEvent;

    import org.eclipse.jface.viewers.ISelection;

    import org.eclipse.jface.viewers.IStructuredSelection;

    import org.eclipse.swt.SWT;

    import org.eclipse.swt.custom.StyleRange;

    import org.eclipse.swt.custom.StyledText;

    import org.eclipse.swt.graphics.Color;

    import org.eclipse.swt.layout.GridData;

    import org.eclipse.swt.widgets.Composite;

    import org.eclipse.ui.ISelectionListener;

    import org.eclipse.ui.IViewSite;

    import org.eclipse.ui.IWorkbenchPart;

    import org.eclipse.ui.PartInitException;

    import org.eclipse.ui.part.ViewPart;

    /**

     * The BadWordsView is a simple view that creates a StyledText'

     * that highlights the bad words.

     */

    public class BadWordsView extends ViewPart {

                  private Color foreground;

                  private StyledText text;

                  ISelectionListener selectionListener = new ISelectionListener() {

                                /**

                                 * @see org.eclipse.ui.ISelectionListener#selectionChanged(IWorkbenchPart, ISelection)

                                 */

                                public void selectionChanged(

                                              IWorkbenchPart part,

                                              ISelection selection) {

                                              setText(selection);

                                }

                  };

                  IPropertyChangeListener preferenceListener =

                                new IPropertyChangeListener() {

                                /*

                                 * @see IPropertyChangeListener.propertyChange()

                                 */

                                public void propertyChange(PropertyChangeEvent event) {

                                              if (event

                                                            .getProperty()

                                                            .equals(BadWordCheckerPlugin.HIGHLIGHT_PREFERENCE)) {

                                                            //Update the colors by clearing the current color,

                                                            //updating the view and then disposing the old color.

                                                            Color oldForeground = foreground;

                                                            foreground = null;

                                                            setBadWordHighlights(text.getText());

                                                            oldForeground.dispose();

                                              }

                                              if (event

                                                            .getProperty()

                                                            .equals(BadWordCheckerPlugin.BAD_WORDS_PREFERENCE))

                                                            //Only update the text if only the words have changed

                                                            setBadWordHighlights(text.getText());

                                }

                  };

                  /**

                   * @see org.eclipse.ui.IWorkbenchPart#createPartControl(Composite)

                   */

                  public void createPartControl(Composite parent) {

                                text = new StyledText(parent, SWT.NULL);

                                GridData data = new GridData(GridData.FILL_BOTH);

                                text.setLayoutData(data);

                                setText(

                                              getSite()

                                                            .getWorkbenchWindow()

                                                            .getSelectionService()

                                                            .getSelection());

                  }

                  /**

                   * Set the text value in the widget passed on the supplied

                   * selection

                   */

                  private void setText(ISelection selection) {

                                if (selection instanceof IStructuredSelection) {

                                              Object firstObject =

                                                            ((IStructuredSelection) selection).getFirstElement();

                                              if (firstObject != null && firstObject instanceof IAdaptable) {

                                                            Object resource =

                                                                          ((IAdaptable) firstObject).getAdapter(IResource.class);

                                                            if (resource != null && resource instanceof IFile) {

                                                                          try {

                                                                                        InputStream contents = ((IFile) resource).getContents();

                                                                                        byte[] data = new byte[contents.available()];

                                                                                        contents.read(data);

                                                                                        setBadWordHighlights(new String(data));

                                                                          } catch (CoreException exception) {

                                                                                        //Do nothing

                                                                          } catch (IOException exception) {

                                                                                        //Do nothing

                                                                          }

                                                            }

                                              }

                                }

                  }

                  /**

                   * Set the highlights for the bad words using the passed in

                   * text

                   */

                  private void setBadWordHighlights(String fileContents) {

                                Color foregroundColor = getForegroundColor();

                                text.setText(fileContents);

                                String[] badStrings =

                                              BadWordCheckerPlugin.getDefault().getBadWordsPreference();

                                Color background = text.getBackground();

                                for (int i = 0; i < badStrings.length; i++) {

                                              String badWord = badStrings[i];

                                              int length = badWord.length();

                                              int nextIndex = 0;

                                              while (nextIndex > -1) {

                                                            nextIndex = fileContents.indexOf(badWord, nextIndex);

                                                            if (nextIndex > -1) {

                                                                          StyleRange range =

                                                                                        new StyleRange(

                                                                                                      nextIndex,

                                                                                                      length,

                                                                                                      foregroundColor,

                                                                                                      background);

                                                                          text.setStyleRange(range);

                                                                          nextIndex += length;

                                                            }

                                              }

                                }

                  }

                  /**

                   * Get the current value of the foreground color.

                   * Create it if it does not exist yet.

                   */

                  private Color getForegroundColor() {

                                if (foreground == null)

                                              foreground =

                                                            new Color(

                                                                          text.getDisplay(),

                                                                          PreferenceConverter.getColor(

                                                                                        BadWordCheckerPlugin.getDefault().getPreferenceStore(),

                                                                                        BadWordCheckerPlugin.HIGHLIGHT_PREFERENCE));

                                return foreground;

                  }

                  /**

                   * @see org.eclipse.ui.IWorkbenchPart#setFocus()

                   */

                  public void setFocus() {

                  }

                  /* (non-Javadoc)

                  * Method declared on IViewPart.

                  */

                  public void init(IViewSite site) throws PartInitException {

                                super.init(site);

                                site.getPage().addSelectionListener(selectionListener);

                                BadWordCheckerPlugin

                                              .getDefault()

                                              .getPreferenceStore()

                                              .addPropertyChangeListener(preferenceListener);

                  }

                  /* (non-Javadoc)

                  * Method declared on IWorkbenchPart.

                  */

                  public void dispose() {

                                // remove ourselves as a selection listener

                                getSite().getPage().removeSelectionListener(selectionListener);

                                //and no longer listen to the preference store

                                BadWordCheckerPlugin

                                              .getDefault()

                                              .getPreferenceStore()

                                              .removePropertyChangeListener(preferenceListener);

                                if (foreground != null)

                                              foreground.dispose();

                                // run super.

                                super.dispose();

                  }

    }

  • 相关阅读:
    关于图片去水印和转载
    多叉树(森林)转二叉树
    [置顶] 读入优化&输出优化
    【NOI OJ】1816 拨钟问题
    Splay树
    【AVL】宠物收养所
    【树状数组】Stars
    对拍
    使用Mybatis进行多表联查操作
    搜索框自动提示
  • 原文地址:https://www.cnblogs.com/drawwindows/p/2109191.html
Copyright © 2011-2022 走看看