2014-09-29 184 views
2

我正在爲我的RCP應用程序創建自定義工具欄。Eclipse RCP應用程序自定義工具欄

enter image description here

  1. 如圖所示我想有一個下拉框,與其他三個文本框。這些基本上是輸入框並且是相互依賴的。現在這些箱子中的每一個都在不同的類別中。我想把它們放在一個類中,這樣更容易爲對方創建監聽器。

    protected void fillCoolBar(ICoolBarManager coolBar) { 
    
    IToolBarManager toolbar = new ToolBarManager(coolBar.getStyle()); 
    coolBar.add(toolbar);  
    
    Toolbar extraToolBar = new Toolbar("Toolbar"); 
    toolbar.add(extraToolBar); 
    toolbar.add(new Separator()); 
    
    toolbar.add(new MyCombo("Demo Combo box")); 
    toolbar.add(new Separator()); 
    
    toolbar.add(new IPaddress("Ip")); 
    toolbar.add(new Separator()); 
    
    toolbar.add(new Mask("Mask")); 
    toolbar.add(new Separator()); 
    
    toolbar.add(new Count("Count")); 
    
    } 
    
    public class IPaddress extends ControlContribution { 
    
    Text textBox; 
    
    
    public IPaddress(String id) { 
        super(id); 
        // TODO Auto-generated constructor stub 
    } 
    
    @Override 
    protected Control createControl(Composite parent) { 
    textBox = new Text(parent, SWT.MULTI | SWT.BORDER | SWT.WRAP); 
    textBox.setLayoutData(new GridData(GridData.FILL_BOTH)); 
    textBox.addModifyListener(new ModifyListener(){ 
        public void modifyText(ModifyEvent event) { 
         Text text = (Text) event.widget; 
         System.out.println(text.getText()); 
        } 
    }); 
    return textBox; 
    } 
    
    } 
    
  2. 因此,我想創建一個新的自定義工具欄會我想要的一切,然後將它的功能固守原來的。但不知何故,它只在左邊顯示一個空欄。

    protected Control createControl(Composite parent) { 
    toolBar = new ToolBar(parent, SWT.FLAT |SWT.BORDER); 
    
    Device dev = toolBar.getDisplay(); 
    
    try { 
        newi = new Image(dev, "C:\\Users\\RahmanAs\\ChipcoachWorkspace\\ChipCoach\\icons\\FileClose.png"); 
        opei = new Image(dev, "C:\\Users\\RahmanAs\\ChipcoachWorkspace\\ChipCoach\\icons\\FileOpen.png"); 
    
    
    } catch (Exception e) { 
        System.out.println("Cannot load images"); 
        System.out.println(e.getMessage()); 
        System.exit(1); 
    } 
    
    
    ToolItem item0 = new ToolItem (toolBar, SWT.PUSH); 
    item0.setImage(newi); 
    item0.setText("Hello"); 
    
    ToolItem item1 = new ToolItem(toolBar, SWT.PUSH); 
    item1.setText("Push"); 
    
    ToolItem item2 = new ToolItem(toolBar, SWT.PUSH); 
    item2.setText("Pull"); 
    
    
    return toolBar; 
    
    
    } 
    
  3. 我也有運行按鈕,我使用Vogella的教程在插件中創建了按鈕。但我無法以這種方式編排他們的展示位置。 (例如,如果我希望他們在開始。)有沒有一種方法來創建它們以編程方式?

回答

2

我認爲你最左邊的ToolBar是空的原因是佈局問題。在我的代碼下面,當我沒有任何按鈕位於定製ToolBar但仍在主要ToolBar中時,我有類似的「空」ToolBar問題。在「foo」和「bar」按鈕中添加固定佈局問題,但我無法找出正確的呼叫layout()pack()來修復它。我認爲這可能與the bug here有關。

我開始創建類似的ToolBar,並圍繞「RCP郵件模板」插件項目構建,您可以從「新插件項目」嚮導創建項目。

爲了解決您的第一兩個問題,我的例子RCP捆在3包(我叫我的項目 「com.bar.foo」):

  1. com.bar.foo.actions - 包含擴展ContributionControl幷包裝ComboText小部件的類。這些與數據模型無關,只是擔心創建小部件。
  2. com.bar.foo.model - 包含數據模型。我在這裏用一個IP,掩碼,網關和一兩個有用的方法構建了一個簡單的模型。
  3. com.bar.foo.toolBar - 這些類通過org.eclipse.ui.menus擴展點插入主UI ToolBar。他們將數據模型鏈接到第一個包中的ContributionControls。這裏最重要的課程是ToolBarContribution,它有效地集中了所有聽衆。這使您更容易將小部件的偵聽器鏈接到相同的模型。

這裏是爲ToolBarContribution源(注意,是因爲它掛鉤了聽衆模型提供它自己的ToolBar到UI解決你的前兩個問題):

package com.bar.foo.toolBar; 

