Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #include <tools/debug.hxx>
21 :
22 : #include <vcl/svapp.hxx>
23 : #include <vcl/menu.hxx>
24 : #include <vcl/event.hxx>
25 : #include <vcl/syswin.hxx>
26 : #include <vcl/taskpanelist.hxx>
27 : #include <vcl/unowrap.hxx>
28 :
29 : #include <rtl/strbuf.hxx>
30 :
31 : #include <salframe.hxx>
32 : #include <svdata.hxx>
33 : #include <brdwin.hxx>
34 : #include <window.h>
35 :
36 : using namespace ::com::sun::star::uno;
37 : using namespace ::com::sun::star::lang;
38 :
39 : // =======================================================================
40 : class SystemWindow::ImplData
41 : {
42 : public:
43 : ImplData();
44 : ~ImplData();
45 :
46 : TaskPaneList* mpTaskPaneList;
47 : Size maMaxOutSize;
48 : OUString maRepresentedURL;
49 : Link maCloseHdl;
50 : };
51 :
52 3501 : SystemWindow::ImplData::ImplData()
53 : {
54 3501 : mpTaskPaneList = NULL;
55 3501 : maMaxOutSize = Size( SHRT_MAX, SHRT_MAX );
56 3501 : }
57 :
58 6890 : SystemWindow::ImplData::~ImplData()
59 : {
60 3445 : if( mpTaskPaneList )
61 1076 : delete mpTaskPaneList;
62 3445 : }
63 :
64 : // =======================================================================
65 :
66 3501 : SystemWindow::SystemWindow( WindowType nType ) :
67 3501 : Window( nType )
68 : {
69 3501 : mpImplData = new ImplData;
70 3501 : mpWindowImpl->mbSysWin = sal_True;
71 3501 : mpWindowImpl->mnActivateMode = ACTIVATE_MODE_GRABFOCUS;
72 :
73 3501 : mpMenuBar = NULL;
74 3501 : mbPined = sal_False;
75 3501 : mbRollUp = sal_False;
76 3501 : mbRollFunc = sal_False;
77 3501 : mbDockBtn = sal_False;
78 3501 : mbHideBtn = sal_False;
79 3501 : mbSysChild = sal_False;
80 3501 : mnMenuBarMode = MENUBAR_MODE_NORMAL;
81 3501 : mnIcon = 0;
82 3501 : }
83 :
84 6890 : SystemWindow::~SystemWindow()
85 : {
86 3445 : delete mpImplData;
87 3445 : mpImplData = NULL;
88 3445 : }
89 :
90 : // -----------------------------------------------------------------------
91 :
92 32781 : long SystemWindow::Notify( NotifyEvent& rNEvt )
93 : {
94 : // capture KeyEvents for menu handling
95 32781 : if ( rNEvt.GetType() == EVENT_KEYINPUT )
96 : {
97 0 : MenuBar* pMBar = mpMenuBar;
98 0 : if ( !pMBar && ( GetType() == WINDOW_FLOATINGWINDOW ) )
99 : {
100 0 : Window* pWin = ImplGetFrameWindow()->ImplGetWindow();
101 0 : if( pWin && pWin->IsSystemWindow() )
102 0 : pMBar = ((SystemWindow*)pWin)->GetMenuBar();
103 : }
104 0 : if ( pMBar && pMBar->ImplHandleKeyEvent( *rNEvt.GetKeyEvent(), sal_False ) )
105 0 : return sal_True;
106 : }
107 :
108 32781 : return Window::Notify( rNEvt );
109 : }
110 :
111 : // -----------------------------------------------------------------------
112 :
113 10095 : long SystemWindow::PreNotify( NotifyEvent& rNEvt )
114 : {
115 : // capture KeyEvents for taskpane cycling
116 10095 : if ( rNEvt.GetType() == EVENT_KEYINPUT )
117 : {
118 0 : if( rNEvt.GetKeyEvent()->GetKeyCode().GetCode() == KEY_F6 &&
119 0 : rNEvt.GetKeyEvent()->GetKeyCode().IsMod1() &&
120 0 : !rNEvt.GetKeyEvent()->GetKeyCode().IsShift() )
121 : {
122 : // Ctrl-F6 goes directly to the document
123 0 : GrabFocusToDocument();
124 0 : return sal_True;
125 : }
126 : else
127 : {
128 0 : TaskPaneList *pTList = mpImplData->mpTaskPaneList;
129 0 : if( !pTList && ( GetType() == WINDOW_FLOATINGWINDOW ) )
130 : {
131 0 : Window* pWin = ImplGetFrameWindow()->ImplGetWindow();
132 0 : if( pWin && pWin->IsSystemWindow() )
133 0 : pTList = ((SystemWindow*)pWin)->mpImplData->mpTaskPaneList;
134 : }
135 0 : if( !pTList )
136 : {
137 : // search topmost system window which is the one to handle dialog/toolbar cycling
138 0 : SystemWindow *pSysWin = this;
139 0 : Window *pWin = this;
140 0 : while( pWin )
141 : {
142 0 : pWin = pWin->GetParent();
143 0 : if( pWin && pWin->IsSystemWindow() )
144 0 : pSysWin = (SystemWindow*) pWin;
145 : }
146 0 : pTList = pSysWin->mpImplData->mpTaskPaneList;
147 : }
148 0 : if( pTList && pTList->HandleKeyEvent( *rNEvt.GetKeyEvent() ) )
149 0 : return sal_True;
150 : }
151 : }
152 10095 : return Window::PreNotify( rNEvt );
153 : }
154 :
155 : // -----------------------------------------------------------------------
156 :
157 8228 : TaskPaneList* SystemWindow::GetTaskPaneList()
158 : {
159 8228 : if( mpImplData->mpTaskPaneList )
160 7150 : return mpImplData->mpTaskPaneList ;
161 : else
162 : {
163 1078 : mpImplData->mpTaskPaneList = new TaskPaneList();
164 1078 : MenuBar* pMBar = mpMenuBar;
165 1078 : if ( !pMBar && ( GetType() == WINDOW_FLOATINGWINDOW ) )
166 : {
167 0 : Window* pWin = ImplGetFrameWindow()->ImplGetWindow();
168 0 : if ( pWin && pWin->IsSystemWindow() )
169 0 : pMBar = ((SystemWindow*)pWin)->GetMenuBar();
170 : }
171 1078 : if( pMBar )
172 842 : mpImplData->mpTaskPaneList->AddWindow( pMBar->ImplGetWindow() );
173 1078 : return mpImplData->mpTaskPaneList;
174 : }
175 : }
176 :
177 : // -----------------------------------------------------------------------
178 :
179 0 : sal_Bool SystemWindow::Close()
180 : {
181 0 : ImplDelData aDelData;
182 0 : ImplAddDel( &aDelData );
183 0 : ImplCallEventListeners( VCLEVENT_WINDOW_CLOSE );
184 0 : if ( aDelData.IsDead() )
185 0 : return sal_False;
186 0 : ImplRemoveDel( &aDelData );
187 :
188 0 : if ( mpWindowImpl->mxWindowPeer.is() && IsCreatedWithToolkit() )
189 0 : return sal_False;
190 :
191 : // Is Window not closeable, ignore close
192 0 : Window* pBorderWin = ImplGetBorderWindow();
193 : WinBits nStyle;
194 0 : if ( pBorderWin )
195 0 : nStyle = pBorderWin->GetStyle();
196 : else
197 0 : nStyle = GetStyle();
198 0 : if ( !(nStyle & WB_CLOSEABLE) )
199 0 : return sal_False;
200 :
201 0 : Hide();
202 :
203 0 : return sal_True;
204 : }
205 :
206 : // -----------------------------------------------------------------------
207 :
208 0 : void SystemWindow::TitleButtonClick( sal_uInt16 )
209 : {
210 0 : }
211 :
212 : // -----------------------------------------------------------------------
213 :
214 0 : void SystemWindow::Pin()
215 : {
216 0 : }
217 :
218 : // -----------------------------------------------------------------------
219 :
220 0 : void SystemWindow::Roll()
221 : {
222 0 : }
223 :
224 : // -----------------------------------------------------------------------
225 :
226 0 : void SystemWindow::Resizing( Size& )
227 : {
228 0 : }
229 :
230 : // -----------------------------------------------------------------------
231 :
232 2244 : void SystemWindow::SetRepresentedURL( const OUString& i_rURL )
233 : {
234 2244 : bool bChanged = (i_rURL != mpImplData->maRepresentedURL);
235 2244 : mpImplData->maRepresentedURL = i_rURL;
236 2244 : if ( !mbSysChild && bChanged )
237 : {
238 468 : const Window* pWindow = this;
239 1404 : while ( pWindow->mpWindowImpl->mpBorderWindow )
240 468 : pWindow = pWindow->mpWindowImpl->mpBorderWindow;
241 :
242 468 : if ( pWindow->mpWindowImpl->mbFrame )
243 468 : pWindow->mpWindowImpl->mpFrame->SetRepresentedURL( i_rURL );
244 : }
245 2244 : }
246 :
247 : // -----------------------------------------------------------------------
248 :
249 3351 : void SystemWindow::SetIcon( sal_uInt16 nIcon )
250 : {
251 3351 : if ( mnIcon == nIcon )
252 5591 : return;
253 :
254 1111 : mnIcon = nIcon;
255 :
256 1111 : if ( !mbSysChild )
257 : {
258 1111 : const Window* pWindow = this;
259 3333 : while ( pWindow->mpWindowImpl->mpBorderWindow )
260 1111 : pWindow = pWindow->mpWindowImpl->mpBorderWindow;
261 :
262 1111 : if ( pWindow->mpWindowImpl->mbFrame )
263 1111 : pWindow->mpWindowImpl->mpFrame->SetIcon( nIcon );
264 : }
265 : }
266 :
267 : // -----------------------------------------------------------------------
268 :
269 2196 : void SystemWindow::EnableSaveBackground( sal_Bool bSave )
270 : {
271 2196 : if( ImplGetSVData()->maWinData.mbNoSaveBackground )
272 0 : bSave = false;
273 :
274 2196 : Window* pWindow = this;
275 6588 : while ( pWindow->mpWindowImpl->mpBorderWindow )
276 2196 : pWindow = pWindow->mpWindowImpl->mpBorderWindow;
277 2196 : if ( pWindow->mpWindowImpl->mbOverlapWin && !pWindow->mpWindowImpl->mbFrame )
278 : {
279 0 : pWindow->mpWindowImpl->mpOverlapData->mbSaveBack = bSave;
280 0 : if ( !bSave )
281 0 : pWindow->ImplDeleteOverlapBackground();
282 : }
283 2196 : }
284 :
285 : // -----------------------------------------------------------------------
286 :
287 12 : sal_Bool SystemWindow::IsSaveBackgroundEnabled() const
288 : {
289 12 : const Window* pWindow = this;
290 36 : while ( pWindow->mpWindowImpl->mpBorderWindow )
291 12 : pWindow = pWindow->mpWindowImpl->mpBorderWindow;
292 12 : if ( pWindow->mpWindowImpl->mpOverlapData )
293 12 : return pWindow->mpWindowImpl->mpOverlapData->mbSaveBack;
294 : else
295 0 : return sal_False;
296 : }
297 :
298 : // -----------------------------------------------------------------------
299 :
300 0 : void SystemWindow::ShowTitleButton( sal_uInt16 nButton, sal_Bool bVisible )
301 : {
302 0 : if ( nButton == TITLE_BUTTON_DOCKING )
303 : {
304 0 : if ( mbDockBtn != bVisible )
305 : {
306 0 : mbDockBtn = bVisible;
307 0 : if ( mpWindowImpl->mpBorderWindow )
308 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetDockButton( bVisible );
309 : }
310 : }
311 0 : else if ( nButton == TITLE_BUTTON_HIDE )
312 : {
313 0 : if ( mbHideBtn != bVisible )
314 : {
315 0 : mbHideBtn = bVisible;
316 0 : if ( mpWindowImpl->mpBorderWindow )
317 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetHideButton( bVisible );
318 : }
319 : }
320 0 : else if ( nButton == TITLE_BUTTON_MENU )
321 : {
322 0 : if ( mpWindowImpl->mpBorderWindow )
323 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetMenuButton( bVisible );
324 : }
325 : else
326 0 : return;
327 : }
328 :
329 : // -----------------------------------------------------------------------
330 :
331 0 : sal_Bool SystemWindow::IsTitleButtonVisible( sal_uInt16 nButton ) const
332 : {
333 0 : if ( nButton == TITLE_BUTTON_DOCKING )
334 0 : return mbDockBtn;
335 : else /* if ( nButton == TITLE_BUTTON_HIDE ) */
336 0 : return mbHideBtn;
337 : }
338 :
339 : // -----------------------------------------------------------------------
340 :
341 0 : void SystemWindow::SetPin( sal_Bool bPin )
342 : {
343 0 : if ( bPin != mbPined )
344 : {
345 0 : mbPined = bPin;
346 0 : if ( mpWindowImpl->mpBorderWindow )
347 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetPin( bPin );
348 : }
349 0 : }
350 :
351 : // -----------------------------------------------------------------------
352 :
353 0 : void SystemWindow::RollUp()
354 : {
355 0 : if ( !mbRollUp )
356 : {
357 0 : maOrgSize = GetOutputSizePixel();
358 0 : mbRollFunc = sal_True;
359 0 : Size aSize = maRollUpOutSize;
360 0 : if ( !aSize.Width() )
361 0 : aSize.Width() = GetOutputSizePixel().Width();
362 0 : mbRollUp = sal_True;
363 0 : if ( mpWindowImpl->mpBorderWindow )
364 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetRollUp( sal_True, aSize );
365 : else
366 0 : SetOutputSizePixel( aSize );
367 0 : mbRollFunc = sal_False;
368 : }
369 0 : }
370 :
371 : // -----------------------------------------------------------------------
372 :
373 0 : void SystemWindow::RollDown()
374 : {
375 0 : if ( mbRollUp )
376 : {
377 0 : mbRollUp = sal_False;
378 0 : if ( mpWindowImpl->mpBorderWindow )
379 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetRollUp( sal_False, maOrgSize );
380 : else
381 0 : SetOutputSizePixel( maOrgSize );
382 : }
383 0 : }
384 :
385 : // -----------------------------------------------------------------------
386 :
387 0 : void SystemWindow::SetMinOutputSizePixel( const Size& rSize )
388 : {
389 0 : maMinOutSize = rSize;
390 0 : if ( mpWindowImpl->mpBorderWindow )
391 : {
392 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetMinOutputSize( rSize.Width(), rSize.Height() );
393 0 : if ( mpWindowImpl->mpBorderWindow->mpWindowImpl->mbFrame )
394 0 : mpWindowImpl->mpBorderWindow->mpWindowImpl->mpFrame->SetMinClientSize( rSize.Width(), rSize.Height() );
395 : }
396 0 : else if ( mpWindowImpl->mbFrame )
397 0 : mpWindowImpl->mpFrame->SetMinClientSize( rSize.Width(), rSize.Height() );
398 0 : }
399 :
400 : // -----------------------------------------------------------------------
401 :
402 0 : void SystemWindow::SetMaxOutputSizePixel( const Size& rSize )
403 : {
404 0 : Size aSize( rSize );
405 0 : if( aSize.Width() > SHRT_MAX || aSize.Width() <= 0 )
406 0 : aSize.Width() = SHRT_MAX;
407 0 : if( aSize.Height() > SHRT_MAX || aSize.Height() <= 0 )
408 0 : aSize.Height() = SHRT_MAX;
409 :
410 0 : mpImplData->maMaxOutSize = aSize;
411 0 : if ( mpWindowImpl->mpBorderWindow )
412 : {
413 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetMaxOutputSize( aSize.Width(), aSize.Height() );
414 0 : if ( mpWindowImpl->mpBorderWindow->mpWindowImpl->mbFrame )
415 0 : mpWindowImpl->mpBorderWindow->mpWindowImpl->mpFrame->SetMaxClientSize( aSize.Width(), aSize.Height() );
416 : }
417 0 : else if ( mpWindowImpl->mbFrame )
418 0 : mpWindowImpl->mpFrame->SetMaxClientSize( aSize.Width(), aSize.Height() );
419 0 : }
420 :
421 97 : const Size& SystemWindow::GetMaxOutputSizePixel() const
422 : {
423 97 : return mpImplData->maMaxOutSize;
424 : }
425 : // -----------------------------------------------------------------------
426 :
427 0 : Size SystemWindow::GetResizeOutputSizePixel() const
428 : {
429 0 : Size aSize = GetOutputSizePixel();
430 0 : if ( aSize.Width() < maMinOutSize.Width() )
431 0 : aSize.Width() = maMinOutSize.Width();
432 0 : if ( aSize.Height() < maMinOutSize.Height() )
433 0 : aSize.Height() = maMinOutSize.Height();
434 0 : return aSize;
435 : }
436 :
437 : // -----------------------------------------------------------------------
438 :
439 1143 : static void ImplWindowStateFromStr(WindowStateData& rData,
440 : const OString& rStr)
441 : {
442 1143 : sal_uLong nValidMask = 0;
443 1143 : sal_Int32 nIndex = 0;
444 1143 : OString aTokenStr;
445 :
446 1143 : aTokenStr = rStr.getToken(0, ',', nIndex);
447 1143 : if (!aTokenStr.isEmpty())
448 : {
449 1069 : rData.SetX(aTokenStr.toInt32());
450 1069 : if( rData.GetX() > -16384 && rData.GetX() < 16384 )
451 1069 : nValidMask |= WINDOWSTATE_MASK_X;
452 : else
453 0 : rData.SetX( 0 );
454 : }
455 : else
456 74 : rData.SetX( 0 );
457 1143 : aTokenStr = rStr.getToken(0, ',', nIndex);
458 1143 : if (!aTokenStr.isEmpty())
459 : {
460 1069 : rData.SetY(aTokenStr.toInt32());
461 1069 : if( rData.GetY() > -16384 && rData.GetY() < 16384 )
462 1069 : nValidMask |= WINDOWSTATE_MASK_Y;
463 : else
464 0 : rData.SetY( 0 );
465 : }
466 : else
467 74 : rData.SetY( 0 );
468 1143 : aTokenStr = rStr.getToken(0, ',', nIndex);
469 1143 : if (!aTokenStr.isEmpty())
470 : {
471 1039 : rData.SetWidth(aTokenStr.toInt32());
472 1039 : if( rData.GetWidth() > 0 && rData.GetWidth() < 16384 )
473 1039 : nValidMask |= WINDOWSTATE_MASK_WIDTH;
474 : else
475 0 : rData.SetWidth( 0 );
476 : }
477 : else
478 104 : rData.SetWidth( 0 );
479 1143 : aTokenStr = rStr.getToken(0, ';', nIndex);
480 1143 : if (!aTokenStr.isEmpty())
481 : {
482 1039 : rData.SetHeight(aTokenStr.toInt32());
483 1039 : if( rData.GetHeight() > 0 && rData.GetHeight() < 16384 )
484 1039 : nValidMask |= WINDOWSTATE_MASK_HEIGHT;
485 : else
486 0 : rData.SetHeight( 0 );
487 : }
488 : else
489 104 : rData.SetHeight( 0 );
490 1143 : aTokenStr = rStr.getToken(0, ';', nIndex);
491 1143 : if (!aTokenStr.isEmpty())
492 : {
493 : // #94144# allow Minimize again, should be masked out when read from configuration
494 : // 91625 - ignore Minimize
495 1143 : sal_uInt32 nState = (sal_uInt32)aTokenStr.toInt32();
496 : //nState &= ~(WINDOWSTATE_STATE_MINIMIZED);
497 1143 : rData.SetState( nState );
498 1143 : nValidMask |= WINDOWSTATE_MASK_STATE;
499 : }
500 : else
501 0 : rData.SetState( 0 );
502 :
503 : // read maximized pos/size
504 1143 : aTokenStr = rStr.getToken(0, ',', nIndex);
505 1143 : if (!aTokenStr.isEmpty())
506 : {
507 1039 : rData.SetMaximizedX(aTokenStr.toInt32());
508 1039 : if( rData.GetMaximizedX() > -16384 && rData.GetMaximizedX() < 16384 )
509 1039 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_X;
510 : else
511 0 : rData.SetMaximizedX( 0 );
512 : }
513 : else
514 104 : rData.SetMaximizedX( 0 );
515 1143 : aTokenStr = rStr.getToken(0, ',', nIndex);
516 1143 : if (!aTokenStr.isEmpty())
517 : {
518 1039 : rData.SetMaximizedY(aTokenStr.toInt32());
519 1039 : if( rData.GetMaximizedY() > -16384 && rData.GetMaximizedY() < 16384 )
520 1039 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_Y;
521 : else
522 0 : rData.SetMaximizedY( 0 );
523 : }
524 : else
525 104 : rData.SetMaximizedY( 0 );
526 1143 : aTokenStr = rStr.getToken(0, ',', nIndex);
527 1143 : if (!aTokenStr.isEmpty())
528 : {
529 1039 : rData.SetMaximizedWidth(aTokenStr.toInt32());
530 1039 : if( rData.GetMaximizedWidth() > 0 && rData.GetMaximizedWidth() < 16384 )
531 0 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_WIDTH;
532 : else
533 1039 : rData.SetMaximizedWidth( 0 );
534 : }
535 : else
536 104 : rData.SetMaximizedWidth( 0 );
537 1143 : aTokenStr = rStr.getToken(0, ';', nIndex);
538 1143 : if (!aTokenStr.isEmpty())
539 : {
540 1039 : rData.SetMaximizedHeight(aTokenStr.toInt32());
541 1039 : if( rData.GetMaximizedHeight() > 0 && rData.GetMaximizedHeight() < 16384 )
542 0 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_HEIGHT;
543 : else
544 1039 : rData.SetMaximizedHeight( 0 );
545 : }
546 : else
547 104 : rData.SetMaximizedHeight( 0 );
548 :
549 : // mark valid fields
550 1143 : rData.SetMask( nValidMask );
551 1143 : }
552 :
553 : // -----------------------------------------------------------------------
554 :
555 2176 : static OString ImplWindowStateToStr(const WindowStateData& rData)
556 : {
557 2176 : sal_uLong nValidMask = rData.GetMask();
558 2176 : if ( !nValidMask )
559 0 : return OString();
560 :
561 2176 : OStringBuffer rStrBuf;
562 :
563 2176 : if ( nValidMask & WINDOWSTATE_MASK_X )
564 2176 : rStrBuf.append(static_cast<sal_Int32>(rData.GetX()));
565 2176 : rStrBuf.append(',');
566 2176 : if ( nValidMask & WINDOWSTATE_MASK_Y )
567 2176 : rStrBuf.append(static_cast<sal_Int32>(rData.GetY()));
568 2176 : rStrBuf.append(',');
569 2176 : if ( nValidMask & WINDOWSTATE_MASK_WIDTH )
570 2137 : rStrBuf.append(static_cast<sal_Int32>(rData.GetWidth()));
571 2176 : rStrBuf.append(',');
572 2176 : if ( nValidMask & WINDOWSTATE_MASK_HEIGHT )
573 2137 : rStrBuf.append(static_cast<sal_Int32>(rData.GetHeight()));
574 2176 : rStrBuf.append( ';' );
575 2176 : if ( nValidMask & WINDOWSTATE_MASK_STATE )
576 : {
577 : // #94144# allow Minimize again, should be masked out when read from configuration
578 : // 91625 - ignore Minimize
579 2176 : sal_uInt32 nState = rData.GetState();
580 2176 : rStrBuf.append(static_cast<sal_Int32>(nState));
581 : }
582 2176 : rStrBuf.append(';');
583 2176 : if ( nValidMask & WINDOWSTATE_MASK_MAXIMIZED_X )
584 2137 : rStrBuf.append(static_cast<sal_Int32>(rData.GetMaximizedX()));
585 2176 : rStrBuf.append(',');
586 2176 : if ( nValidMask & WINDOWSTATE_MASK_MAXIMIZED_Y )
587 2137 : rStrBuf.append(static_cast<sal_Int32>(rData.GetMaximizedY()));
588 2176 : rStrBuf.append( ',' );
589 2176 : if ( nValidMask & WINDOWSTATE_MASK_MAXIMIZED_WIDTH )
590 2137 : rStrBuf.append(static_cast<sal_Int32>(rData.GetMaximizedWidth()));
591 2176 : rStrBuf.append(',');
592 2176 : if ( nValidMask & WINDOWSTATE_MASK_MAXIMIZED_HEIGHT )
593 2137 : rStrBuf.append(static_cast<sal_Int32>(rData.GetMaximizedHeight()));
594 2176 : rStrBuf.append(';');
595 :
596 2176 : return rStrBuf.makeStringAndClear();
597 : }
598 :
599 : // -----------------------------------------------------------------------
600 :
601 2286 : void SystemWindow::ImplMoveToScreen( long& io_rX, long& io_rY, long i_nWidth, long i_nHeight, Window* i_pConfigureWin )
602 : {
603 2286 : Rectangle aScreenRect;
604 2286 : if( !Application::IsUnifiedDisplay() )
605 0 : aScreenRect = Application::GetScreenPosSizePixel( GetScreenNumber() );
606 : else
607 : {
608 2286 : aScreenRect = Application::GetScreenPosSizePixel( 0 );
609 2286 : for( unsigned int i = 1; i < Application::GetScreenCount(); i++ )
610 0 : aScreenRect.Union( Application::GetScreenPosSizePixel( i ) );
611 : }
612 : // unfortunately most of the time width and height are not really known
613 2286 : if( i_nWidth < 1 )
614 1247 : i_nWidth = 50;
615 2286 : if( i_nHeight < 1 )
616 1247 : i_nHeight = 50;
617 :
618 : // check left border
619 2286 : bool bMove = false;
620 2286 : if( io_rX + i_nWidth < aScreenRect.Left() )
621 : {
622 0 : bMove = true;
623 0 : io_rX = aScreenRect.Left();
624 : }
625 : // check right border
626 2286 : if( io_rX > aScreenRect.Right() - i_nWidth )
627 : {
628 0 : bMove = true;
629 0 : io_rX = aScreenRect.Right() - i_nWidth;
630 : }
631 : // check top border
632 2286 : if( io_rY + i_nHeight < aScreenRect.Top() )
633 : {
634 0 : bMove = true;
635 0 : io_rY = aScreenRect.Top();
636 : }
637 : // check bottom border
638 2286 : if( io_rY > aScreenRect.Bottom() - i_nHeight )
639 : {
640 0 : bMove = true;
641 0 : io_rY = aScreenRect.Bottom() - i_nHeight;
642 : }
643 2286 : Window* pParent = i_pConfigureWin->GetParent();
644 2286 : if( bMove && pParent )
645 : {
646 : // calculate absolute screen pos here, since that is what is contained in WindowState
647 0 : Point aParentAbsPos( pParent->OutputToAbsoluteScreenPixel( Point(0,0) ) );
648 0 : Size aParentSizePixel( pParent->GetOutputSizePixel() );
649 0 : Point aPos( (aParentSizePixel.Width() - i_nWidth) / 2,
650 0 : (aParentSizePixel.Height() - i_nHeight) / 2 );
651 0 : io_rX = aParentAbsPos.X() + aPos.X();
652 0 : io_rY = aParentAbsPos.Y() + aPos.Y();
653 : }
654 2286 : }
655 :
656 1143 : void SystemWindow::SetWindowStateData( const WindowStateData& rData )
657 : {
658 1143 : sal_uLong nValidMask = rData.GetMask();
659 1143 : if ( !nValidMask )
660 0 : return;
661 :
662 1143 : if ( mbSysChild )
663 0 : return;
664 :
665 1143 : Window* pWindow = this;
666 3399 : while ( pWindow->mpWindowImpl->mpBorderWindow )
667 1113 : pWindow = pWindow->mpWindowImpl->mpBorderWindow;
668 :
669 1143 : if ( pWindow->mpWindowImpl->mbFrame )
670 : {
671 1143 : sal_uLong nState = rData.GetState();
672 : SalFrameState aState;
673 1143 : aState.mnMask = rData.GetMask();
674 1143 : aState.mnX = rData.GetX();
675 1143 : aState.mnY = rData.GetY();
676 1143 : aState.mnWidth = rData.GetWidth();
677 1143 : aState.mnHeight = rData.GetHeight();
678 :
679 1143 : if( rData.GetMask() & (WINDOWSTATE_MASK_WIDTH|WINDOWSTATE_MASK_HEIGHT) )
680 : {
681 : // #i43799# adjust window state sizes if a minimial output size was set
682 : // otherwise the frame and the client might get different sizes
683 1039 : if( maMinOutSize.Width() > aState.mnWidth )
684 0 : aState.mnWidth = maMinOutSize.Width();
685 1039 : if( maMinOutSize.Height() > aState.mnHeight )
686 0 : aState.mnHeight = maMinOutSize.Height();
687 : }
688 :
689 1143 : aState.mnMaximizedX = rData.GetMaximizedX();
690 1143 : aState.mnMaximizedY = rData.GetMaximizedY();
691 1143 : aState.mnMaximizedWidth = rData.GetMaximizedWidth();
692 1143 : aState.mnMaximizedHeight = rData.GetMaximizedHeight();
693 : // #94144# allow Minimize again, should be masked out when read from configuration
694 : // 91625 - ignore Minimize
695 : //nState &= ~(WINDOWSTATE_STATE_MINIMIZED);
696 1143 : aState.mnState = nState & WINDOWSTATE_STATE_SYSTEMMASK;
697 :
698 : // normalize window positions onto screen
699 1143 : ImplMoveToScreen( aState.mnX, aState.mnY, aState.mnWidth, aState.mnHeight, pWindow );
700 1143 : ImplMoveToScreen( aState.mnMaximizedX, aState.mnMaximizedY, aState.mnMaximizedWidth, aState.mnMaximizedHeight, pWindow );
701 :
702 : // #96568# avoid having multiple frames at the same screen location
703 : // do the check only if not maximized
704 1143 : if( !((rData.GetMask() & WINDOWSTATE_MASK_STATE) && (nState & WINDOWSTATE_STATE_MAXIMIZED)) )
705 1069 : if( rData.GetMask() & (WINDOWSTATE_MASK_POS|WINDOWSTATE_MASK_WIDTH|WINDOWSTATE_MASK_HEIGHT) )
706 : {
707 1069 : Rectangle aDesktop = GetDesktopRectPixel();
708 1069 : ImplSVData *pSVData = ImplGetSVData();
709 1069 : Window *pWin = pSVData->maWinData.mpFirstFrame;
710 1069 : sal_Bool bWrapped = sal_False;
711 4740 : while( pWin )
712 : {
713 8236 : if( !pWin->ImplIsRealParentPath( this ) && ( pWin != this ) &&
714 5604 : pWin->ImplGetWindow()->IsTopWindow() && pWin->mpWindowImpl->mbReallyVisible )
715 : {
716 101 : SalFrameGeometry g = pWin->mpWindowImpl->mpFrame->GetGeometry();
717 101 : if( abs(g.nX-aState.mnX) < 2 && abs(g.nY-aState.mnY) < 5 )
718 : {
719 46 : long displacement = g.nTopDecoration ? g.nTopDecoration : 20;
720 92 : if( (unsigned long) (aState.mnX + displacement + aState.mnWidth + g.nRightDecoration) > (unsigned long) aDesktop.Right() ||
721 46 : (unsigned long) (aState.mnY + displacement + aState.mnHeight + g.nBottomDecoration) > (unsigned long) aDesktop.Bottom() )
722 : {
723 : // displacing would leave screen
724 0 : aState.mnX = g.nLeftDecoration ? g.nLeftDecoration : 10; // should result in (0,0)
725 0 : aState.mnY = displacement;
726 0 : if( bWrapped ||
727 0 : (unsigned long) (aState.mnX + displacement + aState.mnWidth + g.nRightDecoration) > (unsigned long) aDesktop.Right() ||
728 0 : (unsigned long) (aState.mnY + displacement + aState.mnHeight + g.nBottomDecoration) > (unsigned long) aDesktop.Bottom() )
729 0 : break; // further displacement not possible -> break
730 : // avoid endless testing
731 0 : bWrapped = sal_True;
732 : }
733 : else
734 : {
735 : // displace
736 46 : aState.mnX += displacement;
737 46 : aState.mnY += displacement;
738 : }
739 46 : pWin = pSVData->maWinData.mpFirstFrame; // check new pos again
740 : }
741 : }
742 2602 : pWin = pWin->mpWindowImpl->mpFrameData->mpNextFrame;
743 : }
744 : }
745 :
746 1143 : mpWindowImpl->mpFrame->SetWindowState( &aState );
747 :
748 : // do a synchronous resize for layout reasons
749 : // but use rData only when the window is not to be maximized (#i38089#)
750 : // otherwise we have no useful size information
751 1143 : if( (rData.GetMask() & WINDOWSTATE_MASK_STATE) && (nState & WINDOWSTATE_STATE_MAXIMIZED) )
752 : {
753 : // query maximized size from frame
754 74 : SalFrameGeometry aGeometry = mpWindowImpl->mpFrame->GetGeometry();
755 :
756 : // but use it only if it is different from the restore size (rData)
757 : // as currently only on windows the exact size of a maximized window
758 : // can be computed without actually showing the window
759 74 : if( aGeometry.nWidth != rData.GetWidth() || aGeometry.nHeight != rData.GetHeight() )
760 74 : ImplHandleResize( pWindow, aGeometry.nWidth, aGeometry.nHeight );
761 : }
762 : else
763 1069 : if( rData.GetMask() & (WINDOWSTATE_MASK_WIDTH|WINDOWSTATE_MASK_HEIGHT) )
764 1039 : ImplHandleResize( pWindow, aState.mnWidth, aState.mnHeight ); // #i43799# use aState and not rData, see above
765 : }
766 : else
767 : {
768 0 : sal_uInt16 nPosSize = 0;
769 0 : if ( nValidMask & WINDOWSTATE_MASK_X )
770 0 : nPosSize |= WINDOW_POSSIZE_X;
771 0 : if ( nValidMask & WINDOWSTATE_MASK_Y )
772 0 : nPosSize |= WINDOW_POSSIZE_Y;
773 0 : if ( nValidMask & WINDOWSTATE_MASK_WIDTH )
774 0 : nPosSize |= WINDOW_POSSIZE_WIDTH;
775 0 : if ( nValidMask & WINDOWSTATE_MASK_HEIGHT )
776 0 : nPosSize |= WINDOW_POSSIZE_HEIGHT;
777 :
778 0 : if( IsRollUp() )
779 0 : RollDown();
780 :
781 0 : long nX = rData.GetX();
782 0 : long nY = rData.GetY();
783 0 : long nWidth = rData.GetWidth();
784 0 : long nHeight = rData.GetHeight();
785 0 : const SalFrameGeometry& rGeom = pWindow->mpWindowImpl->mpFrame->GetGeometry();
786 0 : if( nX < 0 )
787 0 : nX = 0;
788 0 : if( nX + nWidth > (long) rGeom.nWidth )
789 0 : nX = rGeom.nWidth - nWidth;
790 0 : if( nY < 0 )
791 0 : nY = 0;
792 0 : if( nY + nHeight > (long) rGeom.nHeight )
793 0 : nY = rGeom.nHeight - nHeight;
794 0 : setPosSizePixel( nX, nY, nWidth, nHeight, nPosSize );
795 0 : maOrgSize = Size( nWidth, nHeight );
796 :
797 : // 91625 - ignore Minimize
798 0 : if ( nValidMask & WINDOWSTATE_MASK_STATE )
799 : {
800 0 : sal_uLong nState = rData.GetState();
801 0 : if ( nState & WINDOWSTATE_STATE_ROLLUP )
802 0 : RollUp();
803 : else
804 0 : RollDown();
805 : }
806 : }
807 : }
808 :
809 : // -----------------------------------------------------------------------
810 :
811 2176 : void SystemWindow::GetWindowStateData( WindowStateData& rData ) const
812 : {
813 2176 : sal_uLong nValidMask = rData.GetMask();
814 2176 : if ( !nValidMask )
815 0 : return;
816 :
817 2176 : if ( mbSysChild )
818 0 : return;
819 :
820 2176 : const Window* pWindow = this;
821 6489 : while ( pWindow->mpWindowImpl->mpBorderWindow )
822 2137 : pWindow = pWindow->mpWindowImpl->mpBorderWindow;
823 :
824 2176 : if ( pWindow->mpWindowImpl->mbFrame )
825 : {
826 : SalFrameState aState;
827 2176 : aState.mnMask = 0xFFFFFFFF;
828 2176 : if ( mpWindowImpl->mpFrame->GetWindowState( &aState ) )
829 : {
830 2176 : if ( nValidMask & WINDOWSTATE_MASK_X )
831 2176 : rData.SetX( aState.mnX );
832 2176 : if ( nValidMask & WINDOWSTATE_MASK_Y )
833 2176 : rData.SetY( aState.mnY );
834 2176 : if ( nValidMask & WINDOWSTATE_MASK_WIDTH )
835 2137 : rData.SetWidth( aState.mnWidth );
836 2176 : if ( nValidMask & WINDOWSTATE_MASK_HEIGHT )
837 2137 : rData.SetHeight( aState.mnHeight );
838 2176 : if ( aState.mnMask & WINDOWSTATE_MASK_MAXIMIZED_X )
839 : {
840 0 : rData.SetMaximizedX( aState.mnMaximizedX );
841 0 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_X;
842 : }
843 2176 : if ( aState.mnMask & WINDOWSTATE_MASK_MAXIMIZED_Y )
844 : {
845 0 : rData.SetMaximizedY( aState.mnMaximizedY );
846 0 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_Y;
847 : }
848 2176 : if ( aState.mnMask & WINDOWSTATE_MASK_MAXIMIZED_WIDTH )
849 : {
850 0 : rData.SetMaximizedWidth( aState.mnMaximizedWidth );
851 0 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_WIDTH;
852 : }
853 2176 : if ( aState.mnMask & WINDOWSTATE_MASK_MAXIMIZED_HEIGHT )
854 : {
855 0 : rData.SetMaximizedHeight( aState.mnMaximizedHeight );
856 0 : nValidMask |= WINDOWSTATE_MASK_MAXIMIZED_HEIGHT;
857 : }
858 2176 : if ( nValidMask & WINDOWSTATE_MASK_STATE )
859 : {
860 : // #94144# allow Minimize again, should be masked out when read from configuration
861 : // 91625 - ignore Minimize
862 2176 : if ( !(nValidMask&WINDOWSTATE_MASK_MINIMIZED) )
863 1123 : aState.mnState &= ~(WINDOWSTATE_STATE_MINIMIZED);
864 2176 : rData.SetState( aState.mnState );
865 : }
866 2176 : rData.SetMask( nValidMask );
867 : }
868 : else
869 0 : rData.SetMask( 0 );
870 : }
871 : else
872 : {
873 0 : Point aPos = GetPosPixel();
874 0 : Size aSize = GetSizePixel();
875 0 : sal_uLong nState = 0;
876 :
877 0 : if ( IsRollUp() )
878 : {
879 0 : aSize.Height() += maOrgSize.Height();
880 0 : nState |= WINDOWSTATE_STATE_ROLLUP;
881 : }
882 :
883 0 : if ( nValidMask & WINDOWSTATE_MASK_X )
884 0 : rData.SetX( aPos.X() );
885 0 : if ( nValidMask & WINDOWSTATE_MASK_Y )
886 0 : rData.SetY( aPos.Y() );
887 0 : if ( nValidMask & WINDOWSTATE_MASK_WIDTH )
888 0 : rData.SetWidth( aSize.Width() );
889 0 : if ( nValidMask & WINDOWSTATE_MASK_HEIGHT )
890 0 : rData.SetHeight( aSize.Height() );
891 0 : if ( nValidMask & WINDOWSTATE_MASK_STATE )
892 0 : rData.SetState( nState );
893 : }
894 : }
895 :
896 : // -----------------------------------------------------------------------
897 :
898 1143 : void SystemWindow::SetWindowState(const OString& rStr)
899 : {
900 1143 : if (rStr.isEmpty())
901 1143 : return;
902 :
903 1143 : WindowStateData aData;
904 1143 : ImplWindowStateFromStr( aData, rStr );
905 1143 : SetWindowStateData( aData );
906 : }
907 :
908 : // -----------------------------------------------------------------------
909 :
910 2176 : OString SystemWindow::GetWindowState( sal_uLong nMask ) const
911 : {
912 2176 : WindowStateData aData;
913 2176 : aData.SetMask( nMask );
914 2176 : GetWindowStateData( aData );
915 :
916 2176 : return ImplWindowStateToStr(aData);
917 : }
918 :
919 : // -----------------------------------------------------------------------
920 :
921 4049 : void SystemWindow::SetMenuBar( MenuBar* pMenuBar )
922 : {
923 4049 : if ( mpMenuBar != pMenuBar )
924 : {
925 2145 : MenuBar* pOldMenuBar = mpMenuBar;
926 2145 : Window* pOldWindow = NULL;
927 2145 : Window* pNewWindow=NULL;
928 2145 : mpMenuBar = pMenuBar;
929 :
930 2145 : if ( mpWindowImpl->mpBorderWindow && (mpWindowImpl->mpBorderWindow->GetType() == WINDOW_BORDERWINDOW) )
931 : {
932 2145 : if ( pOldMenuBar )
933 1072 : pOldWindow = pOldMenuBar->ImplGetWindow();
934 : else
935 1073 : pOldWindow = NULL;
936 2145 : if ( pOldWindow )
937 : {
938 1072 : ImplCallEventListeners( VCLEVENT_WINDOW_MENUBARREMOVED, (void*) pOldMenuBar );
939 1072 : pOldWindow->SetAccessible( ::com::sun::star::uno::Reference< ::com::sun::star::accessibility::XAccessible >() );
940 : }
941 2145 : if ( pMenuBar )
942 : {
943 : DBG_ASSERT( !pMenuBar->pWindow, "SystemWindow::SetMenuBar() - MenuBars can only set in one SystemWindow at time" );
944 1074 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetMenuBarWindow( pNewWindow = MenuBar::ImplCreate( mpWindowImpl->mpBorderWindow, pOldWindow, pMenuBar ) );
945 1074 : ImplCallEventListeners( VCLEVENT_WINDOW_MENUBARADDED, (void*) pMenuBar );
946 : }
947 : else
948 1071 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetMenuBarWindow( NULL );
949 2145 : ImplToBottomChild();
950 2145 : if ( pOldMenuBar )
951 : {
952 1072 : sal_Bool bDelete = (pMenuBar == 0) ? sal_True : sal_False;
953 1072 : if( bDelete && pOldWindow )
954 : {
955 1071 : if( mpImplData->mpTaskPaneList )
956 1071 : mpImplData->mpTaskPaneList->RemoveWindow( pOldWindow );
957 : }
958 1072 : MenuBar::ImplDestroy( pOldMenuBar, bDelete );
959 1072 : if( bDelete )
960 1071 : pOldWindow = NULL; // will be deleted in MenuBar::ImplDestroy,
961 : }
962 :
963 : }
964 : else
965 : {
966 0 : if( pMenuBar )
967 0 : pNewWindow = pMenuBar->ImplGetWindow();
968 0 : if( pOldMenuBar )
969 0 : pOldWindow = pOldMenuBar->ImplGetWindow();
970 : }
971 :
972 : // update taskpane list to make menubar accessible
973 2145 : if( mpImplData->mpTaskPaneList )
974 : {
975 1303 : if( pOldWindow )
976 1 : mpImplData->mpTaskPaneList->RemoveWindow( pOldWindow );
977 1303 : if( pNewWindow )
978 232 : mpImplData->mpTaskPaneList->AddWindow( pNewWindow );
979 : }
980 : }
981 4049 : }
982 :
983 : // -----------------------------------------------------------------------
984 :
985 0 : void SystemWindow::SetMenuBarMode( sal_uInt16 nMode )
986 : {
987 0 : if ( mnMenuBarMode != nMode )
988 : {
989 0 : mnMenuBarMode = nMode;
990 0 : if ( mpWindowImpl->mpBorderWindow && (mpWindowImpl->mpBorderWindow->GetType() == WINDOW_BORDERWINDOW) )
991 : {
992 0 : if ( nMode == MENUBAR_MODE_HIDE )
993 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetMenuBarMode( sal_True );
994 : else
995 0 : ((ImplBorderWindow*)mpWindowImpl->mpBorderWindow)->SetMenuBarMode( sal_False );
996 : }
997 : }
998 0 : }
999 :
1000 : // -----------------------------------------------------------------------
1001 :
1002 9529 : sal_Bool SystemWindow::ImplIsInTaskPaneList( Window* pWin )
1003 : {
1004 9529 : if( mpImplData && mpImplData->mpTaskPaneList )
1005 6225 : return mpImplData->mpTaskPaneList->IsInList( pWin );
1006 3304 : return sal_False;
1007 : }
1008 :
1009 0 : unsigned int SystemWindow::GetScreenNumber() const
1010 : {
1011 0 : return mpWindowImpl->mpFrame->maGeometry.nDisplayScreenNumber;
1012 : }
1013 :
1014 0 : void SystemWindow::SetScreenNumber(unsigned int nDisplayScreen)
1015 : {
1016 0 : mpWindowImpl->mpFrame->SetScreenNumber( nDisplayScreen );
1017 0 : }
1018 :
1019 3339 : void SystemWindow::SetApplicationID(const OUString &rApplicationID)
1020 : {
1021 3339 : mpWindowImpl->mpFrame->SetApplicationID( rApplicationID );
1022 3339 : }
1023 :
1024 16 : void SystemWindow::SetCloseHdl(const Link& rLink)
1025 : {
1026 16 : mpImplData->maCloseHdl = rLink;
1027 16 : }
1028 :
1029 2 : const Link& SystemWindow::GetCloseHdl() const
1030 : {
1031 2 : return mpImplData->maCloseHdl;
1032 465 : }
1033 :
1034 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|