Link19
Link19

Reputation: 606

JFace Dialog Layout Issues, Widgets drawn outside of the bounds of the window

I'm trying to lay out a Dialogue box with a scrolling panel on the left and a canvas on the right that fills the available space but isn't covered up by the button bar. The problem I'm having can be seen in my example is that the composites seem to think they have an unlimited amount of space to draw themselves in and I can't understand how this is supposed to work with anything.

import org.eclipse.jface.dialogs.Dialog;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.ScrolledComposite;
import org.eclipse.swt.events.PaintEvent;
import org.eclipse.swt.events.PaintListener;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Canvas;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Shell;

public class FMLDialog extends Dialog
{   
    public FMLDialog(Shell parentShell)
    {
        super(parentShell);
    }


    @Override
    protected void configureShell(Shell shell)
    {
        super.configureShell(shell);
        shell.setSize(new Point(700,500));
        shell.setText("FML");
    }   

    @Override
    public Control createDialogArea(final Composite comp)
    {

        Composite content = (Composite) super.createDialogArea(comp);
        Composite parent = new Composite(content, SWT.NONE);        

        GridLayout gridLayout1 = new GridLayout(1, false);
        gridLayout1.verticalSpacing=10;
        GridLayout gridLayout2 = new GridLayout(2, false);
        parent.setLayout(gridLayout2);
        parent.setLayoutData(new GridData(SWT.FILL, SWT.BEGINNING, true, false));           

        final ScrolledComposite scroll = new ScrolledComposite(parent, SWT.V_SCROLL);
        scroll.setExpandHorizontal(true);
        scroll.setExpandVertical(true);

        Composite optionsPanel = new Composite(scroll, SWT.BORDER);

        optionsPanel.setSize(optionsPanel.computeSize(SWT.DEFAULT, SWT.DEFAULT));
        optionsPanel.setLayout(gridLayout1);
        scroll.setContent(optionsPanel);

        for (int i = 0; i < 200; i++) {
            new Label(optionsPanel, SWT.NONE).setText("this is item " + i);
        }

        scroll.setSize(optionsPanel.computeSize(SWT.DEFAULT, SWT.DEFAULT));

        final Canvas c = new Canvas(parent, SWT.BORDER);
        c.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
        c.addPaintListener(new PaintListener() {

            @Override
            public void paintControl(PaintEvent e) {
                Point size = c.getSize();
                e.gc.drawText("Width: " + size.x + "\nHeight: " + size.y, 5, 5);
                e.gc.drawOval(2, 2, size.x - 4, size.y - 4);
            }
        });

        return content;     

    }

    public static void main(String[] args) {
        Display d = new Display();
        Shell s = new Shell();

        FMLDialog fml = new FMLDialog(s);
        fml.open();
    }

}

Upvotes: 0

Views: 289

Answers (1)

Baz
Baz

Reputation: 36894

There were a couple of issues here starting with not calling ScrolledComposite#setMinSize() and some minor issues with GridData and Layouts.

Here is a modified version of your code that works:

public class FMLDialog extends Dialog
{
    public FMLDialog(Shell parentShell)
    {
        super(parentShell);
    }

    @Override
    protected void configureShell(Shell shell)
    {
        super.configureShell(shell);
        shell.setSize(new Point(700, 500));
        shell.setText("FML");
    }

    @Override
    public Control createDialogArea(final Composite comp)
    {
        Composite content = (Composite) super.createDialogArea(comp);
        content.setLayout(new GridLayout(2, false));
        content.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));

        final ScrolledComposite scroll = new ScrolledComposite(content, SWT.V_SCROLL);
        scroll.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
        scroll.setExpandHorizontal(true);
        scroll.setExpandVertical(true);

        Composite optionsPanel = new Composite(scroll, SWT.BORDER);
        optionsPanel.setLayout(new FillLayout(SWT.VERTICAL));
        optionsPanel.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));

        for (int i = 0; i < 200; i++)
        {
            new Label(optionsPanel, SWT.NONE).setText("this is item " + i);
        }

        scroll.setContent(optionsPanel);
        scroll.setMinSize(optionsPanel.computeSize(SWT.DEFAULT, SWT.DEFAULT));

        final Canvas c = new Canvas(content, SWT.BORDER);
        c.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
        c.addPaintListener(new PaintListener()
        {
            @Override
            public void paintControl(PaintEvent e)
            {
                Point size = c.getSize();
                e.gc.drawText("Width: " + size.x + "\nHeight: " + size.y, 5, 5);
                e.gc.drawOval(2, 2, size.x - 4, size.y - 4);
            }
        });

        return content;
    }

    public static void main(String[] args)
    {
        Display d = new Display();
        Shell s = new Shell();

        FMLDialog fml = new FMLDialog(s);
        fml.open();
    }
}

Upvotes: 2

Related Questions