Window size

Hi all,

What is the best way to build a reasonable window size in a dialog?

I have this code:

VerticalLayout layout = new VerticalLayout();
setContent(layout);
layout.setSizeFull();
layout.setSpacing(true);
layout.setMargin(true);

HorizontalLayout actions = new HorizontalLayout();
actions.setSpacing(true);
actions.addComponent(add);
actions.addComponent(new Button("Close", this));

FormLayout form = new FormLayout();
form.addComponent(levelChooser);
form.addComponent(select);

addComponent(form);
addComponent(addNewCompetence);
addComponent(actions);

I have tried calling setSizeFull() and setSizeUndefined on layout and form, but no matter what I do, it seems a bit wrong.

Is there no justDoIt() function?

Bo.

It’s a little hard for me to say what you are actually trying to achieve, but you mentioned a window before showing the code.

Are you doing a pop-up window? Then you’ve to put the size also to the window itself, not only the contained layout.


window.setWidth("50%");
window.setHeight("50%");
window.center();
layout.setSizeFull();

of course you can also change that to window.setSizeFull(); but a full window size popup is maybe not optimal.

Did I understand correctly what you are trying to do?

Yes, it is indeed a dialog I’m opening. Sorry, I should have said that.

But I’m surprised I have to set something like 50% size or other. Why isn’t there a function to calculate the necessary size and just set that? It’s what you need for dialogs all the time.

Bo.

This is actually a bit tricky. See this example:


  Window dialog = new Window("Dialog");
        dialog.center();
        dialog.getContent().setSizeUndefined();
        mainWindow.addWindow(dialog);
        dialog.addComponent(new TextField("Field 1"));
        dialog.addComponent(new TextField("Field 2"));
        dialog.addComponent(new Button("Ok"));

The trick here is to say setSizeUndefined() for the layout inside the window. The default width for this layout is 100% - which results to width that is in proportion to window caption.

This is actually so confusing that we should do something about it:
http://dev.vaadin.com/ticket/3067

That works, as long as the content of the window is not relative. If I recall correctly the label width is 100% by default, so having a message popup could still cause some problems.

True… It is impossible (for a window) to measure the size of the contents of all the contents are 100% (of the window) wide.

When you think about it, it is totally logical. Unfortunately - when you do not think about it - it is totally strange. It would be great to have justDoIt() method, but defining “It” is really hard.

It isn’t impossible to create a justDoItNow() function that looks at how big the window should be right now with the current set of contents. If a component changes content, then I can call the function again. But right now there is no way at all to do it.

As I wrote earlier, I did already try the setSizeUndefined() trick. But this doesn’t work either. Looks like the problem is that I have a window caption that is too large, and the trick doesn’t take this into account.

Bo.

well you can’t calculate a size of just a relative width object. How wide should a label be? Should it all be in one row and be a mile long or should it wrap the text at some point? At which point? That can’t really be calculated.

I guess the automatic function will not put the window smaller than the window caption (it would cut the text which is not nice).

Tested the original code. Adding the setSizeUndefined() made it work:


    public void init() {
        Window mainWindow = new Window("Dialogtest Application");
        setMainWindow(mainWindow);

        Window dialog = new Window("Dialog");
        dialog.center();
        mainWindow.addWindow(dialog);

        VerticalLayout layout = new VerticalLayout();
        dialog.setContent(layout);
        layout.setSizeFull();
        layout.setSpacing(true);
        layout.setMargin(true);

        HorizontalLayout actions = new HorizontalLayout();
        actions.setSpacing(true);
        actions.addComponent(new Button("Add"));
        actions.addComponent(new Button("Close"));

        FormLayout form = new FormLayout();
        form.addComponent(new Select("Foo"));
        form.addComponent(new Select("Bar"));

        dialog.addComponent(form);
        dialog.addComponent(new Select("Competence"));
        dialog.addComponent(actions);

        // Added this line and the layout started working
        layout.setSizeUndefined();

    }

Sorry to revive such an old post, but I recently started having this problem.

Using above test code, I found that the dialog displays normally on Chrome 19, but it gets truncated on both IE 9 and Firefox 13. I don’t have a copy of Safari to test on, but I suspect that it is a problem with non-Webkit browsers.

Is this a known issue or is it a regression?

Thanks!

The key is to have setSizeUndefined on all the things. the subwindow, the layout of the subwindow and the layouts inside of it. Try putting it in a few places to make sure that nothing has setSizeFull or percentage height.

If nothing helps, make a simple test case in a stand alone application and create a bug ticket over at
dev.vaadin.com
with the test case. I think however that there would have been a lot more talk about this if a bug like this existed.

With which Vaadin versions do you see the problem?

If it is a regression (as it may well be), please
create a bug report
with a link to this thread and if possible a simplified version of a test program that allows reproducing the issue.

Thanks for the quick response!

It turns out that setting sizeUndefined on the form itself (and not just the form’s layout) was required to get it to work on FF and IE. Interestingly, this was not required for Chrome. I was originally testing against 6.7.9, but I saw that 6.8.0 was available, so I am now testing against that.

A new issue has cropped up, sadly. Using my test code, the dialog is being properly centered on FF and Chrome, but it appears in the top-left on IE.


public static class Data
{
    private String id;
    private String name;
    private String description;

    public Data(String id, String name, String description) {
        this.id = id;
        this.name = name;
        this.description = description;
    }

