1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
22 #include "previewadapter.hxx"
24 #include <com/sun/star/ui/dialogs/FilePreviewImageFormats.hpp>
25 #include "dibpreview.hxx"
26 #include "../misc/WinImplHelper.hxx"
31 //---------------------------------------------
33 //---------------------------------------------
35 using namespace ::com::sun::star::uno
;
36 using namespace ::com::sun::star::lang
;
38 //---------------------------------------------
39 // An impl class to hide implementation details
41 //---------------------------------------------
43 class CPreviewAdapterImpl
46 CPreviewAdapterImpl(HINSTANCE instance
);
48 virtual ~CPreviewAdapterImpl();
50 virtual sal_Int32 SAL_CALL
getTargetColorDepth();
52 virtual sal_Int32 SAL_CALL
getAvailableWidth();
54 virtual sal_Int32 SAL_CALL
getAvailableHeight();
56 virtual void SAL_CALL
setImage( sal_Int16 aImageFormat
, const Any
& aImage
)
57 throw (IllegalArgumentException
,RuntimeException
);
59 virtual sal_Bool SAL_CALL
setShowState(sal_Bool bShowState
);
61 virtual sal_Bool SAL_CALL
getShowState();
63 virtual void SAL_CALL
setParent(HWND parent
);
65 virtual HWND SAL_CALL
getParent();
67 //-------------------------------------
68 // parent notification handler
69 //-------------------------------------
71 virtual void SAL_CALL
notifyParentShow(sal_Bool bShow
);
73 virtual void SAL_CALL
notifyParentSizeChanged();
75 virtual void SAL_CALL
notifyParentWindowPosChanged();
78 virtual void SAL_CALL
calcRightMargin();
80 virtual void SAL_CALL
rearrangeLayout();
82 void SAL_CALL
initializeActivePreview() throw(std::runtime_error
);
84 HWND SAL_CALL
findFileListbox() const;
89 std::auto_ptr
<PreviewBase
> m_Preview
;
93 //prevent copy/assignment
95 CPreviewAdapterImpl(const CPreviewAdapterImpl
&);
96 CPreviewAdapterImpl
& operator=(const CPreviewAdapterImpl
&);
99 //-----------------------------------------
101 //-----------------------------------------
103 CPreviewAdapterImpl::CPreviewAdapterImpl(HINSTANCE instance
) :
104 m_Instance(instance
),
105 m_Preview(new PreviewBase()), // create dummy preview (NULL-Object pattern)
111 //-----------------------------------------
113 //-----------------------------------------
115 CPreviewAdapterImpl::~CPreviewAdapterImpl()
119 //-----------------------------------------
121 //-----------------------------------------
123 sal_Int32 SAL_CALL
CPreviewAdapterImpl::getTargetColorDepth()
125 return m_Preview
->getTargetColorDepth();
128 //-----------------------------------------
130 //-----------------------------------------
132 sal_Int32 SAL_CALL
CPreviewAdapterImpl::getAvailableWidth()
134 return m_Preview
->getAvailableWidth();
137 //-----------------------------------------
139 //-----------------------------------------
141 sal_Int32 SAL_CALL
CPreviewAdapterImpl::getAvailableHeight()
143 return m_Preview
->getAvailableHeight();
146 //-----------------------------------------
148 //-----------------------------------------
150 void SAL_CALL
CPreviewAdapterImpl::setImage( sal_Int16 aImageFormat
, const Any
& aImage
)
151 throw (IllegalArgumentException
,RuntimeException
)
153 m_Preview
->setImage(aImageFormat
,aImage
);
156 //-----------------------------------------
158 //-----------------------------------------
160 sal_Bool SAL_CALL
CPreviewAdapterImpl::setShowState( sal_Bool bShowState
)
162 sal_Bool bRet
= m_Preview
->setShowState(bShowState
);
167 //-----------------------------------------
169 //-----------------------------------------
171 sal_Bool SAL_CALL
CPreviewAdapterImpl::getShowState()
173 return m_Preview
->getShowState();
176 //-----------------------------------------
178 //-----------------------------------------
180 void SAL_CALL
CPreviewAdapterImpl::setParent(HWND parent
)
182 OSL_PRECOND(IsWindow(parent
),"Invalid FileDialog handle");
184 m_FileDialog
= parent
;
188 //-----------------------------------------
190 //-----------------------------------------
192 HWND SAL_CALL
CPreviewAdapterImpl::getParent()
197 //-----------------------------------------
199 //-----------------------------------------
201 void SAL_CALL
CPreviewAdapterImpl::calcRightMargin()
203 // Calculate the right reference margin
206 // 1. This method will be called before the dialog becomes
208 // 2. There exist a FileListbox with the id lst1 even
209 // if it is not visible like under Win2000/XP
210 // 3. Initially this FileListbox has the appropriate size
211 // to fit within the FileListbox
212 // 4. The margin between the right edge of the FileListbox
213 // and the right edge of the FileDialog will be constant
214 // even if the size of the dialog changes
216 HWND flb
= GetDlgItem(m_FileDialog
,lst1
);
218 OSL_ENSURE(IsWindow(flb
),"Filelistbox not found");
221 GetWindowRect(flb
,&rcFlb
);
224 GetWindowRect(m_FileDialog
,&rcFileDlg
);
226 m_RightMargin
= rcFileDlg
.right
- rcFlb
.right
;
229 //-----------------------------------------
231 //-----------------------------------------
233 void SAL_CALL
CPreviewAdapterImpl::notifyParentShow(sal_Bool
)
237 //-----------------------------------------
239 //-----------------------------------------
241 void SAL_CALL
CPreviewAdapterImpl::notifyParentSizeChanged()
246 //-----------------------------------------
248 //-----------------------------------------
250 void SAL_CALL
CPreviewAdapterImpl::notifyParentWindowPosChanged()
254 //-----------------------------------------
256 //-----------------------------------------
258 void SAL_CALL
CPreviewAdapterImpl::rearrangeLayout()
260 // try to get a handle to the filelistbox
261 // if there is no new-style filelistbox like
262 // in Win2000/XP there should be at least the
263 // old listbox, so we take this one
264 // lst1 - identifies the old-style filelistbox
265 // lst2 - identifies the new-style filelistbox
267 HWND flb_new
= findFileListbox();
269 // under Windows NT 4.0 the size of the old
270 // filelistbox will be used as reference for
271 // sizing the new filelistbox, so we have
272 // to change the size of it too
273 HWND flb_old
= GetDlgItem(m_FileDialog
,lst1
);
276 GetWindowRect(flb_new
,&rcFlbNew
);
279 GetWindowRect(m_FileDialog
,&rcFileDlg
);
280 rcFileDlg
.right
-= m_RightMargin
;
282 // the available area for the filelistbox should be
283 // the left edge of the filelistbox and the right
284 // edge of the OK button, we take this as reference
285 int height
= rcFlbNew
.bottom
- rcFlbNew
.top
;
286 int width
= rcFileDlg
.right
- rcFlbNew
.left
;
288 HWND prvwnd
= m_Preview
->getWindowHandle();
290 // we use GetWindowLong to ask for the visibility
291 // of the preview window because IsWindowVisible
292 // only returns true the specified window including
293 // its parent windows are visible
294 // this is not the case when we are called in response
295 // to the WM_SHOWWINDOW message, somehow the WS_VISIBLE
296 // style bit of the FileOpen dialog must be set after that
298 LONG lStyle
= GetWindowLong(prvwnd
,GWL_STYLE
);
299 bool bIsVisible
= ((lStyle
& WS_VISIBLE
) != 0);
303 if (IsWindow(prvwnd
) && bIsVisible
)
307 // resize the filelistbox to the half of the
309 SetWindowPos(flb_new
,
310 NULL
, 0, 0, cx
, height
,
311 SWP_NOMOVE
| SWP_NOZORDER
| SWP_NOACTIVATE
);
313 SetWindowPos(flb_old
,
314 NULL
, 0, 0, cx
, height
,
315 SWP_NOMOVE
| SWP_NOZORDER
| SWP_NOACTIVATE
);
317 // get the new dimensions of the filelistbox after
318 // resizing and take the right,top corner as starting
319 // point for the preview window
320 GetWindowRect(flb_new
,&rcFlbNew
);
321 POINT pt
= { rcFlbNew
.right
, rcFlbNew
.top
};
322 ScreenToClient(m_FileDialog
,&pt
);
324 // resize the preview window to fit within
325 // the available space and set the window
326 // to the top of the z-order else it will
329 HWND_TOP
, pt
.x
, pt
.y
, cx
, height
, SWP_NOACTIVATE
);
333 // resize the filelistbox to the maximum available
335 cx
= rcFileDlg
.right
- rcFlbNew
.left
;
337 // resize the old filelistbox
338 SetWindowPos(flb_old
,
339 NULL
, 0, 0, cx
, height
,
340 SWP_NOMOVE
| SWP_NOZORDER
| SWP_NOACTIVATE
);
342 // resize the new filelistbox
343 SetWindowPos(flb_new
,
344 NULL
, 0, 0, cx
, height
,
345 SWP_NOMOVE
| SWP_NOZORDER
| SWP_NOACTIVATE
);
349 //-----------------------------------------
351 //-----------------------------------------
353 void SAL_CALL
CPreviewAdapterImpl::initializeActivePreview() throw(std::runtime_error
)
355 sal_Bool bShowState
= m_Preview
->getImaginaryShowState();
359 m_Preview
->getImage(aImgFrmt
,aImg
);
361 HWND flb
= findFileListbox();
363 PreviewBase
* prv
= new CDIBPreview(
364 m_Instance
, GetParent(flb
), bShowState
);
366 m_Preview
.reset(prv
);
368 m_Preview
->setImage(aImgFrmt
,aImg
);
371 //-----------------------------------------
373 //-----------------------------------------
375 HWND SAL_CALL
CPreviewAdapterImpl::findFileListbox() const
377 // try to get a handle to the filelistbox
378 // if there is no new-style filelistbox like
379 // in Win2000/XP there should be at least the
380 // old listbox, so we take this one
381 // lst1 - identifies the old-style filelistbox
382 // lst2 - identifies the new-style filelistbox
384 HWND flb
= GetDlgItem(m_FileDialog
,lst2
);
386 flb
= GetDlgItem(m_FileDialog
,lst1
);
392 //##############################################################
395 //--------------------------------------------
396 // Implementation for Windows 95/NT/ME/2000/XP
399 //--------------------------------------------
401 class CWin95NTPreviewAdapterImpl
: public CPreviewAdapterImpl
404 CWin95NTPreviewAdapterImpl(HINSTANCE instance
);
406 virtual void SAL_CALL
notifyParentShow(sal_Bool bShow
);
409 //--------------------------------------------
411 //--------------------------------------------
413 CWin95NTPreviewAdapterImpl::CWin95NTPreviewAdapterImpl(HINSTANCE instance
) :
414 CPreviewAdapterImpl(instance
)
418 //--------------------------------------------
420 //--------------------------------------------
422 void SAL_CALL
CWin95NTPreviewAdapterImpl::notifyParentShow(sal_Bool bShow
)
428 initializeActivePreview();
432 catch(std::runtime_error
&)
438 //##############################################################
441 //-------------------------------
443 //-------------------------------
445 CPreviewAdapter::CPreviewAdapter(HINSTANCE instance
)
447 m_pImpl
.reset(new CWin95NTPreviewAdapterImpl(instance
));
450 //-------------------------------
452 //-------------------------------
454 CPreviewAdapter::~CPreviewAdapter()
458 //-------------------------------
460 //-------------------------------
462 Sequence
<sal_Int16
> SAL_CALL
CPreviewAdapter::getSupportedImageFormats()
464 com::sun::star::uno::Sequence
<sal_Int16
> imgFormats(1);
465 imgFormats
[0] = ::com::sun::star::ui::dialogs::FilePreviewImageFormats::BITMAP
;
469 //-------------------------------
471 //-------------------------------
473 sal_Int32 SAL_CALL
CPreviewAdapter::getTargetColorDepth()
475 return m_pImpl
->getTargetColorDepth();
478 //-------------------------------
480 //-------------------------------
482 sal_Int32 SAL_CALL
CPreviewAdapter::getAvailableWidth()
484 return m_pImpl
->getAvailableWidth();
487 //-------------------------------
489 //-------------------------------
491 sal_Int32 SAL_CALL
CPreviewAdapter::getAvailableHeight()
493 return m_pImpl
->getAvailableHeight();
496 //-------------------------------
498 //-------------------------------
500 void SAL_CALL
CPreviewAdapter::setImage( sal_Int16 aImageFormat
, const Any
& aImage
)
501 throw (IllegalArgumentException
, RuntimeException
)
503 m_pImpl
->setImage(aImageFormat
,aImage
);
506 //-------------------------------
508 //-------------------------------
510 sal_Bool SAL_CALL
CPreviewAdapter::setShowState( sal_Bool bShowState
)
512 return m_pImpl
->setShowState(bShowState
);
515 //-------------------------------
517 //-------------------------------
519 sal_Bool SAL_CALL
CPreviewAdapter::getShowState()
521 return m_pImpl
->getShowState();
524 //-------------------------------
526 //-------------------------------
528 void SAL_CALL
CPreviewAdapter::setParent(HWND parent
)
530 m_pImpl
->setParent(parent
);
533 //-------------------------------
535 //-------------------------------
537 void SAL_CALL
CPreviewAdapter::notifyParentShow(bool bShow
)
539 m_pImpl
->notifyParentShow(bShow
);
542 //-------------------------------
544 //-------------------------------
546 void SAL_CALL
CPreviewAdapter::notifyParentSizeChanged()
548 m_pImpl
->notifyParentSizeChanged();
551 //-------------------------------
553 //-------------------------------
555 void SAL_CALL
CPreviewAdapter::notifyParentWindowPosChanged()
557 m_pImpl
->notifyParentWindowPosChanged();
560 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */