summaryrefslogtreecommitdiffstats
path: root/documentation/layout/layout-sub-window.asciidoc
blob: ed75b800aa2cce5a60ef2584e0aa479282ab9761 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
---
title: Sub-Windows
order: 7
layout: page
---

[[layout.sub-window]]
= Sub-Windows

ifdef::web[]
[.sampler]
image:{live-demo-image}[alt="Live Demo", link="http://demo.vaadin.com/sampler/#ui/structure/window"]
endif::web[]

__Sub-windows__ are floating panels within a native browser window. Unlike
native browser windows, sub-windows are managed by the client-side runtime of
Vaadin using HTML features. Vaadin allows opening, closing, resizing, maximizing
and restoring sub-windows, as well as scrolling the window content.

[[figure.layout.sub-window.basic]]
.A Sub-Window
image::img/subwindow-basic.png[width=50%, scaledwidth=70%]

Sub-windows are typically used for __Dialog Windows__ and __Multiple Document
Interface__ applications. Sub-windows are by default not modal; you can set them
modal as described in <<layout.sub-window.modal>>.

[[layout.sub-window.openclose]]
== Opening and Closing Sub-Windows

You can open a new sub-window by creating a new [classname]#Window# object and
adding it to the UI with [methodname]#addWindow()#, typically in some event
listener. A sub-window needs a content component, which is typically a layout.

In the following, we display a sub-window immediately when a UI opens:


[source, java]
----
public static class SubWindowUI extends UI {
    @Override
    protected void init(VaadinRequest request) {
        // Some other UI content
        setContent(new Label("Here's my UI"));

        // Create a sub-window and set the content
        Window subWindow = new Window("Sub-window");
        VerticalLayout subContent = new VerticalLayout();
        subContent.setMargin(true);
        subWindow.setContent(subContent);

        // Put some components in it
        subContent.addComponent(new Label("Meatball sub"));
        subContent.addComponent(new Button("Awlright"));

        // Center it in the browser window
        subWindow.center();

        // Open it in the UI
        addWindow(subWindow);
    }
}
----

The result was shown in <<figure.layout.sub-window.basic>>. Sub-windows by
default have undefined size in both dimensions, so they will shrink to fit the
content.

The user can close a sub-window by clicking the close button in the upper-right
corner of the window. The button is controlled by the __closable__ property, so
you can disable it with [methodname]#setClosable(false)#. You can also use keyboard
shortcuts for closing a sub-window.  You can manage the shortcuts with the [methodname]#addCloseShortcut()#,
[methodname]#removeCloseShortcut()#, [methodname]#removeAllCloseShortcuts()#,
[methodname]#hasCloseShortcut()#, and [methodname]#getCloseShortcuts()# methods.

You close a sub-window also programmatically by calling the
[methodname]#close()# for the sub-window, typically in a click listener for an
[guibutton]#OK# or [guibutton]#Cancel# button. You can also call
[methodname]#removeWindow()# for the current [classname]#UI#.

ifdef::web[]
[[layout.sub-window.openclose.example]]
=== Sub-Window Management

Usually, you would extend the [classname]#Window# class for your specific
sub-window as follows:


[source, java]
----
// Define a sub-window by inheritance
class MySub extends Window {
    public MySub() {
        super("Subs on Sale"); // Set window caption
        center();

        // Some basic content for the window
        VerticalLayout content = new VerticalLayout();
        content.addComponent(new Label("Just say it's OK!"));
        content.setMargin(true);
        setContent(content);

        // Disable the close button
        setClosable(false);

        // Trivial logic for closing the sub-window
        Button ok = new Button("OK");
        ok.addClickListener(new ClickListener() {
            public void buttonClick(ClickEvent event) {
                close(); // Close the sub-window
            }
        });
        content.addComponent(ok);
    }
}
----

You could open the window as follows:


[source, java]
----
// Some UI logic to open the sub-window
final Button open = new Button("Open Sub-Window");
open.addClickListener(new ClickListener() {
    public void buttonClick(ClickEvent event) {
        MySub sub = new MySub();

        // Add it to the root component
        UI.getCurrent().addWindow(sub);
    }
});
----

endif::web[]


[[layout.sub-window.position]]
== Window Positioning

When created, a sub-window will have an undefined default size and position. You
can specify the size of a window with [methodname]#setHeight()# and
[methodname]#setWidth()# methods. You can set the position of the window with
[methodname]#setPositionX()# and [methodname]#setPositionY()# methods.


[source, java]
----
// Create a new sub-window
mywindow = new Window("My Dialog");

// Set window size.
mywindow.setHeight("200px");
mywindow.setWidth("400px");

// Set window position.
mywindow.setPositionX(200);
mywindow.setPositionY(50);

UI.getCurrent().addWindow(mywindow);
----


[[layout.sub-window.scrolling]]
== Scrolling Sub-Window Content

((("scroll bars", id="term.layout.sub-window.scrolling.scrollbars", range="startofrange")))


If a sub-window has a fixed or percentual size and its content becomes too big
to fit in the content area, a scroll bar will appear for the particular
direction. On the other hand, if the sub-window has undefined size in the
direction, it will fit the size of the content and never get a scroll bar.
Scroll bars in sub-windows are handled with regular HTML features, namely
[literal]#++overflow: auto++# property in CSS.
((("overflow")))

((("[interfacename]#Scrollable#")))
As [classname]#Window# extends [classname]#Panel#, windows are also
[interfacename]#Scrollable#. Note that the interface defines __programmatic
scrolling__, not scrolling by the user. Please see
<<dummy/../../../framework/layout/layout-panel#layout.panel,"Panel">>.

(((range="endofrange", startref="term.layout.sub-window.scrolling.scrollbars")))

[[layout.sub-window.modal]]
== Modal Sub-Windows

A modal window is a sub-window that prevents interaction with the other UI.
Dialog windows, as illustrated in <<figure.layout.sub-window.modal>>, are
typical cases of modal windows. The advantage of modal windows is limiting the
scope of user interaction to a sub-task, so changes in application state are
more limited. The disadvantage of modal windows is that they can restrict
workflow too much.

You can make a sub-window modal with [methodname]#setModal(true)#.

[[figure.layout.sub-window.modal]]
.Modal Sub-Window
image::img/subwindow-modal.png[width=70%, scaledwidth=100%]

Depending on the theme, the parent window may be grayed when the modal window is
open.


[WARNING]
.Security Warning
====
Modality of child windows is purely a client-side feature and can be
circumvented with client-side attack code. You should not trust in the modality
of child windows in security-critical situations such as login windows.

====