开发者

SWT Menu causes the layout to clip

开发者 https://www.devze.com 2023-04-12 22:20 出处:网络
I\'m trying SWT for the first time, and I can\'t figure out how to use a Menu bar along with any space-filling layout. The Composite\'s layout is calculated without taking the Menu into account, so th

I'm trying SWT for the first time, and I can't figure out how to use a Menu bar along with any space-filling layout. The Composite's layout is calculated without taking the Menu into account, so that once the Menu is added the bottom of the layout gets clipped.

Amazingly, when the user resizes, the Menu is taken into account and the layout is fine. But I can't figure out how to fix it programmatically; shell.layout(true,true), shell.setSize(250,250), shell.pack() don't fix the problem.

SWT Menu causes the layout to clip

SWT Menu causes the layout to clip

package com.appspot.htmldoodads.pdfstuffs;

import org.eclipse.swt.SWT;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Menu;
import org.eclipse.swt.widgets.MenuItem;
import org.eclipse.swt.widgets.Shell;

public class MenuLayout {
    public static void main(String[] argv) {
        final Display display = new Display();
        final Shell shell = new Shell(display);

        GridLayout shellLayo开发者_如何学运维ut = new GridLayout();
        shell.setLayout(shellLayout);

        // Add a menu bar with File -> Open...
        Menu bar = new Menu(shell, SWT.BAR);
        shell.setMenuBar(bar);
        MenuItem fileItem = new MenuItem(bar, SWT.CASCADE);
        fileItem.setText("&File");
        Menu subMenu = new Menu(shell, SWT.DROP_DOWN);
        fileItem.setMenu(subMenu);
        MenuItem openItem = new MenuItem(subMenu, SWT.CASCADE);
        openItem.setText("&Open...");

        // Add a button that fills the space.
        Button big = new Button(shell, SWT.PUSH);
        big.setText("Fill.");
        GridData bigLayoutData = new GridData(GridData.FILL, GridData.FILL, true, true);
        big.setLayoutData(bigLayoutData);

        // Add a button that doesn't fill space.
        new Button(shell, SWT.PUSH).setText("Regular");

        shell.layout(true, true);
        shell.setSize(250,250);
        shell.open();
        while ( ! shell.isDisposed ()) {
            if (!display.readAndDispatch())
                display.sleep();
        }
        display.dispose();
    }
}


I figured out a solution just as I was finishing the question. I needed to call shell.layout() after shell.open(), so that GTK can render the Menu before SWT calculates the available space for layout.


Adding to yonran's answer:

If using JFace and and a subclass of ApplicationWindow as your main entry point, shell.open() is performed for you. So instead of using the JFace blocking applicationWindow.open() method call, you have to use the typical SWT loop.

JFace Before (Didn't work, and had clipping issue described in question):

public static void main(String[] args) {
    ApplicationWindow window = new MyApplicationWindow("My Window Title");
    window.setBlockOnOpen(true);
    window.open();
    Display.getCurrent().dispose()
}

JFace After (Correctly displays without any clipping):

public static void main(String[] args) {
    ApplicationWindow window = new MyApplicationWindow("My Window Title");
    window.open();

    Shell shell = window.getShell();
    shell.layout(true, true);
    while (!shell.isDisposed())
        if (!Display.getCurrent().readAndDispatch())
            Display.getCurrent().sleep();
    Display.getCurrent().dispose();
}
0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号