Search code examples
javaeclipsescrollswtscrolledcomposite

Eclipse SWT ScrolledComposite refuses to scroll


I'm developing a plugin for eclipse and I'm struggling to use ScrolledComposite as well as making it take up the remaining space.

The parent layout is a 2-column Grid:

@Override
public void createPartControl(Composite parent) {
    parent.setLayout(new GridLayout(2, false));
    // other views etc
}

The ScrolledComposite is created like so (slightly abbreviated):

private void fillScroll() {
    if (scroll != null) {
      scroll.dispose();
    }
    scroll = new ScrolledComposite(parent, SWT.V_SCROLL | SWT.H_SCROLL | SWT.BORDER);

    GridData gd = new GridData();
    gd.horizontalSpan = 2;
    scroll.setLayoutData(gd);

    Composite innerContainer = new Composite(scroll, 0);
    innerContainer.setLayout(new GridLayout(1, false));

    // for loop that adds widgets to innerContainer

    scroll.setExpandHorizontal(true);
    scroll.setExpandVertical(true);
    scroll.setContent(innerContainer);
    scroll.setSize(innerContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT));

    parent.layout(true);
}

Picture of resulting layout

The list of questions are the widgets added in the for loop and are contained by innerContainer.

Expectation: Since innerContainer is too large to fit in the parent, there should be scroll bars.

What actually happens: There are no scroll bars.

How do I fix this problem?


Solution

    1. The GridData on the ScrolledComposite needs to have grabExcessVerticalSpace set to true. I suggest you to use the extended constructor in order to clearly define how it should be displayed, for example:

      GridData gd = new GridData(SWT.FILL, SWT.FILL, true, true, 2, 1);
      
    2. Option A: change scroll.setSize to scroll.setMinSize:

      scroll.setMinSize(innerContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT));
      

      or, Option B: remove scroll.setExpandHorizontal and scroll.setExpandVertical and change scroll.setSize to innerContainer.setSize:

      innerContainer.setSize(innerContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT));