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 package info.magnolia.ui.vaadin.gwt.client.magnoliashell.shell;
35
36 import info.magnolia.ui.vaadin.gwt.client.dialog.connector.OverlayConnector;
37 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.ActivateAppEvent;
38 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.AppRequestedEvent;
39 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.CurrentAppCloseEvent;
40 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.FullScreenEvent;
41 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.HideShellAppsEvent;
42 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.HideShellAppsRequestedEvent;
43 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.ShellAppRequestedEvent;
44 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.ShellAppStartedEvent;
45 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.ShellAppStartingEvent;
46 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.event.ShellAppsHiddenEvent;
47 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.shell.rpc.ShellClientRpc;
48 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.shell.rpc.ShellServerRpc;
49 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.shellmessage.ShellMessageWidget.MessageType;
50 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.viewport.connector.ViewportConnector;
51 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.viewport.widget.AppsViewportWidget;
52 import info.magnolia.ui.vaadin.gwt.client.magnoliashell.viewport.widget.ViewportWidget;
53 import info.magnolia.ui.vaadin.gwt.client.shared.magnoliashell.Fragment;
54 import info.magnolia.ui.vaadin.gwt.client.shared.magnoliashell.ShellAppType;
55 import info.magnolia.ui.vaadin.gwt.client.shared.magnoliashell.ViewportType;
56 import info.magnolia.ui.vaadin.magnoliashell.MagnoliaShell;
57
58 import java.util.Iterator;
59 import java.util.List;
60 import java.util.Map.Entry;
61
62 import com.google.gwt.core.client.Scheduler;
63 import com.google.gwt.event.logical.shared.ValueChangeEvent;
64 import com.google.gwt.event.logical.shared.ValueChangeHandler;
65 import com.google.gwt.user.client.History;
66 import com.google.gwt.user.client.ui.Widget;
67 import com.google.web.bindery.event.shared.EventBus;
68 import com.google.web.bindery.event.shared.SimpleEventBus;
69 import com.vaadin.client.ComponentConnector;
70 import com.vaadin.client.ConnectorHierarchyChangeEvent;
71 import com.vaadin.client.Util;
72 import com.vaadin.client.communication.RpcProxy;
73 import com.vaadin.client.communication.StateChangeEvent;
74 import com.vaadin.client.communication.StateChangeEvent.StateChangeHandler;
75 import com.vaadin.client.ui.AbstractLayoutConnector;
76 import com.vaadin.client.ui.layout.ElementResizeEvent;
77 import com.vaadin.client.ui.layout.ElementResizeListener;
78 import com.vaadin.client.ui.nativebutton.NativeButtonConnector;
79 import com.vaadin.shared.ui.Connect;
80
81
82
83
84 @Connect(MagnoliaShell.class)
85 public class MagnoliaShellConnector extends AbstractLayoutConnector implements MagnoliaShellView.Presenter {
86
87 private ShellServerRpc rpc = RpcProxy.create(ShellServerRpc.class, this);
88 private MagnoliaShellView view;
89 private EventBus eventBus = new SimpleEventBus();
90 private Fragment lastHandledFragment;
91 private boolean isHistoryInitialized = false;
92
93 @Override
94 protected void init() {
95 super.init();
96 addStateChangeHandler(new StateChangeHandler() {
97 @Override
98 public void onStateChanged(StateChangeEvent event) {
99 MagnoliaShellState state = getState();
100 Iterator<Entry<ShellAppType, Integer>> it = state.indications.entrySet().iterator();
101 while (it.hasNext()) {
102 final Entry<ShellAppType, Integer> entry = it.next();
103 view.setShellAppIndication(entry.getKey(), entry.getValue());
104 }
105 }
106 });
107
108 addStateChangeHandler("uriFragment", new StateChangeHandler() {
109 @Override
110 public void onStateChanged(StateChangeEvent stateChangeEvent) {
111 Fragment f = getState().uriFragment;
112 if (f != null) {
113 History.newItem(f.toFragment(), !f.isSameApp(lastHandledFragment));
114 }
115 }
116 });
117
118 registerRpc(ShellClientRpc.class, new ShellClientRpc() {
119 @Override
120 public void showMessage(String type, String topic, String msg, String id) {
121 view.showMessage(MessageType.valueOf(type), topic, msg, id);
122 }
123
124 @Override
125 public void hideAllMessages() {
126 view.hideAllMessages();
127 }
128
129 @Override
130 public void setFullScreen(boolean isFullScreen) {
131 MagnoliaShellConnector.this.doFullScreen(isFullScreen);
132 }
133 });
134
135 getLayoutManager().addElementResizeListener(getWidget().getElement(), new ElementResizeListener() {
136 @Override
137 public void onElementResize(ElementResizeEvent e) {
138 view.updateShellDivet();
139 }
140 });
141
142 eventBus.addHandler(CurrentAppCloseEvent.TYPE, new CurrentAppCloseEvent.Handler() {
143 @Override
144 public void onViewportClose(CurrentAppCloseEvent event) {
145 closeCurrentApp();
146 }
147 });
148
149 eventBus.addHandler(ShellAppStartingEvent.TYPE, new ShellAppStartingEvent.Handler() {
150 @Override
151 public void onShellAppStarting(ShellAppStartingEvent event) {
152 view.onShellAppStarting(event.getType());
153 }
154 });
155
156 eventBus.addHandler(ShellAppStartedEvent.TYPE, new ShellAppStartedEvent.Handler() {
157 @Override
158 public void onShellAppStarted(ShellAppStartedEvent event) {
159 lastHandledFragment = Fragment.fromString("shell:" + event.getType().name().toLowerCase() + ":" + "");
160 activateShellApp(lastHandledFragment);
161 }
162 });
163
164 eventBus.addHandler(HideShellAppsRequestedEvent.TYPE, new HideShellAppsRequestedEvent.Handler() {
165 @Override
166 public void onHideShellAppsRequest(HideShellAppsRequestedEvent event) {
167 onHideShellAppsRequested();
168 }
169 });
170
171 eventBus.addHandler(ShellAppsHiddenEvent.TYPE, new ShellAppsHiddenEvent.Handler() {
172 @Override
173 public void onShellAppsHidden(ShellAppsHiddenEvent event) {
174 rpc.stopCurrentShellApp();
175 }
176 });
177
178 eventBus.addHandler(ActivateAppEvent.TYPE, new ActivateAppEvent.Handler() {
179 @Override
180 public void onActivateApp(ActivateAppEvent event) {
181 rpc.activateApp(Fragment.fromString("app:" + event.getName()));
182 }
183 });
184
185 History.addValueChangeHandler(new ValueChangeHandler<String>() {
186 @Override
187 public void onValueChange(ValueChangeEvent<String> event) {
188 Fragment newFragment = Fragment.fromString(event.getValue());
189 if (newFragment.isShellApp()) {
190 showShellApp(newFragment.resolveShellAppType());
191 } else {
192 loadApp(newFragment.getAppName());
193 rpc.activateApp(newFragment);
194 }
195 lastHandledFragment = newFragment;
196 }
197 });
198 }
199
200 @Override
201 public void activateShellApp(Fragment f) {
202 rpc.activateShellApp(f);
203 }
204
205 @Override
206 public void closeCurrentApp() {
207 rpc.stopCurrentApp();
208 }
209
210 @Override
211 public void removeMessage(String id) {
212 rpc.removeMessage(id);
213 }
214
215 @Override
216 public void loadApp(String appName) {
217 view.onAppStarting();
218 eventBus.fireEvent(new AppRequestedEvent(appName));
219 }
220
221 @Override
222 public void showShellApp(ShellAppType shellAppType) {
223 eventBus.fireEvent(new ShellAppRequestedEvent(shellAppType));
224 }
225
226 private void doFullScreen(boolean isFullScreen) {
227 eventBus.fireEvent(new FullScreenEvent(isFullScreen));
228 }
229
230 @Override
231 public void onHideShellAppsRequested() {
232 ViewportWidget viewportWidget =
233 (ViewportWidget) ((ComponentConnector)getState().viewports.get(ViewportType.APP)).getWidget();
234 AppsViewportWidget appViewportWidget =
235 (AppsViewportWidget) ((ComponentConnector)getState().viewports.get(ViewportType.APP)).getWidget();
236
237
238 Widget currentApp = appViewportWidget.getCurrentApp();
239 if (currentApp != null) {
240 view.onAppStarting();
241 eventBus.fireEvent(new HideShellAppsEvent());
242 } else {
243 showShellApp(ShellAppType.APPLAUNCHER);
244 }
245 }
246
247 @Override
248 public void updateCaption(ComponentConnector connector) {}
249
250 @Override
251 public void onConnectorHierarchyChange(ConnectorHierarchyChangeEvent event) {
252 List<ComponentConnector> children = getChildComponents();
253 for (ComponentConnector connector : children) {
254 if (connector instanceof ViewportConnector) {
255 final ViewportConnector vc = (ViewportConnector) connector;
256 view.updateViewport(vc.getWidget(), vc.getType());
257 vc.setEventBus(eventBus);
258 } else if (connector instanceof OverlayConnector) {
259 if (!view.hasOverlay(connector.getWidget())) {
260 final OverlayConnector oc = (OverlayConnector) connector;
261 ComponentConnector overlayParent = (ComponentConnector) oc.getState().overlayParent;
262 Widget parentWidget = overlayParent.getWidget();
263 view.openOverlayOnWidget(oc.getWidget(), parentWidget);
264 }
265 } else if (connector instanceof NativeButtonConnector) {
266 view.setUserMenu(connector.getWidget());
267 }
268 }
269
270 List<ComponentConnector> oldChildren = event.getOldChildren();
271 oldChildren.removeAll(children);
272 for (ComponentConnector cc : oldChildren) {
273 cc.getWidget().removeFromParent();
274 }
275 }
276
277 @Override
278 protected Widget createWidget() {
279 this.view = new MagnoliaShellViewImpl();
280 this.view.setPresenter(this);
281 return view.asWidget();
282 }
283
284 @Override
285 public MagnoliaShellState getState() {
286 return (MagnoliaShellState) super.getState();
287 }
288
289 @Override
290 public void updateViewportLayout(ViewportWidget activeViewport) {
291 getLayoutManager().setNeedsMeasure(Util.findConnectorFor(activeViewport));
292 getLayoutManager().layoutNow();
293 }
294
295
296 @Override
297 public void initHistory() {
298 Scheduler.get().scheduleDeferred(new Scheduler.ScheduledCommand() {
299 @Override
300 public void execute() {
301 if (!isHistoryInitialized) {
302 isHistoryInitialized = true;
303 History.fireCurrentHistoryState();
304 }
305 }
306 });
307 }
308
309 }