2013-06-21 40 views
2

我的應用程序有兩個孩子的SashForm。當窗口大小調整時,我希望左邊的孩子保持相同的大小。我想要Eclipse對Package Explorer和主編輯器做同樣的事情。當您調整窗口大小時,只有文本編輯器會更改大小。但是,Package Explorer仍然可以通過窗框調整大小。等寬SashForm

我嘗試使用以下

sashForm.addControlListener(new ControlAdapter() { 
    @Override 
    public void controlResized(ControlEvent e) { 
     int width = sashForm.getClientArea().width; 
     int[] weights = sashForm.getWeights(); 
     weights[1] = width - weights[0]; 
     sashForm.setWeights(weights); 
    } 
}); 

問題是左側尺寸的寬度或者收縮以0或膨脹太多。它看起來像權重更新之前,這是所謂的或什麼的。

如果我設置權重[0]等於某個常數,它就是我想要的。

回答

2

這是我能想出的最佳解決方案。

import org.eclipse.swt.SWT; 
import org.eclipse.swt.custom.SashForm; 
import org.eclipse.swt.layout.FillLayout; 
import org.eclipse.swt.widgets.Button; 
import org.eclipse.swt.widgets.Display; 
import org.eclipse.swt.widgets.Event; 
import org.eclipse.swt.widgets.Listener; 
import org.eclipse.swt.widgets.Shell; 

public class Main { 
private static int leftWidth, oldWeight; 

public static void main(String[] args) { 
    Display display = new Display(); 
    final Shell shell = new Shell(display); 
    shell.setText("StackOverflow"); 
    shell.setLayout(new FillLayout()); 
    shell.setSize(600, 400); 

    final SashForm form = new SashForm(shell, SWT.HORIZONTAL); 

    final Button button = new Button(form, SWT.PUSH); 
    button.setText("Left"); 

    button.addListener(SWT.Resize, new Listener() { 
     @Override 
     public void handleEvent(Event arg0) { 
      int[] weights = form.getWeights(); 
      // oldWeights is used to distinguish between a window resize and 
      // a sash move 
      if (oldWeight != weights[0]) { 
       System.out.println("Weights changed!"); 
       oldWeight = weights[0]; 
       leftWidth = (int) Math.round((double) form.getClientArea().width 
         * (double) weights[0] 
         /(double) (weights[0] + weights[1])); 
      } 
     } 
    }); 

    Button buttonR = new Button(form, SWT.PUSH); 
    buttonR.setText("Right"); 

    form.setWeights(new int[] { 200, 800 }); 
    leftWidth = 200; 

    form.addListener(SWT.Resize, new Listener() { 
     @Override 
     public void handleEvent(Event arg0) { 
      int width = form.getClientArea().width; 
      int[] weights = form.getWeights(); 

      double perChange = (double) leftWidth/(double) width; 

      weights[0] = (int) (perChange * 1000.0); 
      weights[1] = 1000 - weights[0]; 

      // oldWeights must be set before form.setWeights 
      oldWeight = weights[0]; 
      form.setWeights(weights); 
     } 
    }); 

    shell.open(); 
    while (!shell.isDisposed()) { 
     if (!display.readAndDispatch()) 
      display.sleep(); 
    } 
    display.dispose(); 
} 

窗框四周跳1px的左右,當調整窗口大小時由於四捨五入的問題,但似乎做我想做的。

這是一個非常hacky的解決方案,我想知道是否有更好的解決方案。如果您使窗口小於左按鈕,它也會崩潰,但這很容易修復。

2

我設法得到一個示例運行,應該給你一個想法如何解決你的問題。問題是,SashForm使用權重而不是像素。因此,您必須根據父級大小計算左側孩子必須佔用的百分比,並將其餘分配給正確的孩子。

在我的代碼示例中,您可以指定左側子項的寬度,併爲右側子項設置最小尺寸,這樣SashForm將始終顯示兩者。

private static final int MIN_WIDTH_LEFT = 100; 
private static final int MIN_WIDTH_RIGHT = 50; 

public static void main(String[] args) 
{ 
    Display display = new Display(); 
    final Shell shell = new Shell(display); 
    shell.setText("StackOverflow"); 
    shell.setLayout(new FillLayout()); 

    final SashForm form = new SashForm(shell, SWT.HORIZONTAL); 

    Button button = new Button(form, SWT.PUSH); 
    button.setText("Left"); 

    Button buttonR = new Button(form, SWT.PUSH); 
    buttonR.setText("Right"); 

    form.setWeights(new int[] {1, 2}); 

    shell.addListener(SWT.Resize, new Listener() 
    { 
     @Override 
     public void handleEvent(Event arg0) 
     { 
      int width = shell.getClientArea().width; 
      int[] weights = form.getWeights(); 

      if(width >= MIN_WIDTH_LEFT + MIN_WIDTH_RIGHT) 
      { 
       weights[0] = 1000000 * MIN_WIDTH_LEFT/width; 
       weights[1] = 1000000 - weights[0]; 
      } 
      else 
      { 
       weights[0] = 1000000 * MIN_WIDTH_LEFT/(MIN_WIDTH_LEFT + MIN_WIDTH_RIGHT); 
       weights[1] = 1000000 * MIN_WIDTH_RIGHT/(MIN_WIDTH_LEFT + MIN_WIDTH_RIGHT); 
      } 

      System.out.println(width + " " + Arrays.toString(weights)); 

      form.setWeights(weights); 
     } 
    }); 

    shell.pack(); 

    shell.setSize(600, 400); 
    shell.open(); 
    while (!shell.isDisposed()) 
    { 
     if (!display.readAndDispatch()) 
      display.sleep(); 
    } 
    display.dispose(); 
} 

這是什麼樣子:

啓動:

enter image description here

調整後:

enter image description here

當減小窗口的大小,直到爲時已小,以顯示兩個米inimal尺寸:

enter image description here

正如你在這種情況下看,左子的最小尺寸被忽略仍然能夠顯示這兩個孩子的。

+0

這大致上是我想要的,但如果您手動調整「左」大於預設寬度,並調整窗口大小,它會跳回到預設寬度。我希望用戶設置寬度保持不變。換句話說,當手動移動窗扇時,我需要調整MIN_WIDTH_LEFT。 – EmbMicro

+0

@EmbMicro好吧,沒有人會阻止你這麼做;)只需從'MIN_WIDTH_LEFT'字段中刪除'final'關鍵字並更改其值。 – Baz

+0

雖然它不工作。我試圖在調整大小時將偵聽器添加到「左側」,並且在窗口移動時它會變小。 'button.addListener(SWT.Resize,新監聽器(){ \t @覆蓋 \t公共無效的handleEvent(事件爲arg0){ \t \t MIN_WIDTH_LEFT = button.getBounds()寬度; \t} });' – EmbMicro

0

必須重寫SashForm才能獲得此行爲。 new SashForm(Composite parent, int style)是舊行爲; new SashForm(Composite parent, int style, false)使用像素指定的寬度/高度。

不能與SashForm的兩個以上的複合孩子,古怪的行爲測試,如果使用新的行爲時,不要setLength,但不會打破SashForm

的現有用途

例如:

public static void main(String[] args) 
{ 
Display display = new Display(); 
final Shell shell = new Shell(display); 
shell.setText("StackOverflow"); 
shell.setLayout(new FillLayout()); 
final SashForm form = new SashForm(shell, SWT.HORIZONTAL); 
Button button = new Button(form, SWT.PUSH); 
button.setText("Left"); 
Button buttonR = new Button(form, SWT.PUSH); 
buttonR.setText("Right"); 
form.setLengths(new int[] { 250, 25 }); 
shell.pack(); 
shell.setSize(600, 400); 
shell.open(); 
while (!shell.isDisposed()) 
{ 
    if (!display.readAndDispatch()) 
     display.sleep(); 
} 
display.dispose(); 
} 

第一個按鈕將默認爲250個像素,第二餘量殼

SashForm.java:

import org.eclipse.swt.*; 
import org.eclipse.swt.widgets.*; 
import org.eclipse.swt.graphics.*; 

public class SashForm extends Composite { 

    /** 
    * The width of all sashes in the form. 
    */ 
    public int SASH_WIDTH = 3; 

    int sashStyle; 
    final private boolean weighted; 
    Sash[] sashes = new Sash[0]; 
    // Remember background and foreground 
    // colors to determine whether to set 
    // sashes to the default color (null) or 
    // a specific color 
    Color background = null; 
    Color foreground = null; 
    Control[] controls = new Control[0]; 
    Control maxControl = null; 
    Listener sashListener; 
    static final int DRAG_MINIMUM = 20; 

public SashForm(Composite parent, int style) { 
    super(parent, checkStyle(style)); 
    super.setLayout(new SashFormLayout()); 
    sashStyle = ((style & SWT.VERTICAL) != 0) ? SWT.HORIZONTAL : SWT.VERTICAL; 
    if ((style & SWT.BORDER) != 0) sashStyle |= SWT.BORDER; 
    if ((style & SWT.SMOOTH) != 0) sashStyle |= SWT.SMOOTH; 
    sashListener = new Listener() { 
     public void handleEvent(Event e) { 
      onDragSash(e); 
     } 
    }; 
    weighted = true; 
} 
public SashForm(Composite parent, int style, boolean weighted) { 
    super(parent, checkStyle(style)); 
    super.setLayout(new SashFormLayout()); 
    sashStyle = ((style & SWT.VERTICAL) != 0) ? SWT.HORIZONTAL : SWT.VERTICAL; 
    if ((style & SWT.BORDER) != 0) sashStyle |= SWT.BORDER; 
    if ((style & SWT.SMOOTH) != 0) sashStyle |= SWT.SMOOTH; 
    sashListener = new Listener() { 
     public void handleEvent(Event e) { 
      onDragSash(e); 
     } 
    }; 
    this.weighted = weighted; 
} 
static int checkStyle (int style) { 
    int mask = SWT.BORDER | SWT.LEFT_TO_RIGHT | SWT.RIGHT_TO_LEFT; 
    return style & mask; 
} 
Sash createSash() { 
    Sash sash = new Sash(this, sashStyle); 
    sash.setBackground(background); 
    sash.setForeground(foreground); 
    sash.setToolTipText(getToolTipText()); 
    sash.addListener(SWT.Selection, sashListener); 
    return sash; 
} 

@Override 
public int getOrientation() { 
    //checkWidget(); 
    return (sashStyle & SWT.VERTICAL) != 0 ? SWT.HORIZONTAL : SWT.VERTICAL; 
} 
/** 
* Returns the width of the sashes when the controls in the SashForm are 
* laid out. 
* 
* @return the width of the sashes 
* 
* @exception SWTException <ul> 
* <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> 
* <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> 
* </ul> 
* 
* @since 3.4 
*/ 
public int getSashWidth() { 
    checkWidget(); 
    return SASH_WIDTH; 
} 
@Override 
public int getStyle() { 
    int style = super.getStyle(); 
    style |= getOrientation() == SWT.VERTICAL ? SWT.VERTICAL : SWT.HORIZONTAL; 
    if ((sashStyle & SWT.SMOOTH) != 0) style |= SWT.SMOOTH; 
    return style; 
} 
/** 
* Answer the control that currently is maximized in the SashForm. 
* This value may be null. 
* 
* @return the control that currently is maximized or null 
*/ 
public Control getMaximizedControl(){ 
    //checkWidget(); 
    return this.maxControl; 
} 

public int[] getWeights() { 
    checkWidget(); 
    Control[] cArray = getControls(false); 
    int[] ratios = new int[cArray.length]; 
    for (int i = 0; i < cArray.length; i++) { 
     Object data = cArray[i].getLayoutData(); 
     if (data != null && data instanceof SashFormData) { 
      ratios[i] = (int)(((SashFormData)data).weight * 1000 >> 16); 
     } else { 
      ratios[i] = 200; 
     } 
    } 
    return ratios; 
} 
Control[] getControls(boolean onlyVisible) { 
    Control[] children = getChildren(); 
    Control[] result = new Control[0]; 
    for (int i = 0; i < children.length; i++) { 
     if (children[i] instanceof Sash) continue; 
     if (onlyVisible && !children[i].getVisible()) continue; 

     Control[] newResult = new Control[result.length + 1]; 
     System.arraycopy(result, 0, newResult, 0, result.length); 
     newResult[result.length] = children[i]; 
     result = newResult; 
    } 
    return result; 
} 
boolean getWeighted() { 
    return weighted; 
} 
void onDragSash(Event event) { 
    Sash sash = (Sash)event.widget; 
    int sashIndex = -1; 
    for (int i= 0; i < sashes.length; i++) { 
     if (sashes[i] == sash) { 
      sashIndex = i; 
      break; 
     } 
    } 
    if (sashIndex == -1) return; 

    Control c1 = controls[sashIndex]; 
    Control c2 = controls[sashIndex + 1]; 
    Rectangle b1 = c1.getBounds(); 
    Rectangle b2 = c2.getBounds(); 

    Rectangle sashBounds = sash.getBounds(); 
    Rectangle area = getClientArea(); 
    boolean correction = false; 
    if (getOrientation() == SWT.HORIZONTAL) { 
     correction = b1.width < DRAG_MINIMUM || b2.width < DRAG_MINIMUM; 
     int totalWidth = b2.x + b2.width - b1.x; 
     int shift = event.x - sashBounds.x; 
     b1.width += shift; 
     b2.x += shift; 
     b2.width -= shift; 
     if (b1.width < DRAG_MINIMUM) { 
      b1.width = DRAG_MINIMUM; 
      b2.x = b1.x + b1.width + sashBounds.width; 
      b2.width = totalWidth - b2.x; 
      event.x = b1.x + b1.width; 
      event.doit = false; 
     } 
     if (b2.width < DRAG_MINIMUM) { 
      b1.width = totalWidth - DRAG_MINIMUM - sashBounds.width; 
      b2.x = b1.x + b1.width + sashBounds.width; 
      b2.width = DRAG_MINIMUM; 
      event.x = b1.x + b1.width; 
      event.doit = false; 
     } 
     Object data1 = c1.getLayoutData(); 
     if (data1 == null || !(data1 instanceof SashFormData)) { 
      data1 = new SashFormData(); 
      c1.setLayoutData(data1); 
     } 
     Object data2 = c2.getLayoutData(); 
     if (data2 == null || !(data2 instanceof SashFormData)) { 
      data2 = new SashFormData(); 
      c2.setLayoutData(data2); 
     } 
     ((SashFormData)data1).weight = (((long)b1.width << 16) + area.width - 1)/area.width; 
     ((SashFormData)data1).length = b1.width; 
     ((SashFormData)data2).weight = (((long)b2.width << 16) + area.width - 1)/area.width; 
     ((SashFormData)data2).length = b2.width; 
    } else { 
     correction = b1.height < DRAG_MINIMUM || b2.height < DRAG_MINIMUM; 
     int totalHeight = b2.y + b2.height - b1.y; 
     int shift = event.y - sashBounds.y; 
     b1.height += shift; 
     b2.y += shift; 
     b2.height -= shift; 
     if (b1.height < DRAG_MINIMUM) { 
      b1.height = DRAG_MINIMUM; 
      b2.y = b1.y + b1.height + sashBounds.height; 
      b2.height = totalHeight - b2.y; 
      event.y = b1.y + b1.height; 
      event.doit = false; 
     } 
     if (b2.height < DRAG_MINIMUM) { 
      b1.height = totalHeight - DRAG_MINIMUM - sashBounds.height; 
      b2.y = b1.y + b1.height + sashBounds.height; 
      b2.height = DRAG_MINIMUM; 
      event.y = b1.y + b1.height; 
      event.doit = false; 
     } 
     Object data1 = c1.getLayoutData(); 
     if (data1 == null || !(data1 instanceof SashFormData)) { 
      data1 = new SashFormData(); 
      c1.setLayoutData(data1); 
     } 
     Object data2 = c2.getLayoutData(); 
     if (data2 == null || !(data2 instanceof SashFormData)) { 
      data2 = new SashFormData(); 
      c2.setLayoutData(data2); 
     } 
     ((SashFormData)data1).weight = (((long)b1.height << 16) + area.height - 1)/area.height; 
     ((SashFormData)data2).weight = (((long)b2.height << 16) + area.height - 1)/area.height; 
    } 
    if (correction || (event.doit && event.detail != SWT.DRAG)) { 
     c1.setBounds(b1); 
     sash.setBounds(event.x, event.y, event.width, event.height); 
     c2.setBounds(b2); 
    } 
} 

@Override 
public void setOrientation(int orientation) { 
    checkWidget(); 
    if (orientation == SWT.RIGHT_TO_LEFT || orientation == SWT.LEFT_TO_RIGHT) { 
     super.setOrientation(orientation); 
     return; 
    } 
    if (getOrientation() == orientation) return; 
    if (orientation != SWT.HORIZONTAL && orientation != SWT.VERTICAL) { 
     SWT.error(SWT.ERROR_INVALID_ARGUMENT); 
    } 
    sashStyle &= ~(SWT.HORIZONTAL | SWT.VERTICAL); 
    sashStyle |= orientation == SWT.VERTICAL ? SWT.HORIZONTAL : SWT.VERTICAL; 
    for (int i = 0; i < sashes.length; i++) { 
     sashes[i].dispose(); 
     sashes[i] = createSash(); 
    } 
    layout(false); 
} 
@Override 
public void setBackground (Color color) { 
    super.setBackground(color); 
    background = color; 
    for (int i = 0; i < sashes.length; i++) { 
     sashes[i].setBackground(background); 
    } 
} 
@Override 
public void setForeground (Color color) { 
    super.setForeground(color); 
    foreground = color; 
    for (int i = 0; i < sashes.length; i++) { 
     sashes[i].setForeground(foreground); 
    } 
} 

@Override 
public void setLayout (Layout layout) { 
    checkWidget(); 
    return; 
} 

public void setMaximizedControl(Control control){ 
    checkWidget(); 
    if (control == null) { 
     if (maxControl != null) { 
      this.maxControl = null; 
      layout(false); 
      for (int i= 0; i < sashes.length; i++){ 
       sashes[i].setVisible(true); 
      } 
     } 
     return; 
    } 

    for (int i= 0; i < sashes.length; i++){ 
     sashes[i].setVisible(false); 
    } 
    maxControl = control; 
    layout(false); 
} 

public void setSashWidth(int width) { 
    checkWidget(); 
    if (SASH_WIDTH == width) return; 
    SASH_WIDTH = width; 
    layout(false); 
} 
@Override 
public void setToolTipText(String string) { 
    super.setToolTipText(string); 
    for (int i = 0; i < sashes.length; i++) { 
     sashes[i].setToolTipText(string); 
    } 
} 

public void setWeights(int[] weights) { 
    checkWidget(); 
    Control[] cArray = getControls(false); 
    if (weights == null || weights.length != cArray.length) { 
     SWT.error(SWT.ERROR_INVALID_ARGUMENT); 
    } 

    int total = 0; 
    for (int i = 0; i < weights.length; i++) { 
     if (weights[i] < 0) { 
      SWT.error(SWT.ERROR_INVALID_ARGUMENT); 
     } 
     total += weights[i]; 
    } 
    if (total == 0) { 
     SWT.error(SWT.ERROR_INVALID_ARGUMENT); 
    } 
    for (int i = 0; i < cArray.length; i++) { 
     Object data = cArray[i].getLayoutData(); 
     if (data == null || !(data instanceof SashFormData)) { 
      data = new SashFormData(); 
      cArray[i].setLayoutData(data); 
     } 
     ((SashFormData)data).weight = (((long)weights[i] << 16) + total - 1)/total; 
    } 

    layout(false); 
} 

public void setLengths(int[] lengths) { 
    checkWidget(); 
    Control[] cArray = getControls(false); 
    if (lengths == null || lengths.length != cArray.length) { 
     SWT.error(SWT.ERROR_INVALID_ARGUMENT); 
    } 

    int total = 0; 
    for (int i = 0; i < lengths.length; i++) { 
     if (lengths[i] < 0) { 
      SWT.error(SWT.ERROR_INVALID_ARGUMENT); 
     } 
     total += lengths[i]; 
    } 
    if (total == 0) { 
     SWT.error(SWT.ERROR_INVALID_ARGUMENT); 
    } 
    for (int i = 0; i < cArray.length; i++) { 
     Object data = cArray[i].getLayoutData(); 
     if (data == null || !(data instanceof SashFormData)) { 
      data = new SashFormData(); 
      cArray[i].setLayoutData(data); 
     } 
     ((SashFormData)data).length = lengths[i]; 
    } 

    layout(false); 
} 
} 

