2012-08-25 21 views
4

我有一個Composite。 在SWT孩子們補充說,兒童,無父母:Java SWT - 偵聽是否將新的子項添加到Composite中?

Composite parent = new Composite(shell, SWT.none); 
Composite child = new Composite(parent, SWT.none); 

這意味着,父母,我不知道,這裏面以何種方式以及何時孩子們加入到他們的父母。

問題:

裏面的父母,我需要知道,當有新的孩子加入到父母的。 有沒有辦法註冊onChildAddListener或任何add()方法來覆蓋?

+0

要「激活」狀態分配到的第一個項目,這是加入。爲我的應用程序自己的邏輯 – Skip

+0

然後在[this](http://stackoverflow.com/questions/9517634/how-to-be-notified-that-a-composites-child-received-lost-focus)中的答案似乎是唯一的方法做到這一點。基本上,聽'SWT.Resize'事件... – Baz

+0

順便說一句:如果您自己添加組件,爲什麼不直接手動將第一個設置爲「Active」? – Baz

回答

4

添加自定義MyComposite並創建自定義ChildEvent以及ChildEventListener接口的唯一方法。 MyComposite能夠註冊ChildEvent的收聽者,並在創建子女Composite時觸發此事件。

import org.eclipse.swt.SWT; 
import org.eclipse.swt.events.TypedEvent; 
import org.eclipse.swt.internal.SWTEventListener; 
import org.eclipse.swt.widgets.*; 

/* 
* This example demonstrates the minimum amount of code required 
* to open an SWT Shell and process the events. 
*/ 
public class HelloWorld1 { 

public static void main (String [] args) { 
    Display display = new Display(); 
    Shell shell = new HelloWorld1().open (display); 
    while (!shell.isDisposed()) { 
     if (!display.readAndDispatch()) display.sleep(); 
    } 
    display.dispose(); 
} 

public Shell open (Display display) { 
    Shell shell = new Shell (display); 
    MyComposite parent = new MyComposite(shell, SWT.NONE); 
    parent.addChildEventListener(new ChildEventListener() { 

     @Override 
     public void add(ChildEvent e) { 
      System.out.println("Child added."); 

     } 
    }); 
    MyComposite child = new MyComposite(parent, SWT.NONE); 

// shell.open(); 
    return shell; 
} 
} 

class MyComposite extends Composite { 

    ChildEventListener[] childEventListeners = new ChildEventListener[0]; 

    public MyComposite(Composite parent, int style) { 
     super(parent, style); 
     if (parent instanceof MyComposite){ 
      ((MyComposite)parent).fireChildEvent(new ChildEvent(this)); 
     } 
    } 
    public void addChildEventListener (ChildEventListener listener) { 
     checkWidget(); 
     if (listener == null) SWT.error (SWT.ERROR_NULL_ARGUMENT); 
     ChildEventListener[] newChildEventListeners = new ChildEventListener[childEventListeners.length + 1]; 
     System.arraycopy(childEventListeners, 0, newChildEventListeners, 0, childEventListeners.length); 
     childEventListeners = newChildEventListeners; 
     childEventListeners[childEventListeners.length - 1] = listener; 
    } 
    public void removeChildEventListener (ChildEventListener listener) { 
     if (childEventListeners.length == 0) return; 
     int index = -1; 
     for (int i = 0; i < childEventListeners.length; i++) { 
      if (listener == childEventListeners[i]){ 
       index = i; 
       break; 
      } 
     } 
     if (index == -1) return; 
     if (childEventListeners.length == 1) { 
      childEventListeners = new ChildEventListener[0]; 
      return; 
     } 
     ChildEventListener[] newChildEventListeners = new ChildEventListener[childEventListeners.length - 1]; 
     System.arraycopy (childEventListeners, 0, newChildEventListeners, 0, index); 
     System.arraycopy (childEventListeners, index + 1, newChildEventListeners, index, childEventListeners.length - index - 1); 
     childEventListeners = newChildEventListeners; 
    } 
    public void fireChildEvent(ChildEvent event){ 
     for (int i = 0; i < childEventListeners.length; i++) { 
      childEventListeners[i].add (event); 
     } 

    } 
} 

interface ChildEventListener extends SWTEventListener { 
    public void add(ChildEvent e); 
} 

class ChildEvent extends TypedEvent { 

    public ChildEvent(Widget widget) { 
     super(widget); 
     // TODO Auto-generated constructor stub 
    } 

} 
+1

Thnx,就是這樣! – Skip

+1

+1 Nice work ... – Baz

+1

嗨,我來自一年後。我想謝謝你!這很有幫助。 – GGrec

1

爲此,我想知道孩子另外的目的 - 是layoing出來的孩子 (添加LayoutDataGridData)當孩子被添加到一個孩子,這是與特定的佈局奠定了(例如GridLayout)。

因爲它是不可能在另外的佈局兒童 - 檢查其佈局上的每個部件調整大小:

/* 
    * To make the forms fill the group - laying out the children is necessary. 
    * Unfortunately it is not possible to listen for children addition, in order to layout the children addition automatically. 
    * This means that the user will have to remember to layout the children, which is a nogo. 
    * 
    * Solution: 
    * istead of adding right layout on child addition - check if there are new children every time the widget is resized. 
    * if a widget without layoutData is found (new child not layed out) - add a layout 
    */ 
    this.addControlListener(new ControlAdapter() { 
     @Override 
     public void controlResized(ControlEvent e) { 
      layoutChildren(); 
     } 
    }); 
} 
private void layoutChildren(){ 
    for(Control child:getChildren()){ 
     if(child.getLayoutData() == null){ 
      child.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false, 1, 1)); 
     } 
    } 
} 

public void addToGroup(Composite child){ 
    child.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false, 1, 1)); 
} 
相關問題