import org.eclipse.jface.action.Action; 
import org.eclipse.jface.action.ToolBarManager; 
import org.eclipse.swt.SWT; 
import org.eclipse.swt.events.SelectionAdapter; 
import org.eclipse.swt.events.SelectionEvent; 
import org.eclipse.swt.events.SelectionListener; 
import org.eclipse.swt.widgets.Combo; 
import org.eclipse.swt.widgets.Composite; 
import org.eclipse.swt.widgets.Control; 
import org.eclipse.swt.widgets.ToolBar; 
import org.eclipse.ui.menus.WorkbenchWindowControlContribution; 

import com.bar.foo.actions.ComboContributionItem; 
import com.bar.foo.actions.TextContributionItem; 
import com.bar.foo.model.NetworkConfig; 

public class ToolBarContribution extends WorkbenchWindowControlContribution { 

    // Our data model. 
    private NetworkConfig configuration = new NetworkConfig(); 

    // Each of these corresponds to a widget in the ToolBar. 
    private Action scanAction; 
    private ComboContributionItem sourceCombo; 
    private TextContributionItem ipText; 
    private TextContributionItem maskText; 
    private TextContributionItem gatewayText; 

    @Override 
    protected Control createControl(Composite parent) { 

     setupContributionItems(); 

     // Let's not get our hands messy with SWT... add IActions or 
     // IContributionItems to a ToolBarManager and let the ToolBarManager 
     // create the SWT ToolBar. 
     ToolBarManager manager = new ToolBarManager(); 
     manager.add(scanAction); 
     manager.add(sourceCombo); 
     manager.add(ipText); 
     manager.add(maskText); 
     manager.add(gatewayText); 

     ToolBar toolBar = manager.createControl(parent); 

     // Highlight the ToolBar in red. 
     toolBar.setBackground(parent.getDisplay().getSystemColor(SWT.COLOR_RED)); 

     return toolBar; 
    } 

    private void setupContributionItems() { 
     scanAction = new Action("Scan Host") { 
      @Override 
      public void run() { 
       System.out.println("Scanning..."); 
       String host = sourceCombo.getComboControl().getText(); 
       configuration.scanHost(host); 
       System.out.println("Scanned!"); 
       refreshTexts(); 
      } 
     }; 
     scanAction.setToolTipText("Scans the host for a configuration."); 

     final SelectionListener comboListener = new SelectionAdapter() { 
      @Override 
      public void widgetSelected(SelectionEvent e) { 
       ipText.getTextControl().setText(""); 
       maskText.getTextControl().setText(""); 
       gatewayText.getTextControl().setText(""); 
      } 
     }; 
     sourceCombo = new ComboContributionItem("sourceCombo") { 
      @Override 
      public Control createControl(Composite parent) { 
       // Let ComboContributionItem create the initial control. 
       Control control = super.createControl(parent); 
       // Now customize the Combo widget. 
       Combo combo = getComboControl(); 
       combo.setItems(configuration.getAvailableHosts()); 
       combo.addSelectionListener(comboListener); 
       // Return the default control. 
       return control; 
      } 
     }; 

     ipText = new TextContributionItem("ipText", SWT.BORDER | SWT.SINGLE 
       | SWT.READ_ONLY); 
     maskText = new TextContributionItem("maskText"); 
     gatewayText = new TextContributionItem("gatewayText"); 
    } 

    private void refreshTexts() { 
     ipText.getTextControl().setText(configuration.getIP()); 
     maskText.getTextControl().setText(configuration.getMask()); 
     gatewayText.getTextControl().setText(configuration.getGateway()); 
    } 
} 

在除了這個ToolBar,我在主要UI中有兩個單獨的按鈕,一個在之前,一個在定製ToolBar之後。他們的來源位於com.bar.foo.toolBar包中。這是第一個命令:

package com.bar.foo.toolBar; 

import org.eclipse.core.commands.AbstractHandler; 
import org.eclipse.core.commands.ExecutionEvent; 
import org.eclipse.core.commands.ExecutionException; 

public class FooHandler extends AbstractHandler { 
    @Override 
    public Object execute(ExecutionEvent event) throws ExecutionException { 
     System.out.println("foo"); 
     return null; 
    } 
} 

這裏是第二個:

package com.bar.foo.toolBar; 

import org.eclipse.core.commands.AbstractHandler; 
import org.eclipse.core.commands.ExecutionEvent; 
import org.eclipse.core.commands.ExecutionException; 

public class BarHandler extends AbstractHandler { 
    @Override 
    public Object execute(ExecutionEvent event) throws ExecutionException { 
     System.out.println("bar"); 
     return null; 
    } 
} 

因爲我不知道太多關於你的數據,我要創建我自己的模型。在包com.bar.foo.model的模型只是一個類:

package com.bar.foo.model; 

public class NetworkConfig { 

    private String ip = ""; 
    private String mask = ""; 
    private String gateway = ""; 

    public String[] getAvailableHosts() { 
     return new String[] { "fooHost" }; 
    } 

    public void scanHost(String host) { 
     if ("fooHost".equals(host)) { 
      ip = "192.168.1.2"; 
      mask = "255.255.255.0"; 
      gateway = "192.168.1.1";  
     } else { 
      ip = ""; 
      mask = ""; 
      gateway = ""; 
     } 
    } 

    public String getIP() { 
     return ip; 
    } 
    public String getMask() { 
     return mask; 
    } 
    public String getGateway() { 
     return gateway; 
    } 
} 

現在對於包含進去定製ToolBarControlContributions的com.bar.foo.actions包。請注意,這兩個類別都不與型號有關,它們可以在您的產品的其他地方重新使用。

第一堂課只包裝Combo小部件。通過覆蓋controlCreated(Combo)方法可以初始定製小部件。我在ToolBarContribution類中使用它來添加SelectionListener並設置Combo的項目。下面是類:

package com.bar.foo.actions; 

import org.eclipse.jface.action.ControlContribution; 
import org.eclipse.swt.SWT; 
import org.eclipse.swt.widgets.Combo; 
import org.eclipse.swt.widgets.Composite; 
import org.eclipse.swt.widgets.Control; 

public class ComboContributionItem extends ControlContribution { 

    private Combo combo; 

    public ComboContributionItem(String id) { 
     super(id); 
    } 

    @Override 
    protected Control createControl(Composite parent) { 
     combo = new Combo(parent, SWT.READ_ONLY | SWT.V_SCROLL | SWT.H_SCROLL); 
     return combo; 
    } 

    @Override 
    public int computeWidth(Control control) { 
     // The widget is now 100 pixels. You can new GC gc = new GC(control) and 
     // use the gc.stringExtent(String) method to help compute a more dynamic 
     // width. 
     return 100; 
    } 

    public Combo getComboControl() { 
     return combo; 
    } 
} 

此包中的其他類包裝一個Text部件:

package com.bar.foo.actions; 

import org.eclipse.jface.action.ControlContribution; 
import org.eclipse.swt.SWT; 
import org.eclipse.swt.widgets.Composite; 
import org.eclipse.swt.widgets.Control; 
import org.eclipse.swt.widgets.Text; 

public class TextContributionItem extends ControlContribution { 

    private final int style; 
    private Text text; 

    public TextContributionItem(String id) { 
     this(id, SWT.BORDER | SWT.SINGLE); 
    } 

    public TextContributionItem(String id, int style) { 
     super(id); 
     this.style = style; 
    } 

    @Override 
    protected Control createControl(Composite parent) { 
     text = new Text(parent, style); 
     return text; 
    } 

    @Override 
    public int computeWidth(Control control) { 
     return 100; 
    } 

    public Text getTextControl() { 
     return text; 
    } 
} 

我不這樣做,但如果你需要進一步定製Text小部件爲您ToolBar,就像我在初始化ComboContributionItem時一樣,您可以覆蓋createControl(Composite)方法。

現在最後一件事:我使用擴展來定製ToolBar。但是,ToolBarContribution使用的邏輯適用於您的fillCoolBar(ICoolBarManager)方法或createControl(Composite)方法,具體取決於您最終希望修改哪一個ToolBar

對我來說,這裏就是我添加到插件的plugin.xml結束:

<extension 
     point="org.eclipse.ui.menus"> 
    <menuContribution 
     locationURI="toolbar:org.eclipse.ui.main.toolbar"> 
     <toolbar 
      id="com.bar.foo.toolbar"> 
     <command 
       commandId="com.bar.foo.commands.foo" 
       label="Foo" 
       style="push"> 
     </command> 
     <control 
       class="com.bar.foo.toolBar.ToolBarContribution"> 
     </control> 
     <command 
       commandId="com.bar.foo.commands.bar" 
       label="Bar" 
       style="push"> 
     </command> 
     </toolbar> 
    </menuContribution> 
</extension> 
<extension 
     point="org.eclipse.ui.commands"> 
    <command 
     id="com.bar.foo.commands.foo" 
     name="Foo"> 
    </command> 
    <command 
     id="com.bar.foo.commands.bar" 
     name="Bar"> 
    </command> 
</extension> 
<extension 
     point="org.eclipse.ui.handlers"> 
    <handler 
     class="com.bar.foo.toolBar.FooHandler" 
     commandId="com.bar.foo.commands.foo"> 
    </handler> 
    <handler 
     class="com.bar.foo.toolBar.BarHandler" 
     commandId="com.bar.foo.commands.bar"> 
    </handler> 
</extension> 

的命令迷上了,這樣還有的定製ToolBarBarHandler按鈕之前FooHandler按鈕定製後ToolBar。這些命令在xml中的指定順序將反映在應用程序中。同樣,項目添加到定製ToolBar的順序也會反映在您的產品中。

關於展示位置的另一個注意事項:可以通過在locationURI的查詢中設置展示位置,例如toolbar:org.eclipse.ui.main.toolbar?after=additions,讓menuContributions顯示在不同的位置。 「之前」是另一個放置關鍵字,如「之後」。更多的例子可以在in this Eclipse help doc找到。

+1

歡迎來到SO!如果您在回答之前需要澄清一下,請留下評論(下次,當您擁有足夠的「聲譽」時)現在,您爲什麼不直接展示如何做,並添加一些示例代碼? – GameDroids 2014-10-09 18:19:27