SashFormData.java:

class SashFormData { 

    long weight; 
    int length; 

String getName() { 
    String string = getClass().getName(); 
    int index = string.lastIndexOf ('.'); 
    if (index == -1) return string; 
    return string.substring (index + 1, string.length()); 
} 

@Override 
public String toString() { 
    return getName()+" {length="+length+", weight="+weight+"}"; //$NON-NLS-2$ 
} 
} 

SashFormLayout.java:

import org.eclipse.swt.*; 
import org.eclipse.swt.graphics.*; 
import org.eclipse.swt.widgets.*; 

class SashFormLayout extends Layout { 
    @Override 
    protected Point computeSize(Composite composite, int wHint, int hHint, boolean flushCache) { 
     SashForm sashForm = (SashForm)composite; 
     Control[] cArray = sashForm.getControls(true); 
     int width = 0; 
     int height = 0; 
     if (cArray.length == 0) {  
      if (wHint != SWT.DEFAULT) width = wHint; 
      if (hHint != SWT.DEFAULT) height = hHint; 
      return new Point(width, height); 
     } 
     // determine control sizes 
     boolean vertical = sashForm.getOrientation() == SWT.VERTICAL; 

     if (sashForm.getWeighted()) { 
      int maxIndex = 0; 
      int maxValue = 0; 
      for (int i = 0; i < cArray.length; i++) { 
       if (vertical) { 
        Point size = cArray[i].computeSize(wHint, SWT.DEFAULT, flushCache); 
        if (size.y > maxValue) { 
         maxIndex = i; 
         maxValue = size.y; 
        } 
        width = Math.max(width, size.x); 
       } else { 
        Point size = cArray[i].computeSize(SWT.DEFAULT, hHint, flushCache); 
        if (size.x > maxValue) { 
         maxIndex = i; 
         maxValue = size.x; 
        } 
        height = Math.max(height, size.y); 
       } 
      } 
      // get the ratios 
      long[] ratios = new long[cArray.length]; 
      long total = 0; 
      for (int i = 0; i < cArray.length; i++) { 
       Object data = cArray[i].getLayoutData(); 
       if (data != null && data instanceof SashFormData) { 
        ratios[i] = ((SashFormData)data).weight; 
       } else { 
        data = new SashFormData(); 
        cArray[i].setLayoutData(data); 
        ((SashFormData)data).weight = ratios[i] = ((200 << 16) + 999)/1000; 

       } 
       total += ratios[i]; 
      } 
      if (ratios[maxIndex] > 0) { 
       int sashwidth = sashForm.sashes.length > 0 ? sashForm.SASH_WIDTH + sashForm.sashes [0].getBorderWidth() * 2 : sashForm.SASH_WIDTH; 
       if (vertical) { 
        height += (int)(total * maxValue/ratios[maxIndex]) + (cArray.length - 1) * sashwidth; 
       } else { 
        width += (int)(total * maxValue/ratios[maxIndex]) + (cArray.length - 1) * sashwidth; 
       } 
      } 
     } else { 
      int maxIndex = 0; 
      int maxValue = 0; 
      for (int i = 0; i < cArray.length; i++) { 
       if (vertical) { 
        Point size = cArray[i].computeSize(wHint, SWT.DEFAULT, flushCache); 
        if (size.y > maxValue) { 
         maxIndex = i; 
         maxValue = size.y; 
        } 
        width = Math.max(width, size.x); 
       } else { 
        Point size = cArray[i].computeSize(SWT.DEFAULT, hHint, flushCache); 
        if (size.x > maxValue) { 
         maxIndex = i; 
         maxValue = size.x; 
        } 
        height = Math.max(height, size.y); 
       } 
      } 
      // get the lengths 
      int[] lengths = new int[cArray.length]; 
      long total = 0; 
      for (int i = 0; i < cArray.length; i++) { 
       Object data = cArray[i].getLayoutData(); 
       if (data != null && data instanceof SashFormData) { 
        lengths[i] = ((SashFormData)data).length; 
       } else { 
        data = new SashFormData(); 
        cArray[i].setLayoutData(data); 
        ((SashFormData)data).length = sashForm.getOrientation() == SWT.HORIZONTAL ? cArray[i].getSize().x : cArray[i].getSize().y; 
       } 
       total += lengths[i]; 
      } 
      if (lengths[maxIndex] > 0) { 
       int sashwidth = sashForm.sashes.length > 0 ? sashForm.SASH_WIDTH + sashForm.sashes [0].getBorderWidth() * 2 : sashForm.SASH_WIDTH; 
       if (vertical) { 
        height += total + (cArray.length - 1) * sashwidth; 
       } else { 
        width += total + (cArray.length - 1) * sashwidth; 
       } 
      } 
     } 
     width += sashForm.getBorderWidth()*2; 
     height += sashForm.getBorderWidth()*2; 
     if (wHint != SWT.DEFAULT) width = wHint; 
     if (hHint != SWT.DEFAULT) height = hHint; 
     return new Point(width, height); 
    } 

    @Override 
    protected boolean flushCache(Control control) { 
     return true; 
    } 

    @Override 
    protected void layout(Composite composite, boolean flushCache) { 
     SashForm sashForm = (SashForm)composite; 
     Rectangle area = sashForm.getClientArea(); 
     if (area.width <= 1 || area.height <= 1) return; 

     Control[] newControls = sashForm.getControls(true); 
     if (sashForm.controls.length == 0 && newControls.length == 0) return; 
     sashForm.controls = newControls; 

     Control[] controls = sashForm.controls; 

     if (sashForm.maxControl != null && !sashForm.maxControl.isDisposed()) { 
      for (int i= 0; i < controls.length; i++){ 
       if (controls[i] != sashForm.maxControl) { 
        controls[i].setBounds(-200, -200, 0, 0); 
       } else { 
        controls[i].setBounds(area); 
       } 
      } 
      return; 
     } 

     // keep just the right number of sashes 
     if (sashForm.sashes.length < controls.length - 1) { 
      Sash[] newSashes = new Sash[controls.length - 1]; 
      System.arraycopy(sashForm.sashes, 0, newSashes, 0, sashForm.sashes.length); 
      for (int i = sashForm.sashes.length; i < newSashes.length; i++) { 
       newSashes[i] = sashForm.createSash(); 
      } 
      sashForm.sashes = newSashes; 
     } 
     if (sashForm.sashes.length > controls.length - 1) { 
      if (controls.length == 0) { 
       for (int i = 0; i < sashForm.sashes.length; i++) { 
        sashForm.sashes[i].dispose(); 
       } 
       sashForm.sashes = new Sash[0]; 
      } else { 
       Sash[] newSashes = new Sash[controls.length - 1]; 
       System.arraycopy(sashForm.sashes, 0, newSashes, 0, newSashes.length); 
       for (int i = controls.length - 1; i < sashForm.sashes.length; i++) { 
        sashForm.sashes[i].dispose(); 
       } 
       sashForm.sashes = newSashes; 
      } 
     } 
     if (controls.length == 0) return; 
     Sash[] sashes = sashForm.sashes; 

     if (sashForm.getWeighted()) { 
      // get the ratios 
      long[] ratios = new long[controls.length]; 
      long total = 0; 
      for (int i = 0; i < controls.length; i++) { 
       Object data = controls[i].getLayoutData(); 
       if (data != null && data instanceof SashFormData) { 
        ratios[i] = ((SashFormData)data).weight; 
       } else { 
        data = new SashFormData(); 
        controls[i].setLayoutData(data); 
        ((SashFormData)data).weight = ratios[i] = ((200 << 16) + 999)/1000; 

       } 
       total += ratios[i]; 
      } 
      int sashwidth = sashes.length > 0 ? sashForm.SASH_WIDTH + sashes [0].getBorderWidth() * 2 : sashForm.SASH_WIDTH; 
      if (sashForm.getOrientation() == SWT.HORIZONTAL) { 
       int width = (int)(ratios[0] * (area.width - sashes.length * sashwidth)/total); 
       int x = area.x; 
       controls[0].setBounds(x, area.y, width, area.height); 
       x += width; 
       for (int i = 1; i < controls.length - 1; i++) { 
        sashes[i - 1].setBounds(x, area.y, sashwidth, area.height); 
        x += sashwidth; 
        width = (int)(ratios[i] * (area.width - sashes.length * sashwidth)/total); 
        controls[i].setBounds(x, area.y, width, area.height); 
        x += width; 
       } 
       if (controls.length > 1) { 
        sashes[sashes.length - 1].setBounds(x, area.y, sashwidth, area.height); 
        x += sashwidth; 
        width = area.width - x; 
        controls[controls.length - 1].setBounds(x, area.y, width, area.height); 
       } 
      } else { 
       int height = (int)(ratios[0] * (area.height - sashes.length * sashwidth)/total); 
       int y = area.y; 
       controls[0].setBounds(area.x, y, area.width, height); 
       y += height; 
       for (int i = 1; i < controls.length - 1; i++) { 
        sashes[i - 1].setBounds(area.x, y, area.width, sashwidth); 
        y += sashwidth; 
        height = (int)(ratios[i] * (area.height - sashes.length * sashwidth)/total); 
        controls[i].setBounds(area.x, y, area.width, height); 
        y += height; 
       } 
       if (controls.length > 1) { 
        sashes[sashes.length - 1].setBounds(area.x, y, area.width, sashwidth); 
        y += sashwidth; 
        height = area.height - y; 
        controls[controls.length - 1].setBounds(area.x, y, area.width, height); 
       } 

      } 
     } else { 
      // get the lengths 
      int[] lengths = new int[controls.length]; 
      for (int i = 0; i < controls.length; i++) { 
       Object data = controls[i].getLayoutData(); 
       if (data != null && data instanceof SashFormData) { 
        lengths[i] = ((SashFormData)data).length; 
       } else { 
        data = new SashFormData(); 
        controls[i].setLayoutData(data); 
        ((SashFormData)data).length = sashForm.getOrientation() == SWT.HORIZONTAL ? controls[i].getSize().x : controls[i].getSize().y; 
       } 
      } 
      int sashwidth = sashes.length > 0 ? sashForm.SASH_WIDTH + sashes [0].getBorderWidth() * 2 : sashForm.SASH_WIDTH; 
      if (sashForm.getOrientation() == SWT.HORIZONTAL) { 
       int width = lengths[0]; 
       int x = area.x; 
       controls[0].setBounds(x, area.y, width, area.height); 
       x += width; 
       for (int i = 1; i < controls.length - 1; i++) { 
        sashes[i - 1].setBounds(x, area.y, sashwidth, area.height); 
        x += sashwidth; 
        width = lengths[i]; 
        controls[i].setBounds(x, area.y, width, area.height); 
        x += width; 
       } 
       if (controls.length > 1) { 
        sashes[sashes.length - 1].setBounds(x, area.y, sashwidth, area.height); 
        x += sashwidth; 
        width = area.width - x; 
        controls[controls.length - 1].setBounds(x, area.y, width, area.height); 
       } 
      } else { 
       int height = lengths[0]; 
       int y = area.y; 
       controls[0].setBounds(area.x, y, area.width, height); 
       y += height; 
       for (int i = 1; i < controls.length - 1; i++) { 
        sashes[i - 1].setBounds(area.x, y, area.width, sashwidth); 
        y += sashwidth; 
        height = lengths[i]; 
        controls[i].setBounds(area.x, y, area.width, height); 
        y += height; 
       } 
       if (controls.length > 1) { 
        sashes[sashes.length - 1].setBounds(area.x, y, area.width, sashwidth); 
        y += sashwidth; 
        height = area.height - y; 
        controls[controls.length - 1].setBounds(area.x, y, area.width, height); 
       } 

      } 
     } 
    } 
}