    public String getId() { return id; }
    public void setId(String id) { this.id = id; }

    public String getName() { return name; }
    public void setName(String name) { this.name = name; }

    public String getDescription() { return description; }
    public void setDescription(String description) { this.description = description; }
}
...
    public void init()
    {
        final Window mainWindow = new Window("Dialogtest Application");
        setMainWindow( mainWindow );

        final Window dialog = new Window("Dialog");
        mainWindow.addWindow(dialog);

        VerticalLayout layout = new VerticalLayout();
        dialog.setContent(layout);
        layout.setSizeUndefined();
        layout.setMargin(true);
        layout.setSpacing(true);

        BeanItem<Data> podItem = new BeanItem<>(new Data("100", "DataRecord-100", "This is a cool piece of data"));
        final Form podForm = new Form();
        podForm.setWriteThrough(false);
        podForm.setInvalidCommitted(false);
        podForm.setItemDataSource(podItem);
        podForm.setFormFieldFactory(new DefaultFieldFactory() {
            @Override
            public Field createField(Item item, Object propertyId, Component uiContext) {
                Field field = super.createField(item, propertyId, uiContext);
                if( "id".equals(propertyId)) {
                    TextField textField = (TextField) field;
                    textField.setRequired(true);
                    textField.setRequiredError("Must have ID");
                } else if( "name".equals(propertyId)) {
                    TextField textField = (TextField) field;
                    textField.setRequired(true);
                    textField.setRequiredError("Must have name");
                } else if( "description".equals(propertyId)) {
                    TextField textField = (TextField) field;
                    textField.setRequired(false);
                }
                return field;
            }
        });
        podForm.setVisibleItemProperties(Arrays.asList(new String[]{"id", "name", "description"}));
        podForm.getLayout().setSizeUndefined();
        podForm.setSizeUndefined(); // this was the critical for it to work on IE and FF

        Button okButton = new Button("Save");
        Button cancelButton = new Button("Cancel");

        HorizontalLayout buttonBar = new HorizontalLayout();
        buttonBar.addComponent(okButton);
        buttonBar.addComponent(cancelButton);
        buttonBar.setSpacing(true);
        buttonBar.setSizeUndefined();

        dialog.addComponent(podForm);
        dialog.addComponent(buttonBar);

        dialog.setSizeUndefined();
        dialog.center(); // centers correctly in FF and Chrome; IE displays top-left.
        dialog.setModal(true);
        dialog.setResizable(false);
        dialog.setDraggable(false);
        dialog.setClosable(false);
    }

I think setModal(true) centers it also. Just to figure this out, try to remove either center() or setModal(true) and test in IE, then add it back and remove the other one.

SetModal does center the window, but the plot thickens.

After a bit more testing, it appears that the centering of the sub window depends on which browser I test with first after a deployment. I have all three browsers (IE, FF, and Chrome) on the same test machine. When I deploy my vaadin app, I then hit it with one of the browsers. I wasn’t following a strict ordering of which browser I tried first, second, and third, but I did have a routine (Chrome was usually first, followed by FF and then IE). As I started adding and moving “center()” calls around, I accidentally tried FF first, and it was centered correctly, as was FF which I checked secondly. Thinking that I had fixed it with my code changes, I then checked Chrome and found that Chrome was now displaying the sub window in the top left.

Intrigued, I tried redeploying without a code change, and this time I checked Chrome first and it displayed centered, but then when I checked IE it was being displayed top-left. Does vaadin store any information in session about which browser is being used that would be misinterpreted between browser types? Since for my application, the user will only ever be using a single browser to access the app, I think I am ok moving forward, but it is curious that the first browser used displays normally, but subsequent browsers have the problem.

Haven’t heard of anything similar before. The sessions should not share anything with each others automatically. Do you share components or something between users, static fields etc.?

Hey, this post is 3 years old but I have some trouble with window sizing when the contents of the window is smaller than the caption of the window itself.

Normally settting the window size to undefined srinks the window size to its contents, but when the caption of the window itself is bigger in width than the content of the window then we have a problem…

Is there a relatively easy way to something like

if window.caption.width > window.content.width
     window.width = window.caption.width
else
     window.width = window.content.width

Thanks!

Hi David,

No, you cannot get the actual width on the server-side. Not sure about the exact solution, but are you sure you want the caption to be truncated when it’s long?

I think the algorithm I put in there does show what I want, but I was missunderstood probably.

I’ll give you an example.
In screen shot 1 ( 82KB ) it shows a window well arranged where it’s content is bigger than the caption of the window.
In screen shot 2 ( 67KB ) it shows a window where the caption gets truncated because the content of the window is smaller than the size of the caption of the window.
In screen shot 3 ( 134KB ) I manually adjusted the width of the window (with the mouse) of the last screenshot, so that the caption of the window itself shows in full and not truncated.

So what I wanted to know is if there is an easy way to know in any given window (say a modal window on top of a UI) a way to know if the width of the window caption is bigger than the content of the window. Because in the former the caption gets automatically truncated if it’s contents are smaller than required to display the full caption, and in the latter I can no longer use window.setSizeUndefined() because I need to know the width of the caption of the window to size the window properly so that, and here the code again…

if window.caption.width > window.content.width
     window.width = window.caption.width
else
     window.width = window.content.width // or just set window.setSizeUndefined() wich will do the same...

Thanks!

17817.png
17818.png
17819.png