renaissance1: #i107215# Improved handling of transferables.

This commit is contained in:
Andre Fischer
2010-03-08 11:34:08 +01:00
parent c87f10322a
commit 4b83a7fe57
35 changed files with 1496 additions and 1903 deletions

View File

@@ -46,12 +46,12 @@
#include "controller/SlsScrollBarManager.hxx" #include "controller/SlsScrollBarManager.hxx"
#include "controller/SlsSelectionManager.hxx" #include "controller/SlsSelectionManager.hxx"
#include "controller/SlsSlotManager.hxx" #include "controller/SlsSlotManager.hxx"
#include "controller/SlsTransferable.hxx"
#include "model/SlideSorterModel.hxx" #include "model/SlideSorterModel.hxx"
#include "model/SlsPageEnumerationProvider.hxx" #include "model/SlsPageEnumerationProvider.hxx"
#include "model/SlsPageDescriptor.hxx" #include "model/SlsPageDescriptor.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsLayouter.hxx" #include "view/SlsLayouter.hxx"
#include "view/SlsViewOverlay.hxx"
#include "view/SlsFontProvider.hxx" #include "view/SlsFontProvider.hxx"
#include "view/SlsPageObjectLayouter.hxx" #include "view/SlsPageObjectLayouter.hxx"
#include "view/SlsPageObjectPainter.hxx" #include "view/SlsPageObjectPainter.hxx"
@@ -209,6 +209,7 @@ SlideSorterController::~SlideSorterController (void)
void SlideSorterController::Dispose (void) void SlideSorterController::Dispose (void)
{ {
mpInsertionIndicatorHandler->End(); mpInsertionIndicatorHandler->End();
mpSelectionManager.reset();
mpAnimator->Dispose(); mpAnimator->Dispose();
} }
@@ -439,11 +440,12 @@ bool SlideSorterController::Command (
// When there is no selection, then we show the insertion // When there is no selection, then we show the insertion
// indicator so that the user knows where a page insertion // indicator so that the user knows where a page insertion
// would take place. // would take place.
GetInsertionIndicatorHandler()->Start( GetInsertionIndicatorHandler()->Start(false);
GetInsertionIndicatorHandler()->UpdatePosition(
pWindow->PixelToLogic(rEvent.GetMousePosPixel()), pWindow->PixelToLogic(rEvent.GetMousePosPixel()),
InsertionIndicatorHandler::MoveMode, InsertionIndicatorHandler::MoveMode);
false); GetInsertionIndicatorHandler()->UpdateIndicatorIcon(
GetInsertionIndicatorHandler()->UpdateIndicatorIcon(); dynamic_cast<Transferable*>(SD_MOD()->pTransferClip));
} }
pWindow->ReleaseMouse(); pWindow->ReleaseMouse();
@@ -786,6 +788,9 @@ Rectangle SlideSorterController::Rearrange (bool bForce)
{ {
Rectangle aNewContentArea (maTotalWindowArea); Rectangle aNewContentArea (maTotalWindowArea);
if (aNewContentArea.IsEmpty())
return aNewContentArea;
SharedSdWindow pWindow (mrSlideSorter.GetContentWindow()); SharedSdWindow pWindow (mrSlideSorter.GetContentWindow());
if (pWindow) if (pWindow)
{ {
@@ -812,6 +817,9 @@ Rectangle SlideSorterController::Rearrange (bool bForce)
// Adapt the scroll bars to the new zoom factor of the browser // Adapt the scroll bars to the new zoom factor of the browser
// window and the arrangement of the page objects. // window and the arrangement of the page objects.
GetScrollBarManager().UpdateScrollBars(false, !bForce); GetScrollBarManager().UpdateScrollBars(false, !bForce);
// When there is a selection then keep it in the visible area.
GetSelectionManager()->MakeSelectionVisible();
} }
return aNewContentArea; return aNewContentArea;
@@ -845,7 +853,7 @@ void SlideSorterController::SetZoom (long int nZoom)
nZoom = 1; nZoom = 1;
{ {
SlideSorterView::DrawLock aLock (mrView); SlideSorterView::DrawLock aLock (mrSlideSorter);
mrView.GetLayouter().SetZoom(nZoom/100.0); mrView.GetLayouter().SetZoom(nZoom/100.0);
mrView.Layout(); mrView.Layout();
GetScrollBarManager().UpdateScrollBars (false); GetScrollBarManager().UpdateScrollBars (false);

View File

@@ -212,6 +212,25 @@ void Animator::RemoveAnimation (const Animator::AnimationId nId)
void Animator::RemoveAllAnimations (void)
{
::std::for_each(
maAnimations.begin(),
maAnimations.end(),
::boost::bind(
&Animation::Expire,
_1));
maAnimations.clear();
mnNextAnimationId = 0;
// No more animations => we do not have to suppress painting
// anymore.
mpDrawLock.reset();
}
bool Animator::ProcessAnimations (const double nTime) bool Animator::ProcessAnimations (const double nTime)
{ {
bool bExpired (false); bool bExpired (false);

View File

@@ -38,7 +38,6 @@
#include "model/SlsPageDescriptor.hxx" #include "model/SlsPageDescriptor.hxx"
#include "model/SlsPageEnumerationProvider.hxx" #include "model/SlsPageEnumerationProvider.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsViewOverlay.hxx"
#include "controller/SlideSorterController.hxx" #include "controller/SlideSorterController.hxx"
#include "controller/SlsInsertionIndicatorHandler.hxx" #include "controller/SlsInsertionIndicatorHandler.hxx"
#include "controller/SlsPageSelector.hxx" #include "controller/SlsPageSelector.hxx"
@@ -47,7 +46,8 @@
#include "controller/SlsScrollBarManager.hxx" #include "controller/SlsScrollBarManager.hxx"
#include "controller/SlsFocusManager.hxx" #include "controller/SlsFocusManager.hxx"
#include "controller/SlsSelectionManager.hxx" #include "controller/SlsSelectionManager.hxx"
#include "SlsTransferable.hxx" #include "controller/SlsTransferable.hxx"
#include "cache/SlsPageCache.hxx"
#include "ViewShellBase.hxx" #include "ViewShellBase.hxx"
#include "DrawViewShell.hxx" #include "DrawViewShell.hxx"
@@ -363,21 +363,40 @@ void Clipboard::CreateSlideTransferable (
maPagesToRemove.push_back (pDescriptor->GetPage()); maPagesToRemove.push_back (pDescriptor->GetPage());
} }
// Create a small set of representatives of the selection for which
// previews are included into the transferable so that an insertion
// indicator can be rendered.
aSelectedPages.Rewind();
::std::vector<Bitmap> aRepresentatives;
aRepresentatives.reserve(3);
::boost::shared_ptr<cache::PageCache> pPreviewCache (
mrSlideSorter.GetView().GetPreviewCache());
while (aSelectedPages.HasMoreElements())
{
model::SharedPageDescriptor pDescriptor (aSelectedPages.GetNextElement());
if ( ! pDescriptor || pDescriptor->GetPage()==NULL)
continue;
Bitmap aPreview (pPreviewCache->GetPreviewBitmap(pDescriptor->GetPage()).GetBitmap());
aRepresentatives.push_back(aPreview);
if (aRepresentatives.size() >= 3)
break;
}
if (aBookmarkList.Count() > 0) if (aBookmarkList.Count() > 0)
{ {
mrSlideSorter.GetView().BrkAction(); mrSlideSorter.GetView().BrkAction();
SdDrawDocument* pDocument = mrSlideSorter.GetModel().GetDocument(); SdDrawDocument* pDocument = mrSlideSorter.GetModel().GetDocument();
::boost::shared_ptr<SubstitutionHandler> pSubstitutionHandler; ::boost::shared_ptr<DragAndDropContext> pDragAndDropContext;
::rtl::Reference<SelectionFunction> pSelectionFunction ( ::rtl::Reference<SelectionFunction> pSelectionFunction (
mrSlideSorter.GetController().GetCurrentSelectionFunction()); mrSlideSorter.GetController().GetCurrentSelectionFunction());
if (pSelectionFunction.is()) if (pSelectionFunction.is())
pSubstitutionHandler = pSelectionFunction->GetSubstitutionHandler(); pDragAndDropContext = pSelectionFunction->GetDragAndDropContext();
SdTransferable* pTransferable = new Transferable ( SdTransferable* pTransferable = new Transferable (
pDocument, pDocument,
NULL, NULL,
FALSE, FALSE,
dynamic_cast<SlideSorterViewShell*>(mrSlideSorter.GetViewShell()), dynamic_cast<SlideSorterViewShell*>(mrSlideSorter.GetViewShell()),
pSubstitutionHandler); aRepresentatives);
if (bDrag) if (bDrag)
SD_MOD()->pTransferDrag = pTransferable; SD_MOD()->pTransferDrag = pTransferable;
@@ -540,11 +559,9 @@ sal_Int8 Clipboard::AcceptDrop (
// Show the insertion marker and the substitution for a drop. // Show the insertion marker and the substitution for a drop.
Point aPosition = pTargetWindow->PixelToLogic (rEvent.maPosPixel); Point aPosition = pTargetWindow->PixelToLogic (rEvent.maPosPixel);
view::ViewOverlay& rOverlay (mrSlideSorter.GetView().GetOverlay());
mrController.GetInsertionIndicatorHandler()->UpdatePosition( mrController.GetInsertionIndicatorHandler()->UpdatePosition(
aPosition, aPosition,
rEvent.maDragEvent.DropAction); rEvent.maDragEvent.DropAction);
rOverlay.GetSubstitutionOverlay()->SetPosition(aPosition);
// Scroll the window when the mouse reaches the window border. // Scroll the window when the mouse reaches the window border.
// mrController.GetScrollBarManager().AutoScroll (rEvent.maPosPixel); // mrController.GetScrollBarManager().AutoScroll (rEvent.maPosPixel);
@@ -629,7 +646,7 @@ sal_Int8 Clipboard::ExecuteDrop (
else else
{ {
// Handle a general drop operation. // Handle a general drop operation.
HandlePageDrop (*pDragTransferable); HandlePageDrop(*pDragTransferable);
nResult = rEvent.mnAction; nResult = rEvent.mnAction;
} }
} }

View File

@@ -51,8 +51,10 @@ using namespace ::com::sun::star::uno;
using namespace ::sd::slidesorter::model; using namespace ::sd::slidesorter::model;
namespace sd { namespace slidesorter { namespace controller { namespace sd { namespace slidesorter { namespace controller {
CurrentSlideManager::CurrentSlideManager (SlideSorter& rSlideSorter) CurrentSlideManager::CurrentSlideManager (SlideSorter& rSlideSorter)
: mrSlideSorter(rSlideSorter), : mrSlideSorter(rSlideSorter),
mnCurrentSlideIndex(-1), mnCurrentSlideIndex(-1),

View File

@@ -6,9 +6,6 @@
* *
* OpenOffice.org - a multi-platform office productivity suite * OpenOffice.org - a multi-platform office productivity suite
* *
* $RCSfile: SlsSelectionFunction.cxx,v $
* $Revision: 1.37 $
*
* This file is part of OpenOffice.org. * This file is part of OpenOffice.org.
* *
* OpenOffice.org is free software: you can redistribute it and/or modify * OpenOffice.org is free software: you can redistribute it and/or modify
@@ -30,59 +27,98 @@
#include "precompiled_sd.hxx" #include "precompiled_sd.hxx"
#include "SlsSubstitutionHandler.hxx" #include "SlsDragAndDropContext.hxx"
#include "SlideSorter.hxx" #include "SlideSorter.hxx"
#include "model/SlideSorterModel.hxx" #include "model/SlideSorterModel.hxx"
#include "model/SlsPageEnumerationProvider.hxx" #include "model/SlsPageEnumerationProvider.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsViewOverlay.hxx"
#include "controller/SlideSorterController.hxx" #include "controller/SlideSorterController.hxx"
#include "controller/SlsInsertionIndicatorHandler.hxx" #include "controller/SlsInsertionIndicatorHandler.hxx"
#include "controller/SlsScrollBarManager.hxx" #include "controller/SlsScrollBarManager.hxx"
#include "controller/SlsProperties.hxx" #include "controller/SlsProperties.hxx"
#include "controller/SlsSelectionFunction.hxx" #include "controller/SlsSelectionFunction.hxx"
#include "controller/SlsSelectionManager.hxx" #include "controller/SlsSelectionManager.hxx"
#include "controller/SlsTransferable.hxx"
#include "DrawDocShell.hxx"
#include "DrawDoc.hxx"
#include "app.hrc" #include "app.hrc"
#include <sfx2/bindings.hxx> #include <sfx2/bindings.hxx>
#include <boost/bind.hpp> #include <boost/bind.hpp>
namespace sd { namespace slidesorter { namespace controller { namespace sd { namespace slidesorter { namespace controller {
SubstitutionHandler::SubstitutionHandler ( DragAndDropContext::DragAndDropContext (
SlideSorter& rSlideSorter, SlideSorter& rSlideSorter,
const model::SharedPageDescriptor& rpHitDescriptor, const Transferable* pTransferable)
const Point& rMouseModelPosition)
: mpTargetSlideSorter(&rSlideSorter), : mpTargetSlideSorter(&rSlideSorter),
mpHitDescriptor(rpHitDescriptor),
mnInsertionIndex(-1) mnInsertionIndex(-1)
{ {
::std::vector<const SdPage*> aPages;
// No Drag-and-Drop for master pages. // No Drag-and-Drop for master pages.
if (rSlideSorter.GetModel().GetEditMode() != EM_PAGE) if (rSlideSorter.GetModel().GetEditMode() != EM_PAGE)
return; return;
view::ViewOverlay& rOverlay (rSlideSorter.GetView().GetOverlay());
if ( ! rOverlay.GetSubstitutionOverlay()->IsVisible())
{
// Show a new substitution for the selected page objects.
model::PageEnumeration aSelectedPages(
model::PageEnumerationProvider::CreateSelectedPagesEnumeration(
rSlideSorter.GetModel()));
rOverlay.GetSubstitutionOverlay()->SetIsVisible(true);
rSlideSorter.GetController().GetInsertionIndicatorHandler()->Start(
rMouseModelPosition,
InsertionIndicatorHandler::MoveMode,
true);
rSlideSorter.GetController().GetInsertionIndicatorHandler()->UpdateIndicatorIcon( rSlideSorter.GetController().GetInsertionIndicatorHandler()->UpdateIndicatorIcon(
aSelectedPages); dynamic_cast<Transferable*>(SD_MOD()->pTransferDrag));
}
void DragAndDropContext::GetPagesFromBookmarks (
::std::vector<const SdPage*>& rPages,
sal_Int32& rnSelectionCount,
DrawDocShell* pDocShell,
const List& rBookmarks) const
{
if (pDocShell == NULL)
return;
const SdDrawDocument* pDocument = pDocShell->GetDoc();
if (pDocument == NULL)
return;
for (ULONG nIndex=0,nCount=rBookmarks.Count(); nIndex<nCount; ++nIndex)
{
const String sPageName (*static_cast<String*>(rBookmarks.GetObject(nIndex)));
BOOL bIsMasterPage (FALSE);
const USHORT nPageIndex (pDocument->GetPageByName(sPageName, bIsMasterPage));
if (nPageIndex == SDRPAGE_NOTFOUND)
continue;
const SdPage* pPage = dynamic_cast<const SdPage*>(pDocument->GetPage(nPageIndex));
if (pPage != NULL)
rPages.push_back(pPage);
}
rnSelectionCount = rBookmarks.Count();
}
void DragAndDropContext::GetPagesFromSelection (
::std::vector<const SdPage*>& rPages,
sal_Int32& rnSelectionCount,
model::PageEnumeration& rSelection) const
{
// Show a new substitution for the selected page objects.
rnSelectionCount = 0;
while (rSelection.HasMoreElements())
{
model::SharedPageDescriptor pDescriptor (rSelection.GetNextElement());
if (rPages.size() < 3)
rPages.push_back(pDescriptor->GetPage());
++rnSelectionCount;
} }
} }
SubstitutionHandler::~SubstitutionHandler (void) DragAndDropContext::~DragAndDropContext (void)
{ {
if (mpTargetSlideSorter != NULL) if (mpTargetSlideSorter != NULL)
mpTargetSlideSorter->GetController().GetScrollBarManager().StopAutoScroll(); mpTargetSlideSorter->GetController().GetScrollBarManager().StopAutoScroll();
@@ -91,18 +127,14 @@ SubstitutionHandler::~SubstitutionHandler (void)
if (mpTargetSlideSorter != NULL) if (mpTargetSlideSorter != NULL)
{ {
view::ViewOverlay& rOverlay (mpTargetSlideSorter->GetView().GetOverlay());
rOverlay.GetSubstitutionOverlay()->SetIsVisible(false);
rOverlay.GetSubstitutionOverlay()->Clear();
mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()->End(); mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()->End();
} }
mpHitDescriptor.reset();
} }
void SubstitutionHandler::Dispose (void) void DragAndDropContext::Dispose (void)
{ {
mnInsertionIndex = -1; mnInsertionIndex = -1;
} }
@@ -110,7 +142,7 @@ void SubstitutionHandler::Dispose (void)
void SubstitutionHandler::UpdatePosition ( void DragAndDropContext::UpdatePosition (
const Point& rMousePosition, const Point& rMousePosition,
const InsertionIndicatorHandler::Mode eMode, const InsertionIndicatorHandler::Mode eMode,
const bool bAllowAutoScroll) const bool bAllowAutoScroll)
@@ -126,39 +158,28 @@ void SubstitutionHandler::UpdatePosition (
// constant while scrolling.) // constant while scrolling.)
SharedSdWindow pWindow (mpTargetSlideSorter->GetContentWindow()); SharedSdWindow pWindow (mpTargetSlideSorter->GetContentWindow());
const Point aMouseModelPosition (pWindow->PixelToLogic(rMousePosition)); const Point aMouseModelPosition (pWindow->PixelToLogic(rMousePosition));
::boost::shared_ptr<InsertionIndicatorHandler> pInsertionIndicatorHandler (
mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler());
if ( ! (bAllowAutoScroll if ( ! (bAllowAutoScroll
&& mpTargetSlideSorter->GetController().GetScrollBarManager().AutoScroll( && mpTargetSlideSorter->GetController().GetScrollBarManager().AutoScroll(
rMousePosition, rMousePosition,
::boost::bind( ::boost::bind(
&SubstitutionHandler::UpdatePosition, &DragAndDropContext::UpdatePosition, this, rMousePosition, eMode, false))))
this,
rMousePosition,
eMode,
false))))
{ {
view::ViewOverlay& rOverlay (mpTargetSlideSorter->GetView().GetOverlay()); pInsertionIndicatorHandler->UpdatePosition(aMouseModelPosition, eMode);
// Move the existing substitution to the new position.
rOverlay.GetSubstitutionOverlay()->SetPosition(aMouseModelPosition);
mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()->UpdatePosition(
aMouseModelPosition,
eMode);
// Remember the new insertion index. // Remember the new insertion index.
if (mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()->IsInsertionTrivial(eMode)) mnInsertionIndex = pInsertionIndicatorHandler->GetInsertionPageIndex();
if (pInsertionIndicatorHandler->IsInsertionTrivial(mnInsertionIndex, eMode))
mnInsertionIndex = -1; mnInsertionIndex = -1;
else
mnInsertionIndex = mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()
->GetInsertionPageIndex();
} }
} }
void SubstitutionHandler::Process (void) void DragAndDropContext::Process (void)
{ {
if (mpTargetSlideSorter == NULL) if (mpTargetSlideSorter == NULL)
return; return;
@@ -183,31 +204,21 @@ void SubstitutionHandler::Process (void)
void SubstitutionHandler::Show (void) void DragAndDropContext::Show (void)
{ {
if (mpTargetSlideSorter != NULL)
{
view::ViewOverlay& rOverlay (mpTargetSlideSorter->GetView().GetOverlay());
rOverlay.GetSubstitutionOverlay()->SetIsVisible(true);
}
} }
void SubstitutionHandler::Hide (void) void DragAndDropContext::Hide (void)
{ {
if (mpTargetSlideSorter != NULL)
{
view::ViewOverlay& rOverlay (mpTargetSlideSorter->GetView().GetOverlay());
rOverlay.GetSubstitutionOverlay()->SetIsVisible(false);
}
} }
void SubstitutionHandler::SetTargetSlideSorter ( void DragAndDropContext::SetTargetSlideSorter (
SlideSorter* pSlideSorter, SlideSorter* pSlideSorter,
const Point aMousePosition, const Point aMousePosition,
const InsertionIndicatorHandler::Mode eMode, const InsertionIndicatorHandler::Mode eMode,
@@ -223,9 +234,11 @@ void SubstitutionHandler::SetTargetSlideSorter (
if (mpTargetSlideSorter != NULL) if (mpTargetSlideSorter != NULL)
{ {
mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()->Start( mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()->Start(
aMousePosition,
eMode,
bIsOverSourceView); bIsOverSourceView);
mpTargetSlideSorter->GetController().GetInsertionIndicatorHandler()->UpdatePosition(
aMousePosition,
eMode);
} }
} }

View File

@@ -6,9 +6,6 @@
* *
* OpenOffice.org - a multi-platform office productivity suite * OpenOffice.org - a multi-platform office productivity suite
* *
* $RCSfile: SlsSelectionFunction.cxx,v $
* $Revision: 1.37 $
*
* This file is part of OpenOffice.org. * This file is part of OpenOffice.org.
* *
* OpenOffice.org is free software: you can redistribute it and/or modify * OpenOffice.org is free software: you can redistribute it and/or modify
@@ -34,8 +31,9 @@
#include <tools/gen.hxx> #include <tools/gen.hxx>
#include "model/SlsSharedPageDescriptor.hxx" #include "model/SlsSharedPageDescriptor.hxx"
#include "view/SlsViewOverlay.hxx"
#include "controller/SlsInsertionIndicatorHandler.hxx" #include "controller/SlsInsertionIndicatorHandler.hxx"
#include <vector>
namespace sd { namespace slidesorter { namespace sd { namespace slidesorter {
class SlideSorter; class SlideSorter;
@@ -45,27 +43,27 @@ class SlideSorter;
namespace sd { namespace slidesorter { namespace controller { namespace sd { namespace slidesorter { namespace controller {
class Transferable;
/** A SubstitutionHandler object handles the display of a number of selected
slides at the mouse position and the insertion or (with or without /** A DragAndDropContext object handles an active drag and drop operation.
removing the pages at their original position) when the object is When the mouse is moved from one slide sorter window to another the
destoyed. target SlideSorter object is exchanged accordingly.
*/ */
class SubstitutionHandler class DragAndDropContext
{ {
public: public:
/** Create a substitution display of the currently selected pages and /** Create a substitution display of the currently selected pages or,
use the given position as the anchor point. when provided, the pages in the transferable.
*/ */
SubstitutionHandler ( DragAndDropContext (
SlideSorter& rSlideSorter, SlideSorter& rSlideSorter,
const model::SharedPageDescriptor& rpHitDescriptor, const Transferable* pTransferable);
const Point& rMouseModelPosition); ~DragAndDropContext (void);
~SubstitutionHandler (void);
/** Call this method (for example as reaction to ESC key press) to avoid /** Call this method (for example as reaction to ESC key press) to avoid
processing (ie moving or inserting) the substition when the called processing (ie moving or inserting) the substition when the called
SubstitutionHandler object is destroyed. DragAndDropContext object is destroyed.
*/ */
void Dispose (void); void Dispose (void);
@@ -91,6 +89,16 @@ private:
model::SharedPageDescriptor mpHitDescriptor; model::SharedPageDescriptor mpHitDescriptor;
sal_Int32 mnInsertionIndex; sal_Int32 mnInsertionIndex;
void GetPagesFromBookmarks (
::std::vector<const SdPage*>& rPages,
sal_Int32& rnSelectionCount,
DrawDocShell* pDocShell,
const List& rBookmarks) const;
void GetPagesFromSelection (
::std::vector<const SdPage*>& rPages,
sal_Int32& rnSelectionCount,
model::PageEnumeration& rSelection) const;
/** Move the substitution display of the currently selected pages. /** Move the substitution display of the currently selected pages.
*/ */
void Process (void); void Process (void);

View File

@@ -33,8 +33,8 @@
#include "controller/SlsInsertionIndicatorHandler.hxx" #include "controller/SlsInsertionIndicatorHandler.hxx"
#include "controller/SlsProperties.hxx" #include "controller/SlsProperties.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsViewOverlay.hxx"
#include "view/SlsLayouter.hxx" #include "view/SlsLayouter.hxx"
#include "view/SlsInsertionIndicatorOverlay.hxx"
#include "model/SlideSorterModel.hxx" #include "model/SlideSorterModel.hxx"
#include "model/SlsPageEnumerationProvider.hxx" #include "model/SlsPageEnumerationProvider.hxx"
#include <com/sun/star/datatransfer/dnd/DNDConstants.hpp> #include <com/sun/star/datatransfer/dnd/DNDConstants.hpp>
@@ -49,10 +49,8 @@ namespace sd { namespace slidesorter { namespace controller {
InsertionIndicatorHandler::InsertionIndicatorHandler (SlideSorter& rSlideSorter) InsertionIndicatorHandler::InsertionIndicatorHandler (SlideSorter& rSlideSorter)
: mrSlideSorter(rSlideSorter), : mrSlideSorter(rSlideSorter),
mpInsertAnimator(), mpInsertAnimator(),
mpInsertionIndicatorOverlay( mpInsertionIndicatorOverlay(new view::InsertionIndicatorOverlay(rSlideSorter)),
mrSlideSorter.GetView().GetOverlay().GetInsertionIndicatorOverlay()), maInsertPosition(),
mnInsertionIndex(-1),
maVisualInsertionIndices(-1,-1),
meMode(MoveMode), meMode(MoveMode),
mbIsActive(false), mbIsActive(false),
mbIsReadOnly(mrSlideSorter.GetModel().IsReadOnly()), mbIsReadOnly(mrSlideSorter.GetModel().IsReadOnly()),
@@ -71,10 +69,7 @@ InsertionIndicatorHandler::~InsertionIndicatorHandler (void)
void InsertionIndicatorHandler::Start ( void InsertionIndicatorHandler::Start (const bool bIsOverSourceView)
const Point& rMouseModelPosition,
const Mode eMode,
const bool bIsOverSourceView)
{ {
if (mbIsActive) if (mbIsActive)
{ {
@@ -85,8 +80,6 @@ void InsertionIndicatorHandler::Start (
if (mbIsReadOnly) if (mbIsReadOnly)
return; return;
SetPosition(rMouseModelPosition, eMode);
mbIsActive = true; mbIsActive = true;
mbIsOverSourceView = bIsOverSourceView; mbIsOverSourceView = bIsOverSourceView;
} }
@@ -94,19 +87,27 @@ void InsertionIndicatorHandler::Start (
void InsertionIndicatorHandler::UpdateIndicatorIcon ( void InsertionIndicatorHandler::End (void)
model::PageEnumeration& rEnumeration)
{ {
mpInsertionIndicatorOverlay->Create(rEnumeration); if ( ! mbIsActive)
maIconSize = mpInsertionIndicatorOverlay->GetSize(); return;
if (mbIsReadOnly)
return;
GetInsertAnimator()->Reset();
mbIsActive = false;
mpInsertionIndicatorOverlay->Hide();
} }
void InsertionIndicatorHandler::UpdateIndicatorIcon (void) void InsertionIndicatorHandler::UpdateIndicatorIcon (const Transferable* pTransferable)
{ {
mpInsertionIndicatorOverlay->Create(); mpInsertionIndicatorOverlay->Create(pTransferable);
maIconSize = mpInsertionIndicatorOverlay->GetSize();
} }
@@ -152,24 +153,6 @@ void InsertionIndicatorHandler::UpdatePosition (
void InsertionIndicatorHandler::End (void)
{
if ( ! mbIsActive)
return;
if (mbIsReadOnly)
return;
GetInsertAnimator()->SetInsertPosition(-1, Pair(-1,-1), Size(0,0));
mbIsActive = false;
mpInsertionIndicatorOverlay->SetIsVisible(false);
GetInsertAnimator()->Reset();
}
bool InsertionIndicatorHandler::IsActive (void) const bool InsertionIndicatorHandler::IsActive (void) const
{ {
return mbIsActive; return mbIsActive;
@@ -183,7 +166,7 @@ sal_Int32 InsertionIndicatorHandler::GetInsertionPageIndex (void) const
if (mbIsReadOnly) if (mbIsReadOnly)
return -1; return -1;
else else
return mnInsertionIndex; return maInsertPosition.GetIndex();
} }
@@ -197,54 +180,31 @@ void InsertionIndicatorHandler::SetPosition (
view::Layouter& rLayouter (mrSlideSorter.GetView().GetLayouter()); view::Layouter& rLayouter (mrSlideSorter.GetView().GetLayouter());
USHORT nPageCount ((USHORT)mrSlideSorter.GetModel().GetPageCount()); USHORT nPageCount ((USHORT)mrSlideSorter.GetModel().GetPageCount());
sal_Int32 nInsertionIndex (mnInsertionIndex); const view::InsertPosition aInsertPosition (rLayouter.GetInsertPosition(
Pair aVisualInsertionIndices (maVisualInsertionIndices); rPoint,
if (rLayouter.GetColumnCount() == 1) maIconSize));
{
// Pages are placed in a single column. Insertion indicator is
// placed between rows.
nInsertionIndex = rLayouter.GetVerticalInsertionIndex(rPoint);
aVisualInsertionIndices = Pair(nInsertionIndex, -1);
}
else
{
// Pages are placed in a grid. Insertion indicator is placed
// between columns.
aVisualInsertionIndices = rLayouter.GetGridInsertionIndices(rPoint);
nInsertionIndex = aVisualInsertionIndices.A() * rLayouter.GetColumnCount()
+ aVisualInsertionIndices.B();
if (aVisualInsertionIndices.B() == rLayouter.GetColumnCount())
--nInsertionIndex;
}
if (mnInsertionIndex != nInsertionIndex if (maInsertPosition != aInsertPosition
|| maVisualInsertionIndices != aVisualInsertionIndices
|| meMode != eMode || meMode != eMode
|| ! mpInsertionIndicatorOverlay->IsVisible()) || ! mpInsertionIndicatorOverlay->IsVisible())
{ {
mnInsertionIndex = nInsertionIndex; maInsertPosition = aInsertPosition;
maVisualInsertionIndices = aVisualInsertionIndices;
meMode = eMode; meMode = eMode;
mbIsInsertionTrivial = IsInsertionTrivial(eMode); mbIsInsertionTrivial = IsInsertionTrivial(maInsertPosition.GetIndex(), eMode);
const Point aIndicatorLocation ( if (maInsertPosition.GetIndex()>=0 && ! mbIsInsertionTrivial)
rLayouter.GetInsertionIndicatorLocation(
maVisualInsertionIndices,
maIconSize));
mpInsertionIndicatorOverlay->SetLocation(aIndicatorLocation);
if (mnInsertionIndex>=0 && ! mbIsInsertionTrivial)
{ {
mpInsertionIndicatorOverlay->SetLocation(maInsertPosition.GetLocation());
GetInsertAnimator()->SetInsertPosition( GetInsertAnimator()->SetInsertPosition(
mnInsertionIndex, maInsertPosition,
maVisualInsertionIndices,
maIconSize); maIconSize);
mpInsertionIndicatorOverlay->SetIsVisible(true); mpInsertionIndicatorOverlay->Show();
} }
else else
{ {
GetInsertAnimator()->Reset(); GetInsertAnimator()->Reset();
mpInsertionIndicatorOverlay->SetIsVisible(false); mpInsertionIndicatorOverlay->Hide();
} }
} }
} }
@@ -262,7 +222,9 @@ void InsertionIndicatorHandler::SetPosition (
bool InsertionIndicatorHandler::IsInsertionTrivial (const Mode eMode) const bool InsertionIndicatorHandler::IsInsertionTrivial (
const sal_Int32 nInsertionIndex,
const Mode eMode) const
{ {
if (eMode == CopyMode) if (eMode == CopyMode)
return false; return false;
@@ -302,7 +264,7 @@ bool InsertionIndicatorHandler::IsInsertionTrivial (const Mode eMode) const
// to check that the insertion position is not directly in front or // to check that the insertion position is not directly in front or
// directly behind the selection and thus moving the selection there // directly behind the selection and thus moving the selection there
// would not change the model. // would not change the model.
if (mnInsertionIndex<nFirstIndex || mnInsertionIndex>(nLastIndex+1)) if (nInsertionIndex<nFirstIndex || nInsertionIndex>(nLastIndex+1))
return false; return false;
return true; return true;

View File

@@ -38,7 +38,6 @@
#include "model/SlsPageDescriptor.hxx" #include "model/SlsPageDescriptor.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsLayouter.hxx" #include "view/SlsLayouter.hxx"
#include "view/SlsViewOverlay.hxx"
#include "view/SlsTheme.hxx" #include "view/SlsTheme.hxx"
#include "Window.hxx" #include "Window.hxx"
#include "sdpage.hxx" #include "sdpage.hxx"

View File

@@ -34,8 +34,8 @@
#include "SlideSorter.hxx" #include "SlideSorter.hxx"
#include "SlideSorterViewShell.hxx" #include "SlideSorterViewShell.hxx"
#include "SlsSubstitutionHandler.hxx" #include "SlsDragAndDropContext.hxx"
#include "SlsTransferable.hxx" #include "controller/SlsTransferable.hxx"
#include "controller/SlideSorterController.hxx" #include "controller/SlideSorterController.hxx"
#include "controller/SlsPageSelector.hxx" #include "controller/SlsPageSelector.hxx"
#include "controller/SlsFocusManager.hxx" #include "controller/SlsFocusManager.hxx"
@@ -50,7 +50,6 @@
#include "model/SlsPageDescriptor.hxx" #include "model/SlsPageDescriptor.hxx"
#include "model/SlsPageEnumerationProvider.hxx" #include "model/SlsPageEnumerationProvider.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsViewOverlay.hxx"
#include "view/SlsLayouter.hxx" #include "view/SlsLayouter.hxx"
#include "view/SlsPageObjectLayouter.hxx" #include "view/SlsPageObjectLayouter.hxx"
#include "framework/FrameworkHelper.hxx" #include "framework/FrameworkHelper.hxx"
@@ -94,14 +93,13 @@ static const sal_uInt32 OVER_FADE_INDICATOR (0x00040000);
static const sal_uInt32 OVER_BUTTON (0x00080000); static const sal_uInt32 OVER_BUTTON (0x00080000);
static const sal_uInt32 SHIFT_MODIFIER (0x00100000); static const sal_uInt32 SHIFT_MODIFIER (0x00100000);
static const sal_uInt32 CONTROL_MODIFIER (0x00200000); static const sal_uInt32 CONTROL_MODIFIER (0x00200000);
static const sal_uInt32 SUBSTITUTION_VISIBLE (0x01000000); static const sal_uInt32 DRAG_ACTIVE (0x01000000);
static const sal_uInt32 RECTANGLE_VISIBLE (0x02000000); static const sal_uInt32 MULTI_SELECTOR (0x02000000);
static const sal_uInt32 KEY_EVENT (0x10000000); static const sal_uInt32 KEY_EVENT (0x10000000);
// Some absent events are defined so they can be expressed explicitly. // Some absent events are defined so they can be expressed explicitly.
static const sal_uInt32 NO_MODIFIER (0x00000000); static const sal_uInt32 NO_MODIFIER (0x00000000);
static const sal_uInt32 SUBSTITUTION_NOT_VISIBLE (0x00000000);
static const sal_uInt32 NOT_OVER_PAGE (0x00000000); static const sal_uInt32 NOT_OVER_PAGE (0x00000000);
// Masks // Masks
@@ -150,25 +148,6 @@ protected:
namespace { namespace {
class RectangleSelector
: public SelectionFunction::MouseMultiSelector
{
public:
/** Start a rectangle selection at the given position.
*/
RectangleSelector (
SlideSorter& rSlideSorter,
const Point& rMouseModelPosition);
virtual ~RectangleSelector (void);
protected:
virtual void UpdateModelPosition (const Point& rMouseModelPosition);
/** Select all pages that lie completly in the selection rectangle.
*/
virtual void UpdateSelection (void);
};
class RangeSelector class RangeSelector
: public SelectionFunction::MouseMultiSelector : public SelectionFunction::MouseMultiSelector
{ {
@@ -205,11 +184,12 @@ class SelectionFunction::EventDescriptor
public: public:
Point maMousePosition; Point maMousePosition;
Point maMouseModelPosition; Point maMouseModelPosition;
::boost::weak_ptr<model::PageDescriptor> mpHitDescriptor; model::SharedPageDescriptor mpHitDescriptor;
SdrPage* mpHitPage; SdrPage* mpHitPage;
sal_uInt32 mnEventCode; sal_uInt32 mnEventCode;
sal_Int32 mnButtonIndex; sal_Int32 mnButtonIndex;
InsertionIndicatorHandler::Mode meDragMode; InsertionIndicatorHandler::Mode meDragMode;
bool mbMakeSelectionVisible;
EventDescriptor ( EventDescriptor (
sal_uInt32 nEventType, sal_uInt32 nEventType,
@@ -244,14 +224,13 @@ SelectionFunction::SelectionFunction (
mbDragSelection(false), mbDragSelection(false),
maInsertionMarkerBox(), maInsertionMarkerBox(),
mbProcessingMouseButtonDown(false), mbProcessingMouseButtonDown(false),
mpSubstitutionHandler(), mpDragAndDropContext(),
mpMouseMultiSelector(), mpMouseMultiSelector(),
mnButtonDownPageIndex(-1), mnButtonDownPageIndex(-1),
mnButtonDownButtonIndex(-1), mnButtonDownButtonIndex(-1),
mbIsDeselectionPending(false), mbIsDeselectionPending(false),
mnShiftKeySelectionAnchor(-1) mnShiftKeySelectionAnchor(-1)
{ {
aDragTimer.SetTimeoutHdl(LINK(this, SelectionFunction, DragSlideHdl));
} }
@@ -259,7 +238,6 @@ SelectionFunction::SelectionFunction (
SelectionFunction::~SelectionFunction (void) SelectionFunction::~SelectionFunction (void)
{ {
aDragTimer.Stop();
} }
@@ -297,15 +275,6 @@ BOOL SelectionFunction::MouseMove (const MouseEvent& rEvent)
{ {
Point aMousePosition (rEvent.GetPosPixel()); Point aMousePosition (rEvent.GetPosPixel());
// Allow one mouse move before the drag timer is disabled.
if (aDragTimer.IsActive())
{
if (bFirstMouseMove)
bFirstMouseMove = FALSE;
else
aDragTimer.Stop();
}
UpdatePageUnderMouse(aMousePosition, (rEvent.GetButtons() & MOUSE_LEFT)!=0); UpdatePageUnderMouse(aMousePosition, (rEvent.GetButtons() & MOUSE_LEFT)!=0);
// Detect the mouse leaving the window. When not button is pressed then // Detect the mouse leaving the window. When not button is pressed then
@@ -314,12 +283,10 @@ BOOL SelectionFunction::MouseMove (const MouseEvent& rEvent)
if (rEvent.IsLeaveWindow() if (rEvent.IsLeaveWindow()
|| ! Rectangle(Point(0,0),mpWindow->GetOutputSizePixel()).IsInside(aMousePosition)) || ! Rectangle(Point(0,0),mpWindow->GetOutputSizePixel()).IsInside(aMousePosition))
{ {
if (mpSubstitutionHandler) if (mpDragAndDropContext)
{ {
// Mouse left the window with pressed left button. Make it a drag. mpDragAndDropContext->Hide();
StartDrag(aMousePosition, InsertionIndicatorHandler::MoveMode); mpDragAndDropContext.reset();
mpSubstitutionHandler->Hide();
mpSubstitutionHandler.reset();
} }
mrSlideSorter.GetView().SetPageUnderMouse(model::SharedPageDescriptor()); mrSlideSorter.GetView().SetPageUnderMouse(model::SharedPageDescriptor());
} }
@@ -347,9 +314,6 @@ BOOL SelectionFunction::MouseButtonUp (const MouseEvent& rEvent)
// #95491# remember button state for creation of own MouseEvents // #95491# remember button state for creation of own MouseEvents
SetMouseButtonCode (rEvent.GetButtons()); SetMouseButtonCode (rEvent.GetButtons());
if (aDragTimer.IsActive())
aDragTimer.Stop();
ProcessMouseEvent(BUTTON_UP, rEvent); ProcessMouseEvent(BUTTON_UP, rEvent);
mbProcessingMouseButtonDown = false; mbProcessingMouseButtonDown = false;
@@ -365,39 +329,26 @@ void SelectionFunction::MouseDragged (const AcceptDropEvent& rEvent)
{ {
if (rEvent.mbLeaving) if (rEvent.mbLeaving)
{ {
if (mpSubstitutionHandler) if (mpDragAndDropContext)
{ {
// Disconnect the substitution handler from this selection function. // Disconnect the substitution handler from this selection function.
mpSubstitutionHandler->Hide(); mpDragAndDropContext->Hide();
mpSubstitutionHandler->SetTargetSlideSorter(); mpDragAndDropContext->SetTargetSlideSorter();
mpSubstitutionHandler.reset(); mpDragAndDropContext.reset();
} }
} }
else if ( ! mpSubstitutionHandler) else if ( ! mpDragAndDropContext)
{ {
const SdTransferable* pDragTransferable = SD_MOD()->pTransferDrag; const SdTransferable* pDragTransferable = SD_MOD()->pTransferDrag;
const Transferable* pSlideSorterTransferable
= dynamic_cast<const Transferable*>(pDragTransferable);
if (pSlideSorterTransferable != NULL)
{
// Connect the substitution handler to this selection function. // Connect the substitution handler to this selection function.
mpSubstitutionHandler = pSlideSorterTransferable->GetSubstitutionHandler(); mpDragAndDropContext.reset(new DragAndDropContext(
if (mpSubstitutionHandler)
{
mpSubstitutionHandler->SetTargetSlideSorter(
&mrSlideSorter,
rEvent.maPosPixel,
InsertionIndicatorHandler::GetModeFromDndAction(rEvent.mnAction),
pSlideSorterTransferable->GetView() == &mrSlideSorter.GetView());
mpSubstitutionHandler->Show();
}
}
else
mpSubstitutionHandler.reset(
new SubstitutionHandler(
mrSlideSorter, mrSlideSorter,
mrSlideSorter.GetController().GetPageAt(rEvent.maPosPixel), dynamic_cast<const Transferable*>(pDragTransferable)));
rEvent.maPosPixel)); mrController.GetInsertionIndicatorHandler()->Start(
pDragTransferable->GetView()==&mrSlideSorter.GetView());
mpDragAndDropContext->UpdatePosition(
rEvent.maPosPixel,
InsertionIndicatorHandler::GetModeFromDndAction(rEvent.mnAction));
} }
// 1. Compute some frequently used values relating to the event. // 1. Compute some frequently used values relating to the event.
@@ -405,23 +356,21 @@ void SelectionFunction::MouseDragged (const AcceptDropEvent& rEvent)
new EventDescriptor(rEvent, mrSlideSorter)); new EventDescriptor(rEvent, mrSlideSorter));
// 2. Detect whether we are dragging pages or dragging a selection rectangle. // 2. Detect whether we are dragging pages or dragging a selection rectangle.
view::ViewOverlay& rOverlay (mrSlideSorter.GetView().GetOverlay()); if (mpDragAndDropContext)
if (mpSubstitutionHandler) pEventDescriptor->mnEventCode |= DRAG_ACTIVE;
pEventDescriptor->mnEventCode |= SUBSTITUTION_VISIBLE;
if (mpMouseMultiSelector) if (mpMouseMultiSelector)
pEventDescriptor->mnEventCode |= RECTANGLE_VISIBLE; pEventDescriptor->mnEventCode |= MULTI_SELECTOR;
// 3. Set the drag mode. // 3. Set the drag mode.
pEventDescriptor->SetDragMode( pEventDescriptor->SetDragMode(
InsertionIndicatorHandler::GetModeFromDndAction(rEvent.mnAction)); InsertionIndicatorHandler::GetModeFromDndAction(rEvent.mnAction));
// 4. Process the event. // 4. Process the event.
EventPreprocessing(*pEventDescriptor); if ( ! ProcessEvent(*pEventDescriptor))
if ( ! EventProcessing(*pEventDescriptor))
{ {
OSL_TRACE ("can not handle event code %x", pEventDescriptor->mnEventCode); OSL_TRACE ("can not handle event code %x", pEventDescriptor->mnEventCode);
} }
EventPostprocessing(*pEventDescriptor); PostProcessEvent(*pEventDescriptor);
} }
@@ -429,10 +378,10 @@ void SelectionFunction::MouseDragged (const AcceptDropEvent& rEvent)
void SelectionFunction::NotifyDragFinished (void) void SelectionFunction::NotifyDragFinished (void)
{ {
if (mpSubstitutionHandler) if (mpDragAndDropContext)
{ {
mpSubstitutionHandler->Dispose(); mpDragAndDropContext->Dispose();
mpSubstitutionHandler.reset(); mpDragAndDropContext.reset();
} }
mrController.GetInsertionIndicatorHandler()->End(); mrController.GetInsertionIndicatorHandler()->End();
} }
@@ -440,9 +389,9 @@ void SelectionFunction::NotifyDragFinished (void)
::boost::shared_ptr<SubstitutionHandler> SelectionFunction::GetSubstitutionHandler (void) const ::boost::shared_ptr<DragAndDropContext> SelectionFunction::GetDragAndDropContext (void) const
{ {
return mpSubstitutionHandler; return mpDragAndDropContext;
} }
@@ -483,13 +432,13 @@ BOOL SelectionFunction::KeyInput (const KeyEvent& rEvent)
// operation then stop that. Otherwise transfer the focus to // operation then stop that. Otherwise transfer the focus to
// the tool box. // the tool box.
if ( ! (mpSubstitutionHandler || mpMouseMultiSelector)) if ( ! (mpDragAndDropContext || mpMouseMultiSelector))
rFocusManager.SetFocusToToolBox(); rFocusManager.SetFocusToToolBox();
if (mpSubstitutionHandler) if (mpDragAndDropContext)
{ {
mpSubstitutionHandler->Dispose(); mpDragAndDropContext->Dispose();
mpSubstitutionHandler.reset(); mpDragAndDropContext.reset();
} }
if (mpMouseMultiSelector) if (mpMouseMultiSelector)
{ {
@@ -734,53 +683,26 @@ void SelectionFunction::DoPaste (void)
void SelectionFunction::StartDragTimer (void)
{
if ( ! mrSlideSorter.GetProperties()->IsUIReadOnly())
{
bFirstMouseMove = TRUE;
aDragTimer.Start();
}
}
IMPL_LINK( SelectionFunction, DragSlideHdl, Timer*, EMPTYARG )
{
StartDrag(aMDPos, InsertionIndicatorHandler::MoveMode);
return 0;
}
void SelectionFunction::StartDrag ( void SelectionFunction::StartDrag (
const Point& rMousePosition, const Point& rMousePosition,
const InsertionIndicatorHandler::Mode eMode) const InsertionIndicatorHandler::Mode eMode)
{ {
if (mbPageHit if ( ! mrSlideSorter.GetProperties()->IsUIReadOnly())
&& ! mrSlideSorter.GetProperties()->IsUIReadOnly())
{ {
if ( ! mpSubstitutionHandler)
mpSubstitutionHandler.reset(
new SubstitutionHandler(
mrSlideSorter,
mrSlideSorter.GetController().GetPageAt(rMousePosition),
rMousePosition));
else
mpSubstitutionHandler->UpdatePosition(
rMousePosition,
eMode);
mbPageHit = false;
mpWindow->ReleaseMouse();
if (mrSlideSorter.GetViewShell() != NULL) if (mrSlideSorter.GetViewShell() != NULL)
{ {
SlideSorterViewShell* pSlideSorterViewShell SlideSorterViewShell* pSlideSorterViewShell
= dynamic_cast<SlideSorterViewShell*>(mrSlideSorter.GetViewShell()); = dynamic_cast<SlideSorterViewShell*>(mrSlideSorter.GetViewShell());
pSlideSorterViewShell->StartDrag (rMousePosition, mpWindow); pSlideSorterViewShell->StartDrag (rMousePosition, mpWindow);
} }
if ( ! mpDragAndDropContext)
{
mpDragAndDropContext.reset(new DragAndDropContext(mrSlideSorter, NULL));
mrController.GetInsertionIndicatorHandler()->Start(true);
}
mpDragAndDropContext->UpdatePosition(rMousePosition, eMode);
mpWindow->ReleaseMouse();
} }
} }
@@ -802,7 +724,7 @@ void SelectionFunction::UpdatePageUnderMouse (
{ {
// In some modes (dragging, moving) the mouse over indicator is only // In some modes (dragging, moving) the mouse over indicator is only
// annoying. Turn it off in these cases. // annoying. Turn it off in these cases.
if (mpSubstitutionHandler || mpMouseMultiSelector) if (mpDragAndDropContext || mpMouseMultiSelector)
mrSlideSorter.GetView().SetPageUnderMouse(model::SharedPageDescriptor()); mrSlideSorter.GetView().SetPageUnderMouse(model::SharedPageDescriptor());
else else
mrSlideSorter.GetView().UpdatePageUnderMouse(rMousePosition, bIsMouseButtonDown); mrSlideSorter.GetView().UpdatePageUnderMouse(rMousePosition, bIsMouseButtonDown);
@@ -888,19 +810,6 @@ void SelectionFunction::GotoNextPage (int nOffset)
void SelectionFunction::ClearOverlays (void)
{
view::ViewOverlay& rOverlay (mrSlideSorter.GetView().GetOverlay());
rOverlay.GetSubstitutionOverlay()->SetIsVisible(false);
rOverlay.GetSubstitutionOverlay()->Clear();
mrController.GetInsertionIndicatorHandler()->End();
}
void SelectionFunction::ProcessMouseEvent (sal_uInt32 nEventType, const MouseEvent& rEvent) void SelectionFunction::ProcessMouseEvent (sal_uInt32 nEventType, const MouseEvent& rEvent)
{ {
// #95491# remember button state for creation of own MouseEvents // #95491# remember button state for creation of own MouseEvents
@@ -916,15 +825,11 @@ void SelectionFunction::ProcessMouseEvent (sal_uInt32 nEventType, const MouseEve
= EncodeMouseEvent(*pEventDescriptor, rEvent) | EncodeState(*pEventDescriptor); = EncodeMouseEvent(*pEventDescriptor, rEvent) | EncodeState(*pEventDescriptor);
// 3. Process the event. // 3. Process the event.
EventPreprocessing(*pEventDescriptor); if ( ! ProcessEvent(*pEventDescriptor))
if ( ! EventProcessing(*pEventDescriptor))
{ {
OSL_TRACE ("can not handle event code %x", pEventDescriptor->mnEventCode); OSL_TRACE ("can not handle event code %x", pEventDescriptor->mnEventCode);
} }
EventPostprocessing(*pEventDescriptor); PostProcessEvent(*pEventDescriptor);
if (nEventType == BUTTON_UP)
mbPageHit = false;
} }
@@ -998,10 +903,9 @@ sal_uInt32 SelectionFunction::EncodeState (
sal_uInt32 nEventCode (0); sal_uInt32 nEventCode (0);
// Detect whether the event has happened over a page object. // Detect whether the event has happened over a page object.
if (rDescriptor.mpHitPage != NULL && ! rDescriptor.mpHitDescriptor.expired()) if (rDescriptor.mpHitPage != NULL && rDescriptor.mpHitDescriptor)
{ {
model::SharedPageDescriptor pHitDescriptor (rDescriptor.mpHitDescriptor); if (rDescriptor.mpHitDescriptor->HasState(model::PageDescriptor::ST_Selected))
if (pHitDescriptor->HasState(model::PageDescriptor::ST_Selected))
nEventCode |= OVER_SELECTED_PAGE; nEventCode |= OVER_SELECTED_PAGE;
else else
nEventCode |= OVER_UNSELECTED_PAGE; nEventCode |= OVER_UNSELECTED_PAGE;
@@ -1013,10 +917,10 @@ sal_uInt32 SelectionFunction::EncodeState (
} }
// Detect whether we are dragging pages or dragging a selection rectangle. // Detect whether we are dragging pages or dragging a selection rectangle.
if (mpSubstitutionHandler) if (mpDragAndDropContext)
nEventCode |= SUBSTITUTION_VISIBLE; nEventCode |= DRAG_ACTIVE;
if (mpMouseMultiSelector) if (mpMouseMultiSelector)
nEventCode |= RECTANGLE_VISIBLE; nEventCode |= MULTI_SELECTOR;
return nEventCode; return nEventCode;
} }
@@ -1035,25 +939,9 @@ void SelectionFunction::ProcessKeyEvent (const KeyEvent& rEvent)
= EncodeKeyEvent(*pEventDescriptor, rEvent) | EncodeState(*pEventDescriptor); = EncodeKeyEvent(*pEventDescriptor, rEvent) | EncodeState(*pEventDescriptor);
// 3. Process the event. // 3. Process the event.
EventPreprocessing(*pEventDescriptor); if ( ! ProcessEvent(*pEventDescriptor))
if ( ! EventProcessing(*pEventDescriptor))
OSL_TRACE ("can not handle event code %x", pEventDescriptor->mnEventCode); OSL_TRACE ("can not handle event code %x", pEventDescriptor->mnEventCode);
EventPostprocessing(*pEventDescriptor); PostProcessEvent(*pEventDescriptor);
}
void SelectionFunction::EventPreprocessing (const EventDescriptor& rDescriptor)
{
// Some general processing that is not specific to the exact event code.
if (rDescriptor.mnEventCode & BUTTON_DOWN)
mbPageHit = (rDescriptor.mpHitPage!=NULL);
// Set the focus to the slide under the mouse.
// if (rDescriptor.mpHitPage != NULL)
//
// mrController.GetFocusManager().FocusPage((rDescriptor.mpHitPage->GetPageNum()-1)/2);
} }
@@ -1069,66 +957,91 @@ bool Match (
bool SelectionFunction::EventProcessing (const EventDescriptor& rDescriptor) bool SelectionFunction::ProcessEvent (EventDescriptor& rDescriptor)
{ {
// Define some macros to make the following switch statement more readable. // Define some macros to make the following switch statement more readable.
#define ANY_MODIFIER(code) \ #define ANY_MODIFIER(code) \
code|NO_MODIFIER: \ code|NO_MODIFIER: \
case code|SHIFT_MODIFIER: \ case code|SHIFT_MODIFIER: \
case code|CONTROL_MODIFIER case code|CONTROL_MODIFIER
#define ANY_PAGE(code) \
code|NOT_OVER_PAGE: \
case code|OVER_UNSELECTED_PAGE: \
case code|OVER_SELECTED_PAGE
#define ANY_PAGE_AND_MODIFIER(code) \
ANY_PAGE(code|NO_MODIFIER): \
case ANY_PAGE(code|SHIFT_MODIFIER): \
case ANY_PAGE(code|CONTROL_MODIFIER)
bool bResult (true); bool bResult (true);
bool bMakeSelectionVisible (true);
mrController.GetPageSelector().DisableBroadcasting(); mrController.GetPageSelector().DisableBroadcasting();
PageSelector::UpdateLock aLock (mrSlideSorter); PageSelector::UpdateLock aLock (mrSlideSorter);
// 2b. With the event code determine the type of operation with which to // With the event code determine the type of operation with which to
// react to the event. // react to the event.
// Acquire a shared_ptr to the hit page descriptor. switch (rDescriptor.mnEventCode & (DRAG_ACTIVE | MULTI_SELECTOR))
model::SharedPageDescriptor pHitDescriptor;
if ( ! rDescriptor.mpHitDescriptor.expired())
pHitDescriptor = model::SharedPageDescriptor(rDescriptor.mpHitDescriptor);
switch (rDescriptor.mnEventCode & (SUBSTITUTION_VISIBLE | RECTANGLE_VISIBLE))
{ {
case SUBSTITUTION_VISIBLE: case DRAG_ACTIVE:
OSL_ASSERT(mpSubstitutionHandler); ProcessEventWhileDragActive(rDescriptor);
break;
case MULTI_SELECTOR:
ProcessEventWhileMultiSelectorActive(rDescriptor);
break;
default:
OSL_ASSERT(!mpMouseMultiSelector);
OSL_ASSERT(!mpDragAndDropContext);
switch (rDescriptor.mnEventCode & (BUTTON_DOWN | BUTTON_UP | MOUSE_MOTION))
{
case BUTTON_DOWN:
ProcessButtonDownEvent(rDescriptor);
break;
case BUTTON_UP:
ProcessButtonUpEvent(rDescriptor);
break;
case MOUSE_MOTION:
ProcessMouseMotionEvent(rDescriptor);
break;
}
}
mrController.GetPageSelector().EnableBroadcasting(rDescriptor.mbMakeSelectionVisible);
return bResult;
}
void SelectionFunction::ProcessEventWhileDragActive (EventDescriptor& rDescriptor)
{
OSL_ASSERT(mpDragAndDropContext);
// The substitution is visible. Handle events accordingly. // The substitution is visible. Handle events accordingly.
if (Match(rDescriptor.mnEventCode, MOUSE_MOTION | LEFT_BUTTON | SINGLE_CLICK)) if (Match(rDescriptor.mnEventCode, MOUSE_MOTION | LEFT_BUTTON | SINGLE_CLICK))
{ {
if ((rDescriptor.mnEventCode & CONTROL_MODIFIER) != 0) if ((rDescriptor.mnEventCode & CONTROL_MODIFIER) != 0)
StartDrag(rDescriptor.maMousePosition, InsertionIndicatorHandler::CopyMode); StartDrag(rDescriptor.maMousePosition, InsertionIndicatorHandler::CopyMode);
mpSubstitutionHandler->UpdatePosition( mpDragAndDropContext->UpdatePosition(
rDescriptor.maMousePosition, rDescriptor.maMousePosition,
rDescriptor.meDragMode); rDescriptor.meDragMode);
} }
else if (Match(rDescriptor.mnEventCode, MOUSE_DRAG)) else if (Match(rDescriptor.mnEventCode, MOUSE_DRAG))
{ {
mpSubstitutionHandler->UpdatePosition( mpDragAndDropContext->UpdatePosition(
rDescriptor.maMousePosition, rDescriptor.maMousePosition,
rDescriptor.meDragMode); rDescriptor.meDragMode);
} }
else if (Match(rDescriptor.mnEventCode, BUTTON_UP | LEFT_BUTTON)) else if (Match(rDescriptor.mnEventCode, BUTTON_UP | LEFT_BUTTON))
{ {
// The following Process() call may lead to the desctruction // The following Process() call may lead to the desctruction
// of pHitDescriptor so release our reference to it. // of rDescriptor.mpHitDescriptor so release our reference to it.
pHitDescriptor.reset(); rDescriptor.mpHitDescriptor.reset();
mpSubstitutionHandler.reset(); mpDragAndDropContext.reset();
} }
break; }
case RECTANGLE_VISIBLE:
void SelectionFunction::ProcessEventWhileMultiSelectorActive (EventDescriptor& rDescriptor)
{
OSL_ASSERT(mpMouseMultiSelector); OSL_ASSERT(mpMouseMultiSelector);
// The selection rectangle is visible. Handle events accordingly. // The selection rectangle is visible. Handle events accordingly.
if (Match(rDescriptor.mnEventCode, MOUSE_MOTION | LEFT_BUTTON | SINGLE_CLICK)) if (Match(rDescriptor.mnEventCode, MOUSE_MOTION | LEFT_BUTTON | SINGLE_CLICK))
@@ -1138,7 +1051,7 @@ bool SelectionFunction::EventProcessing (const EventDescriptor& rDescriptor)
mpMouseMultiSelector->SetSelectionModeFromModifier(rDescriptor.mnEventCode); mpMouseMultiSelector->SetSelectionModeFromModifier(rDescriptor.mnEventCode);
mpMouseMultiSelector->UpdatePosition(rDescriptor.maMousePosition); mpMouseMultiSelector->UpdatePosition(rDescriptor.maMousePosition);
} }
bMakeSelectionVisible = false; rDescriptor.mbMakeSelectionVisible = false;
} }
else if (Match(rDescriptor.mnEventCode, BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK)) else if (Match(rDescriptor.mnEventCode, BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK))
{ {
@@ -1149,40 +1062,37 @@ bool SelectionFunction::EventProcessing (const EventDescriptor& rDescriptor)
else else
{ {
mpMouseMultiSelector.reset(); mpMouseMultiSelector.reset();
EventDescriptor aModifiedDescriptor (rDescriptor); rDescriptor.mnEventCode &= ~MULTI_SELECTOR;
aModifiedDescriptor.mnEventCode &= ~RECTANGLE_VISIBLE; ProcessEvent(rDescriptor);
EventProcessing(aModifiedDescriptor);
} }
break; }
default:
OSL_ASSERT(!mpMouseMultiSelector);
switch (rDescriptor.mnEventCode & (BUTTON_DOWN | BUTTON_UP | MOUSE_MOTION))
{ void SelectionFunction::ProcessButtonDownEvent (EventDescriptor& rDescriptor)
case BUTTON_DOWN: {
switch (rDescriptor.mnEventCode) switch (rDescriptor.mnEventCode)
{ {
case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE: case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE:
SetCurrentPage(pHitDescriptor); SetCurrentPage(rDescriptor.mpHitDescriptor);
StartDragTimer();
break; break;
case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE: case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE:
StartDragTimer();
break; break;
case BUTTON_DOWN | LEFT_BUTTON | DOUBLE_CLICK | OVER_SELECTED_PAGE: case BUTTON_DOWN | LEFT_BUTTON | DOUBLE_CLICK | OVER_SELECTED_PAGE:
case BUTTON_DOWN | LEFT_BUTTON | DOUBLE_CLICK | OVER_UNSELECTED_PAGE: case BUTTON_DOWN | LEFT_BUTTON | DOUBLE_CLICK | OVER_UNSELECTED_PAGE:
// A double click allways shows the selected slide in the center // A double click allways shows the selected slide in the center
// pane in an edit view. // pane in an edit view.
SetCurrentPage(pHitDescriptor); SetCurrentPage(rDescriptor.mpHitDescriptor);
SwitchView(pHitDescriptor); SwitchView(rDescriptor.mpHitDescriptor);
break; break;
// Range selection with the shift modifier.
case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE | SHIFT_MODIFIER: case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE | SHIFT_MODIFIER:
case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | SHIFT_MODIFIER: case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | SHIFT_MODIFIER:
RangeSelect(pHitDescriptor); // Range selection with the shift modifier.
RangeSelect(rDescriptor.mpHitDescriptor);
break; break;
case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | OVER_BUTTON: case BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | OVER_BUTTON:
@@ -1191,12 +1101,12 @@ bool SelectionFunction::EventProcessing (const EventDescriptor& rDescriptor)
// released over same page and button then invoke action of that // released over same page and button then invoke action of that
// button. // button.
mnButtonDownButtonIndex = rDescriptor.mnButtonIndex; mnButtonDownButtonIndex = rDescriptor.mnButtonIndex;
OSL_ASSERT(pHitDescriptor); OSL_ASSERT(rDescriptor.mpHitDescriptor);
mnButtonDownPageIndex = pHitDescriptor->GetPageIndex(); mnButtonDownPageIndex = rDescriptor.mpHitDescriptor->GetPageIndex();
pHitDescriptor->GetVisualState().SetActiveButtonState( rDescriptor.mpHitDescriptor->GetVisualState().SetActiveButtonState(
mnButtonDownButtonIndex, mnButtonDownButtonIndex,
model::VisualState::BS_Pressed); model::VisualState::BS_Pressed);
mrSlideSorter.GetView().RequestRepaint(pHitDescriptor); mrSlideSorter.GetView().RequestRepaint(rDescriptor.mpHitDescriptor);
break; break;
// Right button for context menu. // Right button for context menu.
@@ -1207,66 +1117,70 @@ bool SelectionFunction::EventProcessing (const EventDescriptor& rDescriptor)
// selection is set to this single page. Otherwise the // selection is set to this single page. Otherwise the
// selection is not modified. // selection is not modified.
DeselectAllPages(); DeselectAllPages();
SetCurrentPage(pHitDescriptor); SetCurrentPage(rDescriptor.mpHitDescriptor);
bMakeSelectionVisible = false; rDescriptor.mbMakeSelectionVisible = false;
break; break;
case BUTTON_DOWN | RIGHT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE: case BUTTON_DOWN | RIGHT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE:
// Do not change the selection. Just adjust the insertion indicator. // Do not change the selection. Just adjust the insertion indicator.
bMakeSelectionVisible = false; rDescriptor.mbMakeSelectionVisible = false;
break; break;
case BUTTON_DOWN | RIGHT_BUTTON | SINGLE_CLICK | NOT_OVER_PAGE:
// Rectangle selection. case BUTTON_DOWN | RIGHT_BUTTON | SINGLE_CLICK | NOT_OVER_PAGE:
// Fallthrough.
case ANY_MODIFIER(BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | NOT_OVER_PAGE): case ANY_MODIFIER(BUTTON_DOWN | LEFT_BUTTON | SINGLE_CLICK | NOT_OVER_PAGE):
mbIsDeselectionPending = true; DeselectAllPages();
OSL_ASSERT(!mpMouseMultiSelector);
break; break;
} }
break; }
case BUTTON_UP:
void SelectionFunction::ProcessButtonUpEvent (const EventDescriptor& rDescriptor)
{
switch (rDescriptor.mnEventCode) switch (rDescriptor.mnEventCode)
{ {
case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE: case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE:
SetCurrentPage(pHitDescriptor); SetCurrentPage(rDescriptor.mpHitDescriptor);
break; break;
// Multi selection with the control modifier. // Multi selection with the control modifier.
case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE | CONTROL_MODIFIER: case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE | CONTROL_MODIFIER:
mrController.GetPageSelector().DeselectPage(pHitDescriptor); mrController.GetPageSelector().DeselectPage(rDescriptor.mpHitDescriptor);
break; break;
case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | CONTROL_MODIFIER: case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | CONTROL_MODIFIER:
mrController.GetPageSelector().SelectPage(pHitDescriptor); mrController.GetPageSelector().SelectPage(rDescriptor.mpHitDescriptor);
// fallthrough // fallthrough
case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | OVER_BUTTON: case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_UNSELECTED_PAGE | OVER_BUTTON:
case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE | OVER_BUTTON: case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE | OVER_BUTTON:
if (mnButtonDownButtonIndex == rDescriptor.mnButtonIndex if (mnButtonDownButtonIndex == rDescriptor.mnButtonIndex
&& mnButtonDownPageIndex == pHitDescriptor->GetPageIndex()) && mnButtonDownPageIndex == rDescriptor.mpHitDescriptor->GetPageIndex())
{ {
ProcessButtonClick(pHitDescriptor, mnButtonDownButtonIndex); ProcessButtonClick(rDescriptor.mpHitDescriptor, mnButtonDownButtonIndex);
} }
break; break;
case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | NOT_OVER_PAGE: case BUTTON_UP | LEFT_BUTTON | SINGLE_CLICK | NOT_OVER_PAGE:
if (mbIsDeselectionPending) if (mbIsDeselectionPending)
DeselectAllPages(); DeselectAllPages();
break; break;
} }
break; }
case MOUSE_MOTION:
void SelectionFunction::ProcessMouseMotionEvent (const EventDescriptor& rDescriptor)
{
switch (rDescriptor.mnEventCode) switch (rDescriptor.mnEventCode)
{ {
// A mouse motion without visible substitution starts that. // A mouse motion without visible substitution starts that.
case ANY_MODIFIER(MOUSE_MOTION | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE): case ANY_MODIFIER(MOUSE_MOTION | LEFT_BUTTON | SINGLE_CLICK | OVER_SELECTED_PAGE):
mpSubstitutionHandler.reset(new SubstitutionHandler(
mrSlideSorter,
pHitDescriptor,
rDescriptor.maMouseModelPosition));
StartDrag( StartDrag(
rDescriptor.maMousePosition, rDescriptor.maMousePosition,
(rDescriptor.mnEventCode | CONTROL_MODIFIER) != 0 (rDescriptor.mnEventCode & CONTROL_MODIFIER) != 0
? InsertionIndicatorHandler::CopyMode ? InsertionIndicatorHandler::CopyMode
: InsertionIndicatorHandler::MoveMode); : InsertionIndicatorHandler::MoveMode);
break; break;
@@ -1279,45 +1193,20 @@ bool SelectionFunction::EventProcessing (const EventDescriptor& rDescriptor)
mpMouseMultiSelector->SetSelectionModeFromModifier(rDescriptor.mnEventCode); mpMouseMultiSelector->SetSelectionModeFromModifier(rDescriptor.mnEventCode);
break; break;
} }
break;
}
}
mrController.GetPageSelector().EnableBroadcasting(bMakeSelectionVisible);
return bResult;
} }
void SelectionFunction::EventPostprocessing (const EventDescriptor& rDescriptor) void SelectionFunction::PostProcessEvent (const EventDescriptor& rDescriptor)
{ {
if (rDescriptor.mnEventCode & BUTTON_UP) if (rDescriptor.mnEventCode & BUTTON_UP)
{ {
view::ViewOverlay& rOverlay (mrSlideSorter.GetView().GetOverlay());
mpWindow->ReleaseMouse(); mpWindow->ReleaseMouse();
// The overlays should not be visible anymore. Warn when one of
// them still is. An exception is th insertion indicator in the
// case that the context menu is visible.
DBG_ASSERT(
mrController.IsContextMenuOpen()
|| !rOverlay.GetInsertionIndicatorOverlay()->IsVisible(),
"slidesorter::SelectionFunction: insertion indicator still visible");
DBG_ASSERT(
!rOverlay.GetSubstitutionOverlay()->IsVisible(),
"slidesorter::SelectionFunction: substitution still visible");
DBG_ASSERT(
!rOverlay.GetSelectionRectangleOverlay()->IsVisible(),
"slidesorter::SelectionFunction: selection rectangle still visible");
// Now turn them off. // Now turn them off.
if ( ! mrController.IsContextMenuOpen()) if ( ! mrController.IsContextMenuOpen())
rOverlay.GetInsertionIndicatorOverlay()->SetIsVisible(false); mrController.GetInsertionIndicatorHandler()->End();
rOverlay.GetSubstitutionOverlay()->SetIsVisible(false);
rOverlay.GetSelectionRectangleOverlay()->SetIsVisible(false);
mnButtonDownPageIndex = -1; mnButtonDownPageIndex = -1;
mnButtonDownButtonIndex = -1; mnButtonDownButtonIndex = -1;
@@ -1429,16 +1318,14 @@ SelectionFunction::EventDescriptor::EventDescriptor (
maMousePosition = rEvent.GetPosPixel(); maMousePosition = rEvent.GetPosPixel();
maMouseModelPosition = pWindow->PixelToLogic(maMousePosition); maMouseModelPosition = pWindow->PixelToLogic(maMousePosition);
model::SharedPageDescriptor pHitDescriptor ( mpHitDescriptor = rSlideSorter.GetController().GetPageAt(maMousePosition);
rSlideSorter.GetController().GetPageAt(maMousePosition)); if (mpHitDescriptor)
if (pHitDescriptor.get() != NULL)
{ {
mpHitDescriptor = pHitDescriptor; mpHitPage = mpHitDescriptor->GetPage();
mpHitPage = pHitDescriptor->GetPage();
mnButtonIndex = rSlideSorter.GetView().GetLayouter() mnButtonIndex
.GetPageObjectLayouter()->GetButtonIndexAt( = rSlideSorter.GetView().GetLayouter().GetPageObjectLayouter()->GetButtonIndexAt(
pHitDescriptor, mpHitDescriptor,
maMouseModelPosition); maMouseModelPosition);
} }
} }
@@ -1456,7 +1343,8 @@ SelectionFunction::EventDescriptor::EventDescriptor (
mpHitPage(), mpHitPage(),
mnEventCode(0), mnEventCode(0),
mnButtonIndex(-1), mnButtonIndex(-1),
meDragMode(InsertionIndicatorHandler::MoveMode) meDragMode(InsertionIndicatorHandler::MoveMode),
mbMakeSelectionVisible(true)
{ {
model::SharedPageDescriptor pHitDescriptor ( model::SharedPageDescriptor pHitDescriptor (
rSlideSorter.GetController().GetFocusManager().GetFocusedPageDescriptor()); rSlideSorter.GetController().GetFocusManager().GetFocusedPageDescriptor());
@@ -1480,7 +1368,8 @@ SelectionFunction::EventDescriptor::EventDescriptor (
mpHitPage(), mpHitPage(),
mnEventCode(MOUSE_DRAG), mnEventCode(MOUSE_DRAG),
mnButtonIndex(-1), mnButtonIndex(-1),
meDragMode(InsertionIndicatorHandler::MoveMode) meDragMode(InsertionIndicatorHandler::MoveMode),
mbMakeSelectionVisible(true)
{ {
SharedSdWindow pWindow (rSlideSorter.GetContentWindow()); SharedSdWindow pWindow (rSlideSorter.GetContentWindow());
@@ -1504,7 +1393,8 @@ SelectionFunction::EventDescriptor::EventDescriptor (const EventDescriptor& rDes
mpHitPage(rDescriptor.mpHitPage), mpHitPage(rDescriptor.mpHitPage),
mnEventCode(rDescriptor.mnEventCode), mnEventCode(rDescriptor.mnEventCode),
mnButtonIndex(rDescriptor.mnButtonIndex), mnButtonIndex(rDescriptor.mnButtonIndex),
meDragMode(InsertionIndicatorHandler::MoveMode) meDragMode(InsertionIndicatorHandler::MoveMode),
mbMakeSelectionVisible(true)
{ {
} }
@@ -1603,15 +1493,15 @@ void SelectionFunction::MouseMultiSelector::SetSelectionModeFromModifier (
switch (nEventCode & MODIFIER_MASK) switch (nEventCode & MODIFIER_MASK)
{ {
case NO_MODIFIER: case NO_MODIFIER:
SetSelectionMode(RectangleSelector::SM_Normal); SetSelectionMode(SM_Normal);
break; break;
case SHIFT_MODIFIER: case SHIFT_MODIFIER:
SetSelectionMode(RectangleSelector::SM_Add); SetSelectionMode(SM_Add);
break; break;
case CONTROL_MODIFIER: case CONTROL_MODIFIER:
SetSelectionMode(RectangleSelector::SM_Toggle); SetSelectionMode(SM_Toggle);
break; break;
} }
} }
@@ -1669,92 +1559,6 @@ void SelectionFunction::MouseMultiSelector::UpdateSelectionState (
//===== RectangleSelector =====================================================
namespace {
RectangleSelector::RectangleSelector (
SlideSorter& rSlideSorter,
const Point& rMouseModelPosition)
: MouseMultiSelector(rSlideSorter,rMouseModelPosition)
{
if (mrSlideSorter.GetProperties()->IsShowSelection())
{
mrSlideSorter.GetView().GetOverlay().GetSelectionRectangleOverlay()
->Start(rMouseModelPosition);
}
}
RectangleSelector::~RectangleSelector (void)
{
if (mrSlideSorter.GetProperties()->IsShowSelection())
{
mrSlideSorter.GetView().GetOverlay().GetSelectionRectangleOverlay()->SetIsVisible(false);
}
}
void RectangleSelector::UpdateModelPosition (const Point& rMouseModelPosition)
{
if (mrSlideSorter.GetProperties()->IsShowSelection())
{
mrSlideSorter.GetView().GetOverlay().GetSelectionRectangleOverlay()
->Update(rMouseModelPosition);
UpdateSelection();
}
}
void RectangleSelector::UpdateSelection (void)
{
if ( ! mrSlideSorter.GetProperties()->IsShowSelection())
return;
view::ViewOverlay& rOverlay (mrSlideSorter.GetView().GetOverlay());
if (rOverlay.GetSelectionRectangleOverlay()->IsVisible())
{
view::SlideSorterView::DrawLock aDrawLock (mrSlideSorter);
PageSelector::UpdateLock aPageSelectorUpdateLock (mrSlideSorter);
// Select all pages whose page object lies completly or partially
// inside the selection rectangle.
const Rectangle& rSelectionRectangle (
rOverlay.GetSelectionRectangleOverlay()->GetSelectionRectangle());
model::PageEnumeration aPages (
model::PageEnumerationProvider::CreateAllPagesEnumeration(
mrSlideSorter.GetModel()));
while (aPages.HasMoreElements())
{
model::SharedPageDescriptor pDescriptor (aPages.GetNextElement());
// Determine whether the page object is inside the selection rectangle.
Rectangle aPageBox (
mrSlideSorter.GetView().GetLayouter().GetPageObjectLayouter()->GetBoundingBox(
pDescriptor,
view::PageObjectLayouter::Preview,
view::PageObjectLayouter::WindowCoordinateSystem));
const bool bIsPageInSelectionRectangle (rSelectionRectangle.IsOver(aPageBox));
UpdateSelectionState(pDescriptor, bIsPageInSelectionRectangle);
}
// Rely on auto scrolling to make page objects visible.
mrSlideSorter.GetController().GetSelectionManager()->ResetMakeSelectionVisiblePending();
}
}
} // end of anonymous namespace
//===== RangeSelector ========================================================= //===== RangeSelector =========================================================
namespace { namespace {

View File

@@ -81,8 +81,8 @@ namespace {
private: private:
SlideSorter& mrSlideSorter; SlideSorter& mrSlideSorter;
double mnStart; double mnStart;
double mnEnd; const double mnEnd;
::boost::function<double(double)> maAccelerationFunction; const ::boost::function<double(double)> maAccelerationFunction;
}; };
class HorizontalVisibleAreaScroller class HorizontalVisibleAreaScroller
{ {
@@ -93,8 +93,8 @@ namespace {
private: private:
SlideSorter& mrSlideSorter; SlideSorter& mrSlideSorter;
double mnStart; double mnStart;
double mnEnd; const double mnEnd;
::boost::function<double(double)> maAccelerationFunction; const ::boost::function<double(double)> maAccelerationFunction;
}; };
} }
@@ -116,6 +116,8 @@ SelectionManager::SelectionManager (SlideSorter& rSlideSorter)
SelectionManager::~SelectionManager (void) SelectionManager::~SelectionManager (void)
{ {
if (mnAnimationId != Animator::NotAnAnimationId)
mrController.GetAnimator()->RemoveAnimation(mnAnimationId);
} }
@@ -655,6 +657,8 @@ void SelectionManager::SetInsertionPosition (const sal_Int32 nInsertionPosition)
namespace { namespace {
const static sal_Int32 gnMaxScrollDistance = 300;
VerticalVisibleAreaScroller::VerticalVisibleAreaScroller ( VerticalVisibleAreaScroller::VerticalVisibleAreaScroller (
SlideSorter& rSlideSorter, SlideSorter& rSlideSorter,
const double nStart, const double nStart,
@@ -666,6 +670,14 @@ VerticalVisibleAreaScroller::VerticalVisibleAreaScroller (
controller::AnimationParametricFunction( controller::AnimationParametricFunction(
controller::AnimationBezierFunction (0.1,0.6))) controller::AnimationBezierFunction (0.1,0.6)))
{ {
// When the distance to scroll is larger than a threshold then first
// jump to within this distance of the final value and start the
// animation from there.
if (abs(nStart-nEnd) > gnMaxScrollDistance)
if (nStart < nEnd)
mnStart = nEnd-gnMaxScrollDistance;
else
mnStart = nEnd+gnMaxScrollDistance;
} }

View File

@@ -49,7 +49,6 @@
#include "model/SlsPageDescriptor.hxx" #include "model/SlsPageDescriptor.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsLayouter.hxx" #include "view/SlsLayouter.hxx"
#include "view/SlsViewOverlay.hxx"
#include "framework/FrameworkHelper.hxx" #include "framework/FrameworkHelper.hxx"
#include "Window.hxx" #include "Window.hxx"
#include "fupoor.hxx" #include "fupoor.hxx"
@@ -1093,8 +1092,7 @@ void SlotManager::InsertSlide (SfxRequest& rRequest)
} }
// No selection. Is there an insertion indicator? // No selection. Is there an insertion indicator?
else if (mrSlideSorter.GetView().GetOverlay() else if (mrSlideSorter.GetController().GetInsertionIndicatorHandler()->IsActive())
.GetInsertionIndicatorOverlay()->IsVisible())
{ {
// Select the page before the insertion indicator. // Select the page before the insertion indicator.
nInsertionIndex nInsertionIndex

View File

@@ -31,7 +31,7 @@
// MARKER(update_precomp.py): autogen include statement, do not remove // MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_sd.hxx" #include "precompiled_sd.hxx"
#include "SlsTransferable.hxx" #include "controller/SlsTransferable.hxx"
#include "SlideSorterViewShell.hxx" #include "SlideSorterViewShell.hxx"
#include "View.hxx" #include "View.hxx"
@@ -43,10 +43,10 @@ Transferable::Transferable (
::sd::View* pWorkView, ::sd::View* pWorkView,
BOOL bInitOnGetData, BOOL bInitOnGetData,
SlideSorterViewShell* pViewShell, SlideSorterViewShell* pViewShell,
const ::boost::shared_ptr<SubstitutionHandler>& rpSubstitutionHandler) const ::std::vector<Bitmap>& rRepresentatives)
: SdTransferable (pSrcDoc, pWorkView, bInitOnGetData), : SdTransferable (pSrcDoc, pWorkView, bInitOnGetData),
mpViewShell(pViewShell), mpViewShell(pViewShell),
mpSubstitutionHandler(rpSubstitutionHandler) maRepresentatives(rRepresentatives)
{ {
if (mpViewShell != NULL) if (mpViewShell != NULL)
StartListening(*mpViewShell); StartListening(*mpViewShell);
@@ -68,7 +68,6 @@ void Transferable::DragFinished (sal_Int8 nDropAction)
{ {
if (mpViewShell != NULL) if (mpViewShell != NULL)
mpViewShell->DragFinished(nDropAction); mpViewShell->DragFinished(nDropAction);
mpSubstitutionHandler.reset();
} }
@@ -96,11 +95,10 @@ void Transferable::Notify (SfxBroadcaster& rBroadcaster, const SfxHint& rHint)
::boost::shared_ptr<SubstitutionHandler> Transferable::GetSubstitutionHandler (void) const const ::std::vector<Bitmap>& Transferable::GetRepresentatives (void) const
{ {
return mpSubstitutionHandler; return maRepresentatives;
} }
} } } // end of namespace ::sd::slidesorter::controller } } } // end of namespace ::sd::slidesorter::controller

View File

@@ -52,6 +52,7 @@ SLOFILES = \
$(SLO)$/SlsAnimationFunction.obj \ $(SLO)$/SlsAnimationFunction.obj \
$(SLO)$/SlsClipboard.obj \ $(SLO)$/SlsClipboard.obj \
$(SLO)$/SlsCurrentSlideManager.obj \ $(SLO)$/SlsCurrentSlideManager.obj \
$(SLO)$/SlsDragAndDropContext.obj \
$(SLO)$/SlsFocusManager.obj \ $(SLO)$/SlsFocusManager.obj \
$(SLO)$/SlsInsertionIndicatorHandler.obj\ $(SLO)$/SlsInsertionIndicatorHandler.obj\
$(SLO)$/SlsListener.obj \ $(SLO)$/SlsListener.obj \
@@ -62,7 +63,6 @@ SLOFILES = \
$(SLO)$/SlsSelectionFunction.obj \ $(SLO)$/SlsSelectionFunction.obj \
$(SLO)$/SlsSelectionManager.obj \ $(SLO)$/SlsSelectionManager.obj \
$(SLO)$/SlsSlotManager.obj \ $(SLO)$/SlsSlotManager.obj \
$(SLO)$/SlsSubstitutionHandler.obj \
$(SLO)$/SlsTransferable.obj $(SLO)$/SlsTransferable.obj
# --- Tagets ------------------------------------------------------- # --- Tagets -------------------------------------------------------

View File

@@ -96,6 +96,12 @@ public:
*/ */
void RemoveAnimation (const AnimationId nAnimationId); void RemoveAnimation (const AnimationId nAnimationId);
/** A typical use case for this method is the temporary shutdown of the
slidesorter when the slide sorter bar is put into a cache due to a
change of the edit mode.
*/
void RemoveAllAnimations (void);
private: private:
SlideSorter& mrSlideSorter; SlideSorter& mrSlideSorter;
Timer maTimer; Timer maTimer;

View File

@@ -33,6 +33,8 @@
#include "view/SlsInsertAnimator.hxx" #include "view/SlsInsertAnimator.hxx"
#include "view/SlsLayouter.hxx"
namespace sd { namespace slidesorter { class SlideSorter; } } namespace sd { namespace slidesorter { class SlideSorter; } }
namespace sd { namespace slidesorter { namespace model { namespace sd { namespace slidesorter { namespace model {
class PageEnumeration; class PageEnumeration;
@@ -45,6 +47,8 @@ class InsertionIndicatorOverlay;
namespace sd { namespace slidesorter { namespace controller { namespace sd { namespace slidesorter { namespace controller {
class Transferable;
/** Manage the visibility and location of the insertion indicator. Its /** Manage the visibility and location of the insertion indicator. Its
actual display is controlled by the InsertionIndicatorOverlay. actual display is controlled by the InsertionIndicatorOverlay.
@@ -60,13 +64,16 @@ public:
/** Activate the insertion marker at the given coordinates. /** Activate the insertion marker at the given coordinates.
*/ */
void Start ( void Start (const bool bIsOverSourceView);
const Point& rMouseModelPosition,
const Mode eMode,
const bool bIsOverSourceView);
void UpdateIndicatorIcon (model::PageEnumeration& rEnumeration); /** Deactivate the insertion marker.
void UpdateIndicatorIcon (void); */
void End (void);
/** Update the indicator icon from the current transferable (from the
clipboard or an active drag and drop operation.)
*/
void UpdateIndicatorIcon (const Transferable* pTransferable);
/** Set the position of the insertion marker to the given coordinates. /** Set the position of the insertion marker to the given coordinates.
*/ */
@@ -77,10 +84,6 @@ public:
const Point& rMouseModelPosition, const Point& rMouseModelPosition,
const sal_Int8 nDndAction); const sal_Int8 nDndAction);
/** Deactivate the insertion marker.
*/
void End (void);
/** Return whether the insertion marker is active. /** Return whether the insertion marker is active.
*/ */
bool IsActive (void) const; bool IsActive (void) const;
@@ -96,14 +99,15 @@ public:
would be the case when the selection is not consecutive or would be would be the case when the selection is not consecutive or would be
moved to a position outside and not adjacent to the selection. moved to a position outside and not adjacent to the selection.
*/ */
bool IsInsertionTrivial (const Mode eMode) const; bool IsInsertionTrivial (
const sal_Int32 nInsertionIndex,
const Mode eMode) const;
private: private:
SlideSorter& mrSlideSorter; SlideSorter& mrSlideSorter;
::boost::shared_ptr<view::InsertAnimator> mpInsertAnimator; ::boost::shared_ptr<view::InsertAnimator> mpInsertAnimator;
::boost::shared_ptr<view::InsertionIndicatorOverlay> mpInsertionIndicatorOverlay; ::boost::shared_ptr<view::InsertionIndicatorOverlay> mpInsertionIndicatorOverlay;
sal_Int32 mnInsertionIndex; view::InsertPosition maInsertPosition;
Pair maVisualInsertionIndices;
Mode meMode; Mode meMode;
bool mbIsInsertionTrivial; bool mbIsInsertionTrivial;
bool mbIsActive; bool mbIsActive;

View File

@@ -52,7 +52,7 @@ class SlideSorter;
namespace sd { namespace slidesorter { namespace controller { namespace sd { namespace slidesorter { namespace controller {
class SlideSorterController; class SlideSorterController;
class SubstitutionHandler; class DragAndDropContext;
class SelectionFunction class SelectionFunction
@@ -109,7 +109,7 @@ public:
const Point& rMousePosition, const Point& rMousePosition,
const bool bIsMouseButtonDown); const bool bIsMouseButtonDown);
::boost::shared_ptr<SubstitutionHandler> GetSubstitutionHandler (void) const; ::boost::shared_ptr<DragAndDropContext> GetDragAndDropContext (void) const;
class MouseMultiSelector; class MouseMultiSelector;
@@ -126,9 +126,6 @@ protected:
private: private:
class EventDescriptor; class EventDescriptor;
/// Set in MouseButtonDown this flag indicates that a page has been hit.
bool mbPageHit;
/// The rectangle of the mouse drag selection. /// The rectangle of the mouse drag selection.
Rectangle maDragSelectionRectangle; Rectangle maDragSelectionRectangle;
bool mbDragSelection; bool mbDragSelection;
@@ -144,7 +141,7 @@ private:
*/ */
bool mbProcessingMouseButtonDown; bool mbProcessingMouseButtonDown;
::boost::shared_ptr<SubstitutionHandler> mpSubstitutionHandler; ::boost::shared_ptr<DragAndDropContext> mpDragAndDropContext;
::boost::scoped_ptr<MouseMultiSelector> mpMouseMultiSelector; ::boost::scoped_ptr<MouseMultiSelector> mpMouseMultiSelector;
/** Remember where the left mouse button was pressed. /** Remember where the left mouse button was pressed.
@@ -159,7 +156,6 @@ private:
*/ */
sal_Int32 mnShiftKeySelectionAnchor; sal_Int32 mnShiftKeySelectionAnchor;
DECL_LINK( DragSlideHdl, Timer* );
void StartDrag ( void StartDrag (
const Point& rMousePosition, const Point& rMousePosition,
const InsertionIndicatorHandler::Mode eMode); const InsertionIndicatorHandler::Mode eMode);
@@ -192,22 +188,11 @@ private:
/// Deselect all pages. /// Deselect all pages.
void DeselectAllPages (void); void DeselectAllPages (void);
/** For a possibly following mouse motion by starting the drag timer
that after a short time of pressed but un-moved mouse starts a drag
operation.
*/
void StartDragTimer (void);
/** Select all pages between and including the selection anchor and the /** Select all pages between and including the selection anchor and the
specified page. specified page.
*/ */
void RangeSelect (const model::SharedPageDescriptor& rpDescriptor); void RangeSelect (const model::SharedPageDescriptor& rpDescriptor);
/** Hide and clear the insertion indiciator, substitution display and
selection rectangle.
*/
void ClearOverlays (void);
/** Compute a numerical code that describes a mouse event and that can /** Compute a numerical code that describes a mouse event and that can
be used for fast look up of the appropriate reaction. be used for fast look up of the appropriate reaction.
*/ */
@@ -228,9 +213,13 @@ private:
*/ */
sal_uInt32 EncodeState (const EventDescriptor& rDescriptor) const; sal_uInt32 EncodeState (const EventDescriptor& rDescriptor) const;
void EventPreprocessing (const EventDescriptor& rEvent); bool ProcessEvent (EventDescriptor& rEvent);
bool EventProcessing (const EventDescriptor& rEvent); void PostProcessEvent (const EventDescriptor& rEvent);
void EventPostprocessing (const EventDescriptor& rEvent); void ProcessEventWhileDragActive (EventDescriptor& rDescriptor);
void ProcessEventWhileMultiSelectorActive (EventDescriptor& rDescriptor);
void ProcessButtonDownEvent (EventDescriptor& rDescriptor);
void ProcessButtonUpEvent (const EventDescriptor& rDescriptor);
void ProcessMouseMotionEvent (const EventDescriptor& rDescriptor);
void ProcessButtonClick ( void ProcessButtonClick (
const model::SharedPageDescriptor& rpDescriptor, const model::SharedPageDescriptor& rpDescriptor,
@@ -245,4 +234,3 @@ private:
} } } // end of namespace ::sd::slidesorter::controller } } } // end of namespace ::sd::slidesorter::controller
#endif #endif

View File

@@ -34,19 +34,12 @@
#include "sdxfer.hxx" #include "sdxfer.hxx"
class SdDrawDocument; class SdDrawDocument;
namespace sd namespace sd { namespace slidesorter {
{ class SlideSorterViewShell;
class pWorkView; } }
namespace slidesorter
{
class SlideSorterViewShell;
}
}
namespace sd { namespace slidesorter { namespace controller { namespace sd { namespace slidesorter { namespace controller {
class SubstitutionHandler;
/** This class exists to have DragFinished call the correct object: the /** This class exists to have DragFinished call the correct object: the
SlideSorterViewShell instead of the old SlideView. SlideSorterViewShell instead of the old SlideView.
@@ -60,17 +53,17 @@ public:
::sd::View* pWorkView, ::sd::View* pWorkView,
BOOL bInitOnGetData, BOOL bInitOnGetData,
SlideSorterViewShell* pViewShell, SlideSorterViewShell* pViewShell,
const ::boost::shared_ptr<SubstitutionHandler>& rpSubstitutionHandler); const ::std::vector<Bitmap>& rRepresentatives);
virtual ~Transferable (void); virtual ~Transferable (void);
virtual void DragFinished (sal_Int8 nDropAction); virtual void DragFinished (sal_Int8 nDropAction);
::boost::shared_ptr<SubstitutionHandler> GetSubstitutionHandler (void) const; const ::std::vector<Bitmap>& GetRepresentatives (void) const;
private: private:
SlideSorterViewShell* mpViewShell; SlideSorterViewShell* mpViewShell;
::boost::shared_ptr<SubstitutionHandler> mpSubstitutionHandler; const ::std::vector<Bitmap> maRepresentatives;
virtual void Notify (SfxBroadcaster& rBroadcaster, const SfxHint& rHint); virtual void Notify (SfxBroadcaster& rBroadcaster, const SfxHint& rHint);
}; };

View File

@@ -31,6 +31,7 @@
#ifndef SD_SLIDESORTER_SLIDE_SORTER_VIEW_HXX #ifndef SD_SLIDESORTER_SLIDE_SORTER_VIEW_HXX
#define SD_SLIDESORTER_SLIDE_SORTER_VIEW_HXX #define SD_SLIDESORTER_SLIDE_SORTER_VIEW_HXX
#include "SlideSorter.hxx"
#include "model/SlsPageDescriptor.hxx" #include "model/SlsPageDescriptor.hxx"
#include "model/SlsSharedPageDescriptor.hxx" #include "model/SlsSharedPageDescriptor.hxx"
@@ -48,10 +49,6 @@
class Point; class Point;
namespace sd { namespace slidesorter {
class SlideSorter;
} }
namespace sd { namespace slidesorter { namespace controller { namespace sd { namespace slidesorter { namespace controller {
class SlideSorterController; class SlideSorterController;
class Properties; class Properties;
@@ -71,7 +68,6 @@ class LayeredDevice;
class Layouter; class Layouter;
class PageObjectPainter; class PageObjectPainter;
class SelectionPainter; class SelectionPainter;
class ViewOverlay;
class SlideSorterView class SlideSorterView
: public sd::View, : public sd::View,
@@ -162,8 +158,6 @@ public:
::boost::shared_ptr<cache::PageCache> GetPreviewCache (void); ::boost::shared_ptr<cache::PageCache> GetPreviewCache (void);
view::ViewOverlay& GetOverlay (void);
/** Set the bounding box of the insertion marker in model coordinates. /** Set the bounding box of the insertion marker in model coordinates.
It will be painted as a dark rectangle that fills the given box. It will be painted as a dark rectangle that fills the given box.
@@ -209,15 +203,17 @@ public:
const bool bStateValue); const bool bStateValue);
::boost::shared_ptr<PageObjectPainter> GetPageObjectPainter (void); ::boost::shared_ptr<PageObjectPainter> GetPageObjectPainter (void);
::boost::shared_ptr<LayeredDevice> GetLayeredDevice (void) const;
class DrawLock class DrawLock
{ {
public: public:
DrawLock (view::SlideSorterView& rView); DrawLock (view::SlideSorterView& rView, const SharedSdWindow& rpWindow);
DrawLock (SlideSorter& rSlideSorter); DrawLock (SlideSorter& rSlideSorter);
~DrawLock (void); ~DrawLock (void);
private: private:
view::SlideSorterView& mrView; view::SlideSorterView& mrView;
SharedSdWindow mpWindow;
}; };
protected: protected:
@@ -231,7 +227,6 @@ private:
bool mbPageObjectVisibilitiesValid; bool mbPageObjectVisibilitiesValid;
::boost::shared_ptr<cache::PageCache> mpPreviewCache; ::boost::shared_ptr<cache::PageCache> mpPreviewCache;
::boost::shared_ptr<LayeredDevice> mpLayeredDevice; ::boost::shared_ptr<LayeredDevice> mpLayeredDevice;
::boost::shared_ptr<ViewOverlay> mpViewOverlay;
Range maVisiblePageRange; Range maVisiblePageRange;
bool mbModelChangedWhileModifyEnabled; bool mbModelChangedWhileModifyEnabled;
Size maPreviewSize; Size maPreviewSize;
@@ -242,6 +237,7 @@ private:
sal_Int32 mnButtonUnderMouse; sal_Int32 mnButtonUnderMouse;
::boost::shared_ptr<PageObjectPainter> mpPageObjectPainter; ::boost::shared_ptr<PageObjectPainter> mpPageObjectPainter;
::boost::shared_ptr<SelectionPainter> mpSelectionPainter; ::boost::shared_ptr<SelectionPainter> mpSelectionPainter;
Region maRedrawRegion;
/** Determine the visibility of all page objects. /** Determine the visibility of all page objects.
*/ */

View File

@@ -38,6 +38,9 @@
namespace sd { namespace slidesorter { namespace view { namespace sd { namespace slidesorter { namespace view {
class InsertPosition;
/** Animate the positions of page objects to make room at the insert /** Animate the positions of page objects to make room at the insert
position while a move or copy operation takes place. position while a move or copy operation takes place.
*/ */
@@ -51,8 +54,7 @@ public:
icon. icon.
*/ */
void SetInsertPosition ( void SetInsertPosition (
const sal_Int32 nPageIndex, const InsertPosition& rInsertPosition,
const Pair& rVisualInsertionIndices,
const Size& rIconSize); const Size& rIconSize);
void Reset (void); void Reset (void);

View File

@@ -0,0 +1,130 @@
/*************************************************************************
*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* Copyright 2008 by Sun Microsystems, Inc.
*
* OpenOffice.org - a multi-platform office productivity suite
*
* This file is part of OpenOffice.org.
*
* OpenOffice.org is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License version 3
* only, as published by the Free Software Foundation.
*
* OpenOffice.org is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License version 3 for more details
* (a copy is included in the LICENSE file that accompanied this code).
*
* You should have received a copy of the GNU Lesser General Public License
* version 3 along with OpenOffice.org. If not, see
* <http://www.openoffice.org/license.html>
* for a copy of the LGPLv3 License.
*
************************************************************************/
#ifndef SD_SLIDESORTER_INSERTION_INDICATOR_OVERLAY_HXX
#define SD_SLIDESORTER_INSERTION_INDICATOR_OVERLAY_HXX
#include "model/SlsSharedPageDescriptor.hxx"
#include "view/SlsILayerPainter.hxx"
#include <tools/gen.hxx>
#include <vcl/bitmapex.hxx>
#include <boost/scoped_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
#include <vector>
class OutputDevice;
class SdPage;
namespace sd { namespace slidesorter {
class SlideSorter;
} }
namespace sd { namespace slidesorter { namespace model {
class PageEnumeration;
} } }
namespace sd { namespace slidesorter { namespace controller {
class Transferable;
} } }
namespace sd { namespace slidesorter { namespace view {
class FramePainter;
class LayeredDevice;
/** The insertion indicator is painted as a vertical or horizonal bar
in the space between slides.
*/
class InsertionIndicatorOverlay
: public ILayerPainter,
public ::boost::enable_shared_from_this<InsertionIndicatorOverlay>
{
public:
InsertionIndicatorOverlay (SlideSorter& rSlideSorter);
virtual ~InsertionIndicatorOverlay (void);
virtual void SetLayerInvalidator (const SharedILayerInvalidator& rpInvalidator);
void Create (const controller::Transferable* pTransferable);
/** Given a position in model coordinates this method calculates the
insertion marker both as an index in the document and as a location
used for drawing the insertion indicator.
*/
void SetLocation (const Point& rPosition);
Size GetSize (void) const;
virtual void Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea);
bool IsVisible (void) const;
void Hide (void);
void Show (void);
Rectangle GetBoundingBox (void) const;
private:
SlideSorter& mrSlideSorter;
bool mbIsVisible;
const sal_Int32 mnLayerIndex;
SharedILayerInvalidator mpLayerInvalidator;
// Center of the insertion indicator.
Point maLocation;
BitmapEx maIcon;
Point maIconOffset;
::boost::scoped_ptr<FramePainter> mpShadowPainter;
void SetPositionAndSize (const Rectangle& rBoundingBox);
void SelectRepresentatives (
model::PageEnumeration& rSelection,
::std::vector<model::SharedPageDescriptor>& rDescriptors) const;
Point PaintRepresentatives (
OutputDevice& rContent,
const Size aPreviewSize,
const sal_Int32 nOffset,
const ::std::vector<Bitmap>& rPages) const;
void PaintPageCount (
OutputDevice& rDevice,
const sal_Int32 nSelectionCount,
const Size aPreviewSize,
const Point aFirstPageOffset) const;
/** Setup the insertion indicator by creating the icon. It consists of
scaled down previews of some of the selected pages.
*/
void Create (
const ::std::vector<Bitmap>& rPages,
const sal_Int32 nSelectionCount);
};
} } } // end of namespace ::sd::slidesorter::view
#endif

View File

@@ -45,6 +45,11 @@ class Size;
namespace sd { namespace slidesorter { namespace view { namespace sd { namespace slidesorter { namespace view {
class InsertPosition;
/** Calculate the size and position of page objects displayed by a slide /** Calculate the size and position of page objects displayed by a slide
sorter. The layouter takes into account various input values: sorter. The layouter takes into account various input values:
1.) Size of the window in which the slide sorter is displayed. 1.) Size of the window in which the slide sorter is displayed.
@@ -192,20 +197,6 @@ public:
*/ */
Rectangle GetPageBox (const sal_Int32 nObjectCount = -1) const; Rectangle GetPageBox (const sal_Int32 nObjectCount = -1) const;
/** Return the location of the center of the insertion indicator that is
specified by the parameters.
@param aVisualIndicatorIndices
Row and column of where to paint the insertion indicator. Column
is -1 when the indicator is placed between rows of a single
column.
@param rIndicatorSize
The size of the insertion indicator. This size is used to adapt
the location when at the left or right of a row.
*/
Point GetInsertionIndicatorLocation (
const Pair& rVisualIndicatorIndices,
const Size& rIndicatorSize) const;
/** Return the index of the first fully or partially visible page /** Return the index of the first fully or partially visible page
object. This takes into account only the vertical dimension. object. This takes into account only the vertical dimension.
@return @return
@@ -233,40 +224,22 @@ public:
const Point& rModelPosition, const Point& rModelPosition,
const bool bIncludePageBorders = false) const; const bool bIncludePageBorders = false) const;
/** Return the page index of where to do an insert operation when the /** Return an object that describes the logical and visual properties of
user would release the the mouse button at the given position after where to do an insert operation when the user would release the the
a drag operation. This method assumes that pages are placed in a mouse button at the given position after a drag operation and of
single column. where and how to display an insertion indicator.
@param rPosition @param rPosition
The position in the model coordinate system for which to The position in the model coordinate system for which to
determine the insertion page index. The position does not have determine the insertion page index. The position does not have
to be over a page object to return a valid value. to be over a page object to return a valid value.
@return @param rIndicatorSize
Returns the page index, as accepted by the slide sorter model, The size of the insertion indicator. This size is used to adapt
of the page after which an insertion would take place. An index the location when at the left or right of a row or at the top or
of 0 means that insertion will take place before the first page, bottom of a column.
An index equal to or greater than the page count means to insert
after the last page.
A value of -1 indicates that no valid insertion index exists for
the given point.
*/ */
sal_Int32 GetVerticalInsertionIndex (const Point& rModelPosition) const; InsertPosition GetInsertPosition (
const Point& rModelPosition,
/** Return a pair of row and column indices of where to do an insert const Size& rIndicatorSize) const;
operation when the user would release the the mouse button at the
given position after a drag operation. This method assumes that
pages are placed in a row-first grid.
@param rPosition
The position in the model coordinate system for which to
determine the insertion page index. The position does not have
to be over a page object to return a valid value.
@return
Returns a pair of (row,column) indices and defines the place of
where to paint the insertion indicator. The column index lies
in the range [0,column count]. A value of (-1,-1) indicates
that no valid insertion index exists for the given point.
*/
Pair GetGridInsertionIndices (const Point& rModelPosition) const;
/** Return whether the main orientation of the slides in the slide /** Return whether the main orientation of the slides in the slide
sorter is vertical, i.e. all slides are arranged in one column. sorter is vertical, i.e. all slides are arranged in one column.
@@ -293,6 +266,14 @@ private:
sal_Int32 mnPageCount; sal_Int32 mnPageCount;
sal_Int32 mnColumnCount; sal_Int32 mnColumnCount;
sal_Int32 mnRowCount; sal_Int32 mnRowCount;
/// The maximum number of columns. Can only be larger than the current
/// number of columns when there are not enough pages to fill all
/// available columns.
sal_Int32 mnMaxColumnCount;
/// The maximum number of rows. Can only be larger than the current
/// number of rows when there are not enough pages to fill all available
/// rows.
sal_Int32 mnMaxRowCount;
Size maPageObjectSize; Size maPageObjectSize;
bool mbIsVertical; bool mbIsVertical;
@@ -371,6 +352,42 @@ private:
Rectangle GetPreviewBox (const sal_Int32 nIndex) const; Rectangle GetPreviewBox (const sal_Int32 nIndex) const;
}; };
/** Collect all values concerning the logical and visual properties of the
insertion position that is used for drag-and-drop and copy-and-past.
*/
class InsertPosition
{
public:
InsertPosition (void);
InsertPosition& operator= (const InsertPosition& rInsertPosition);
bool operator== (const InsertPosition& rInsertPosition) const;
bool operator!= (const InsertPosition& rInsertPosition) const;
sal_Int32 GetRow (void) const { return mnRow; }
sal_Int32 GetColumn (void) const { return mnColumn; }
sal_Int32 GetIndex (void) const { return mnIndex; }
Point GetLocation (void) const { return maLocation; }
bool IsAtRunStart (void) const { return mbIsAtRunStart; }
bool IsAtRunEnd (void) const { return mbIsAtRunEnd; }
bool IsExtraSpaceNeeded (void) const { return mbIsExtraSpaceNeeded; }
private:
sal_Int32 mnRow;
sal_Int32 mnColumn;
sal_Int32 mnIndex;
Point maLocation;
bool mbIsAtRunStart : 1;
bool mbIsAtRunEnd : 1;
bool mbIsExtraSpaceNeeded : 1;
friend class Layouter;
};
} } } // end of namespace ::sd::slidesorter::view } } } // end of namespace ::sd::slidesorter::view
#endif #endif

View File

@@ -1,293 +0,0 @@
/*************************************************************************
*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* Copyright 2008 by Sun Microsystems, Inc.
*
* OpenOffice.org - a multi-platform office productivity suite
*
* $RCSfile: SlsViewOverlay.hxx,v $
* $Revision: 1.10 $
*
* This file is part of OpenOffice.org.
*
* OpenOffice.org is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License version 3
* only, as published by the Free Software Foundation.
*
* OpenOffice.org is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License version 3 for more details
* (a copy is included in the LICENSE file that accompanied this code).
*
* You should have received a copy of the GNU Lesser General Public License
* version 3 along with OpenOffice.org. If not, see
* <http://www.openoffice.org/license.html>
* for a copy of the LGPLv3 License.
*
************************************************************************/
#ifndef SD_SLIDESORTER_VIEW_OVERLAY_HXX
#define SD_SLIDESORTER_VIEW_OVERLAY_HXX
#include "model/SlsSharedPageDescriptor.hxx"
#include "view/SlsILayerPainter.hxx"
#include <basegfx/polygon/b2dpolypolygon.hxx>
#include <osl/mutex.hxx>
#include <tools/gen.hxx>
#include <vcl/bitmapex.hxx>
#include <vcl/image.hxx>
#include <basegfx/range/b2drectangle.hxx>
#include <basegfx/polygon/b2dpolygon.hxx>
#include <vector>
#include <boost/scoped_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
class OutputDevice;
class Region;
namespace sd { namespace slidesorter {
class SlideSorter;
} }
namespace sd { namespace slidesorter { namespace model {
class PageEnumeration;
} } }
namespace sd { namespace slidesorter { namespace controller {
class SlideSorterController;
} } }
namespace sd { namespace slidesorter { namespace view {
class LayeredDevice;
class InsertionIndicatorOverlay;
class SelectionRectangleOverlay;
class SubstitutionOverlay;
class ViewOverlay;
class FramePainter;
/** This base class of slide sorter overlays uses the drawing layer overlay
support for the display.
*/
class OverlayBase :
public ILayerPainter,
public ::boost::enable_shared_from_this<OverlayBase>
{
public:
OverlayBase (ViewOverlay& rViewOverlay, const sal_Int32 nLayer);
virtual ~OverlayBase (void);
bool IsVisible (void) const;
void SetIsVisible (const bool bIsVisible);
virtual void SetLayerInvalidator (const SharedILayerInvalidator& rpInvalidator);
sal_Int32 GetLayerIndex (void) const;
protected:
::osl::Mutex maMutex;
ViewOverlay& mrViewOverlay;
SharedILayerInvalidator mpLayerInvalidator;
class Invalidator;
friend class Invalidator;
virtual Rectangle GetBoundingBox (void) const = 0;
private:
bool mbIsVisible;
const sal_Int32 mnLayerIndex;
void Invalidate (const Rectangle& rInvalidationBox);
};
/** During internal drag and drop the outlines of the selected slides are
painted at the mouse position in dashed lines.
*/
class SubstitutionOverlay
: public OverlayBase
{
public:
SubstitutionOverlay (ViewOverlay& rViewOverlay, const sal_Int32 nLayer);
virtual ~SubstitutionOverlay (void);
void SetAnchor (const Point& rAnchor);
/** Clear the substitution display. Until the next call of Create() no
substution is painted.
*/
void Clear (void);
/** Move the substitution display by the given amount of pixels.
*/
void Move (const Point& rPositionOffset);
void SetPosition (const Point& rPosition);
Point GetPosition (void) const;
virtual void Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea);
protected:
virtual Rectangle GetBoundingBox (void) const;
private:
/** The current position can be set by calling SetPosition() or Move().
*/
Point maPosition;
/** The substitution paints only the page object under the mouse and the
8-neighborhood around it. It uses different levels of transparency
for the center and the four elements at its sides and the four
elements at its corners. All values between 0 (opaque) and 100
(fully transparent.)
*/
static const sal_Int32 mnCenterTransparency;
static const sal_Int32 mnSideTransparency;
static const sal_Int32 mnCornerTransparency;
};
/** Slides can be selected by drawing a selection rectangle in the slide
sorter. When the left mouse button is released all slides that are at
least partially in the rectangle are selected.
*/
class SelectionRectangleOverlay
: public OverlayBase
{
public:
SelectionRectangleOverlay (ViewOverlay& rViewOverlay, const sal_Int32 nLayer);
void Start (const Point& rAnchor);
void Update (const Point& rSecondCorner);
Rectangle GetSelectionRectangle (void);
virtual void Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea);
protected:
virtual Rectangle GetBoundingBox (void) const;
private:
Point maAnchor;
Point maSecondCorner;
};
/** The insertion indicator is painted as a vertical or horizonal bar
in the space between slides.
*/
class InsertionIndicatorOverlay
: public OverlayBase
{
public:
InsertionIndicatorOverlay (ViewOverlay& rViewOverlay, const sal_Int32 nLayer);
/** Setup the insertion indicator by creating the icon. It consists of
scaled down previews of some of the selected pages.
*/
void Create (model::PageEnumeration& rSelection);
void Create (void);
/** Given a position in model coordinates this method calculates the
insertion marker both as an index in the document and as a location
used for drawing the insertion indicator.
*/
void SetLocation (const Point& rPosition);
Size GetSize (void) const;
virtual void Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea);
protected:
virtual Rectangle GetBoundingBox (void) const;
private:
// Center of the insertion indicator.
Point maLocation;
/** Remember whether the insertion indicator is displayed before (left
of or above) or after (right of or below) the page at the insertion
index.
*/
bool mbIsBeforePage;
BitmapEx maIcon;
Point maIconOffset;
::boost::scoped_ptr<FramePainter> mpShadowPainter;
void SetPositionAndSize (const Rectangle& rBoundingBox);
void SelectRepresentatives (
model::PageEnumeration& rSelection,
::std::vector<model::SharedPageDescriptor>& rDescriptors) const;
Point PaintRepresentatives (
OutputDevice& rContent,
const Size aPreviewSize,
const sal_Int32 nOffset,
const ::std::vector<model::SharedPageDescriptor>& rDescriptors) const;
void PaintPageCount (
OutputDevice& rDevice,
model::PageEnumeration& rSelection,
const Size aPreviewSize,
const Point aFirstPageOffset) const;
};
/** The view overlay manages and paints some indicators that are painted on
top of the regular view content (the page objects). It is separated
from the view to allow the indicators to be altered in position and size
without repainting the whole view content (inside that the bounding box
of the indicator). This is achieved by using the drawing layer overlay
support.
The view overlay itself simply gives access to the more specialized
classes that handle individual indicators.
*/
class ViewOverlay
{
public:
ViewOverlay (
SlideSorter& rSlideSorter,
const ::boost::shared_ptr<LayeredDevice>& rpLayeredDevice);
virtual ~ViewOverlay (void);
::boost::shared_ptr<SelectionRectangleOverlay> GetSelectionRectangleOverlay (void);
::boost::shared_ptr<InsertionIndicatorOverlay> GetInsertionIndicatorOverlay (void);
::boost::shared_ptr<SubstitutionOverlay> GetSubstitutionOverlay (void);
SlideSorter& GetSlideSorter (void) const;
::boost::shared_ptr<LayeredDevice> GetLayeredDevice (void) const;
private:
SlideSorter& mrSlideSorter;
const ::boost::shared_ptr<LayeredDevice> mpLayeredDevice;
::boost::shared_ptr<SelectionRectangleOverlay> mpSelectionRectangleOverlay;
::boost::shared_ptr<InsertionIndicatorOverlay> mpInsertionIndicatorOverlay;
::boost::shared_ptr<SubstitutionOverlay> mpSubstitutionOverlay;
};
} } } // end of namespace ::sd::slidesorter::view
#endif

View File

@@ -37,6 +37,7 @@
#include "controller/SlideSorterController.hxx" #include "controller/SlideSorterController.hxx"
#include "controller/SlsScrollBarManager.hxx" #include "controller/SlsScrollBarManager.hxx"
#include "controller/SlsProperties.hxx" #include "controller/SlsProperties.hxx"
#include "controller/SlsAnimator.hxx"
#include "view/SlideSorterView.hxx" #include "view/SlideSorterView.hxx"
#include "view/SlsTheme.hxx" #include "view/SlsTheme.hxx"
#include "model/SlideSorterModel.hxx" #include "model/SlideSorterModel.hxx"
@@ -497,17 +498,18 @@ void SlideSorter::ArrangeGUIElements (
{ {
Point aOrigin (rOffset); Point aOrigin (rOffset);
if (rSize.Width()!=0 && rSize.Height()!=0) if (rSize.Width()>0
&& rSize.Height()>0
&& GetContentWindow()
&& GetContentWindow()->IsVisible())
{ {
// Prevent untimely redraws while the view is not yet correctly // Prevent untimely redraws while the view is not yet correctly
// resized. // resized.
view::SlideSorterView::DrawLock aLock (*mpSlideSorterView); view::SlideSorterView::DrawLock aLock (*this);
if (GetContentWindow())
GetContentWindow()->EnablePaint (FALSE); GetContentWindow()->EnablePaint (FALSE);
mpSlideSorterController->Resize (Rectangle(aOrigin, rSize)); mpSlideSorterController->Resize (Rectangle(aOrigin, rSize));
if (GetContentWindow())
GetContentWindow()->EnablePaint (TRUE); GetContentWindow()->EnablePaint (TRUE);
mbLayoutPending = false; mbLayoutPending = false;
@@ -537,6 +539,9 @@ SvBorder SlideSorter::GetBorder (void)
bool SlideSorter::RelocateToWindow (::Window* pParentWindow) bool SlideSorter::RelocateToWindow (::Window* pParentWindow)
{ {
// Stop all animations for they have been started for the old window.
mpSlideSorterController->GetAnimator()->RemoveAllAnimations();
ReleaseListeners(); ReleaseListeners();
if (mpViewShell != NULL) if (mpViewShell != NULL)
@@ -548,8 +553,8 @@ bool SlideSorter::RelocateToWindow (::Window* pParentWindow)
// For accessibility we have to shortly hide the content window. This // For accessibility we have to shortly hide the content window. This
// triggers the construction of a new accessibility object for the new // triggers the construction of a new accessibility object for the new
// view shell. (One is created earlier while the construtor of the base // view shell. (One is created earlier while the construtor of the base
// class is executed. At that time the correct accessibility object can // class is executed. But because at that time the correct
// not be constructed.) // accessibility object can not be constructed we do that now.)
if (mpContentWindow.get() !=NULL) if (mpContentWindow.get() !=NULL)
{ {
mpContentWindow->Hide(); mpContentWindow->Hide();

View File

@@ -397,6 +397,11 @@ SdPage* SlideSorterViewShell::GetActualPage (void)
pCurrentPage = pDescriptor->GetPage(); pCurrentPage = pDescriptor->GetPage();
} }
if (pCurrentPage == NULL)
{
}
return pCurrentPage; return pCurrentPage;
} }
@@ -531,8 +536,8 @@ void SlideSorterViewShell::Paint (
::sd::Window* pWindow) ::sd::Window* pWindow)
{ {
SetActiveWindow (pWindow); SetActiveWindow (pWindow);
OSL_ASSERT(mpSlideSorter.get()!=NULL); OSL_ASSERT(mpSlideSorter);
if (mpSlideSorter.get() != NULL) if (mpSlideSorter)
mpSlideSorter->GetController().Paint(rBBox,pWindow); mpSlideSorter->GetController().Paint(rBBox,pWindow);
} }
@@ -542,9 +547,7 @@ void SlideSorterViewShell::Paint (
void SlideSorterViewShell::ArrangeGUIElements (void) void SlideSorterViewShell::ArrangeGUIElements (void)
{ {
OSL_ASSERT(mpSlideSorter.get()!=NULL); OSL_ASSERT(mpSlideSorter.get()!=NULL);
mpSlideSorter->ArrangeGUIElements( mpSlideSorter->ArrangeGUIElements(maViewPos, maViewSize);
maViewPos,
maViewSize);
} }
@@ -611,6 +614,8 @@ void SlideSorterViewShell::ReadFrameViewData (FrameView* pFrameView)
} }
else else
rView.GetLayouter().SetColumnCount(nSlidesPerRow,nSlidesPerRow); rView.GetLayouter().SetColumnCount(nSlidesPerRow,nSlidesPerRow);
mpSlideSorter->GetController().GetCurrentSlideManager()->CurrentSlideHasChanged(
mpFrameView->GetSelectedPage());
mpSlideSorter->GetController().Rearrange(true); mpSlideSorter->GetController().Rearrange(true);
// DrawMode for 'main' window // DrawMode for 'main' window

View File

@@ -41,7 +41,6 @@
#include "view/SlsLayouter.hxx" #include "view/SlsLayouter.hxx"
#include "view/SlsPageObjectLayouter.hxx" #include "view/SlsPageObjectLayouter.hxx"
#include "view/SlsPageObjectPainter.hxx" #include "view/SlsPageObjectPainter.hxx"
#include "view/SlsViewOverlay.hxx"
#include "view/SlsILayerPainter.hxx" #include "view/SlsILayerPainter.hxx"
#include "controller/SlideSorterController.hxx" #include "controller/SlideSorterController.hxx"
#include "controller/SlsProperties.hxx" #include "controller/SlsProperties.hxx"
@@ -331,7 +330,6 @@ SlideSorterView::SlideSorterView (SlideSorter& rSlideSorter)
mbPageObjectVisibilitiesValid (false), mbPageObjectVisibilitiesValid (false),
mpPreviewCache(), mpPreviewCache(),
mpLayeredDevice(new LayeredDevice(rSlideSorter.GetContentWindow())), mpLayeredDevice(new LayeredDevice(rSlideSorter.GetContentWindow())),
mpViewOverlay (new ViewOverlay(rSlideSorter, mpLayeredDevice)),
maVisiblePageRange(-1,-1), maVisiblePageRange(-1,-1),
mbModelChangedWhileModifyEnabled(true), mbModelChangedWhileModifyEnabled(true),
maPreviewSize(0,0), maPreviewSize(0,0),
@@ -397,9 +395,6 @@ void SlideSorterView::Dispose (void)
// Deletion of the objects and the page will be done in SdrModel // Deletion of the objects and the page will be done in SdrModel
// destructor (as long as objects and pages are added) // destructor (as long as objects and pages are added)
OSL_ASSERT(mpViewOverlay.unique());
mpViewOverlay.reset();
OSL_ASSERT(mpLayeredDevice.unique()); OSL_ASSERT(mpLayeredDevice.unique());
mpLayeredDevice.reset(); mpLayeredDevice.reset();
@@ -828,7 +823,7 @@ void SlideSorterView::CompleteRedraw (
} }
else else
{ {
View::CompleteRedraw(pDevice, rPaintArea, pRedirector); maRedrawRegion.Union(rPaintArea);
} }
#ifdef DEBUG_TIMING #ifdef DEBUG_TIMING
@@ -918,14 +913,6 @@ void SlideSorterView::ConfigurationChanged (
ViewOverlay& SlideSorterView::GetOverlay (void)
{
return *mpViewOverlay.get();
}
Pair SlideSorterView::GetVisiblePageRange (void) Pair SlideSorterView::GetVisiblePageRange (void)
{ {
if ( ! mbPageObjectVisibilitiesValid) if ( ! mbPageObjectVisibilitiesValid)
@@ -1120,21 +1107,37 @@ bool SlideSorterView::SetState (
::boost::shared_ptr<LayeredDevice> SlideSorterView::GetLayeredDevice (void) const
{
return mpLayeredDevice;
}
//===== Animator::DrawLock ==================================================== //===== Animator::DrawLock ====================================================
SlideSorterView::DrawLock::DrawLock (view::SlideSorterView& rView) SlideSorterView::DrawLock::DrawLock (
: mrView(rView) view::SlideSorterView& rView,
const SharedSdWindow& rpWindow)
: mrView(rView),
mpWindow(rpWindow)
{ {
mrView.LockRedraw(TRUE); if (mrView.mnLockRedrawSmph == 0)
mrView.maRedrawRegion.SetEmpty();
++mrView.mnLockRedrawSmph;
} }
SlideSorterView::DrawLock::DrawLock (SlideSorter& rSlideSorter) SlideSorterView::DrawLock::DrawLock (SlideSorter& rSlideSorter)
: mrView(rSlideSorter.GetView()) : mrView(rSlideSorter.GetView()),
mpWindow(rSlideSorter.GetContentWindow())
{ {
mrView.LockRedraw(TRUE); if (mrView.mnLockRedrawSmph == 0)
mrView.maRedrawRegion.SetEmpty();
++mrView.mnLockRedrawSmph;
} }
@@ -1142,7 +1145,19 @@ SlideSorterView::DrawLock::DrawLock (SlideSorter& rSlideSorter)
SlideSorterView::DrawLock::~DrawLock (void) SlideSorterView::DrawLock::~DrawLock (void)
{ {
mrView.LockRedraw(FALSE); OSL_ASSERT(mrView.mnLockRedrawSmph>0);
--mrView.mnLockRedrawSmph;
if (mrView.mnLockRedrawSmph == 0)
if (mpWindow)
{
mpWindow->Invalidate(mrView.maRedrawRegion);
mpWindow->Update();
}
/*
mrView.CompleteRedraw(
mpWindow.get(),
mrView.maRedrawRegion);
*/
} }

View File

@@ -50,6 +50,7 @@ FramePainter::FramePainter (const BitmapEx& rShadowBitmap)
maShadowBottomLeft(rShadowBitmap,-1,+1), maShadowBottomLeft(rShadowBitmap,-1,+1),
maShadowBottom(rShadowBitmap,0,+1), maShadowBottom(rShadowBitmap,0,+1),
maShadowBottomRight(rShadowBitmap,+1,+1), maShadowBottomRight(rShadowBitmap,+1,+1),
maShadowCenter(rShadowBitmap,0,0),
mbIsValid(false) mbIsValid(false)
{ {
if (rShadowBitmap.GetSizePixel().Width() == rShadowBitmap.GetSizePixel().Height() if (rShadowBitmap.GetSizePixel().Width() == rShadowBitmap.GetSizePixel().Height()
@@ -100,6 +101,7 @@ void FramePainter::PaintFrame (
maShadowBottom.PaintSide(rDevice, maShadowBottom.PaintSide(rDevice,
aBox.BottomLeft(), aBox.BottomRight(), aBox.BottomLeft(), aBox.BottomRight(),
maShadowBottomLeft, maShadowBottomRight); maShadowBottomLeft, maShadowBottomRight);
maShadowCenter.PaintCenter(rDevice,aBox);
} }
@@ -137,13 +139,17 @@ FramePainter::OffsetBitmap::OffsetBitmap (
// Enlarge the side bitmaps so that painting the frame requires less // Enlarge the side bitmaps so that painting the frame requires less
// paint calls. // paint calls.
const sal_Int32 nSideBitmapSize (64); const sal_Int32 nSideBitmapSize (64);
if (nHorizontalPosition == 0) if (nHorizontalPosition == 0 && nVerticalPosition == 0)
{
maBitmap.Scale(Size(nSideBitmapSize,nSideBitmapSize), BMP_SCALE_FAST);
}
else if (nHorizontalPosition == 0)
{ {
maBitmap.Scale(Size(nSideBitmapSize,aSize.Height()), BMP_SCALE_FAST); maBitmap.Scale(Size(nSideBitmapSize,aSize.Height()), BMP_SCALE_FAST);
} }
else if (nVerticalPosition == 0) else if (nVerticalPosition == 0)
{ {
maBitmap.Scale(Size(aSize.Width(), nSideBitmapSize), BMP_SCALE_FAST); maBitmap.Scale(Size(maBitmap.GetSizePixel().Width(), nSideBitmapSize), BMP_SCALE_FAST);
} }
} }
@@ -216,4 +222,23 @@ void FramePainter::OffsetBitmap::PaintSide (
} }
void FramePainter::OffsetBitmap::PaintCenter (
OutputDevice& rDevice,
const Rectangle& rBox) const
{
const Size aBitmapSize (maBitmap.GetSizePixel());
for (sal_Int32 nY=rBox.Top(); nY<=rBox.Bottom(); nY+=aBitmapSize.Height())
for (sal_Int32 nX=rBox.Left(); nX<=rBox.Right(); nX+=aBitmapSize.Width())
rDevice.DrawBitmapEx(
Point(nX,nY),
Size(
::std::min(aBitmapSize.Width(), rBox.Right()-nX+1),
std::min(aBitmapSize.Height(), rBox.Bottom()-nY+1)),
maBitmap);
}
} } } // end of namespace sd::slidesorter::view } } } // end of namespace sd::slidesorter::view

View File

@@ -46,6 +46,10 @@ class FramePainter
public: public:
FramePainter (const BitmapEx& rBitmap); FramePainter (const BitmapEx& rBitmap);
~FramePainter (void); ~FramePainter (void);
/** Paint a border around the given box by using a set of bitmaps for
the corners and sides.
*/
void PaintFrame (OutputDevice&rDevice, const Rectangle aBox) const; void PaintFrame (OutputDevice&rDevice, const Rectangle aBox) const;
private: private:
@@ -90,6 +94,12 @@ private:
const OffsetBitmap& rCornerBitmap1, const OffsetBitmap& rCornerBitmap1,
const OffsetBitmap& rCornerBitmap2) const; const OffsetBitmap& rCornerBitmap2) const;
/** Fill the given rectangle with the bitmap.
*/
void PaintCenter (
OutputDevice& rDevice,
const Rectangle& rBox) const;
private: private:
BitmapEx maBitmap; BitmapEx maBitmap;
Point maOffset; Point maOffset;
@@ -102,6 +112,7 @@ private:
OffsetBitmap maShadowBottomLeft; OffsetBitmap maShadowBottomLeft;
OffsetBitmap maShadowBottom; OffsetBitmap maShadowBottom;
OffsetBitmap maShadowBottomRight; OffsetBitmap maShadowBottomRight;
OffsetBitmap maShadowCenter;
bool mbIsValid; bool mbIsValid;
}; };

View File

@@ -75,15 +75,16 @@ public:
void operator () (const double nTime); void operator () (const double nTime);
void UpdateOffsets( void UpdateOffsets(
const sal_Int32 nInsertIndex, const InsertPosition& rInsertPosition,
const Size& rRequiredSpace, const Size& rRequiredSpace,
const view::Layouter& GetLayouter); const view::Layouter& GetLayouter);
void ResetOffsets (void);
/// Index of the row or column that this run represents. /// Index of the row or column that this run represents.
sal_Int32 mnRunIndex; sal_Int32 mnRunIndex;
/// The index at which to make place for the insertion indicator (-1 for /// The index at which to make place for the insertion indicator (-1 for
/// no indicator). /// no indicator).
sal_Int32 mnInsertIndex; sal_Int32 mnLocalInsertIndex;
/// Index of the first page in the run. /// Index of the first page in the run.
sal_Int32 mnStartIndex; sal_Int32 mnStartIndex;
/// Index of the last page in the run. /// Index of the last page in the run.
@@ -132,8 +133,7 @@ public:
virtual ~Implementation (void); virtual ~Implementation (void);
void SetInsertPosition ( void SetInsertPosition (
const sal_Int32 nPageIndex, const InsertPosition& rInsertPosition,
const Pair& rVisualInsertionIndices,
const Size& rIconSize); const Size& rIconSize);
void Reset (void); void Reset (void);
@@ -150,15 +150,12 @@ private:
::boost::shared_ptr<controller::Animator> mpAnimator; ::boost::shared_ptr<controller::Animator> mpAnimator;
typedef ::std::set<SharedPageObjectRun, PageObjectRun::Comparator> RunContainer; typedef ::std::set<SharedPageObjectRun, PageObjectRun::Comparator> RunContainer;
RunContainer maRuns; RunContainer maRuns;
/// The current insertion index. The special value -1 means that there InsertPosition maInsertPosition;
/// is no current insertion index.
sal_Int32 mnCurrentInsertPosition;
Pair maVisualInsertionIndices;
void StopAnimation (void); void StopAnimation (void);
SharedPageObjectRun GetRun ( SharedPageObjectRun GetRun (
view::Layouter& rLayouter, view::Layouter& rLayouter,
const sal_Int32 nRowIndex, const InsertPosition& rInsertPosition,
const bool bCreate = true); const bool bCreate = true);
RunContainer::iterator FindRun (const sal_Int32 nRunIndex) const; RunContainer::iterator FindRun (const sal_Int32 nRunIndex) const;
}; };
@@ -178,11 +175,10 @@ InsertAnimator::InsertAnimator (SlideSorter& rSlideSorter)
void InsertAnimator::SetInsertPosition ( void InsertAnimator::SetInsertPosition (
const sal_Int32 nPageIndex, const InsertPosition& rInsertPosition,
const Pair& rVisualInsertionIndices,
const Size& rIconSize) const Size& rIconSize)
{ {
mpImplementation->SetInsertPosition(nPageIndex, rVisualInsertionIndices, rIconSize); mpImplementation->SetInsertPosition(rInsertPosition, rIconSize);
} }
@@ -203,8 +199,7 @@ InsertAnimator::Implementation::Implementation (SlideSorter& rSlideSorter)
mrView(rSlideSorter.GetView()), mrView(rSlideSorter.GetView()),
mpAnimator(rSlideSorter.GetController().GetAnimator()), mpAnimator(rSlideSorter.GetController().GetAnimator()),
maRuns(), maRuns(),
mnCurrentInsertPosition(-1), maInsertPosition()
maVisualInsertionIndices()
{ {
} }
@@ -220,17 +215,15 @@ InsertAnimator::Implementation::~Implementation (void)
void InsertAnimator::Implementation::SetInsertPosition ( void InsertAnimator::Implementation::SetInsertPosition (
const sal_Int32 nPageIndex, const InsertPosition& rInsertPosition,
const Pair& rVisualInsertionIndices,
const Size& rIconSize) const Size& rIconSize)
{ {
if (nPageIndex==mnCurrentInsertPosition && rVisualInsertionIndices==maVisualInsertionIndices) if (maInsertPosition == rInsertPosition)
return; return;
SharedPageObjectRun pOldRun (GetRun(mrView.GetLayouter(), maVisualInsertionIndices.A())); SharedPageObjectRun pOldRun (GetRun(mrView.GetLayouter(), maInsertPosition));
SharedPageObjectRun pCurrentRun (GetRun(mrView.GetLayouter(), rVisualInsertionIndices.A())); SharedPageObjectRun pCurrentRun (GetRun(mrView.GetLayouter(), rInsertPosition));
mnCurrentInsertPosition = nPageIndex; maInsertPosition = rInsertPosition;
maVisualInsertionIndices = rVisualInsertionIndices;
// When the new insert position is in a different run then move the page // When the new insert position is in a different run then move the page
// objects in the old run to their default positions. // objects in the old run to their default positions.
@@ -238,7 +231,7 @@ void InsertAnimator::Implementation::SetInsertPosition (
{ {
if (pOldRun) if (pOldRun)
{ {
pOldRun->UpdateOffsets(-1, Size(0,0), mrView.GetLayouter()); pOldRun->ResetOffsets();
maRuns.insert(pOldRun); maRuns.insert(pOldRun);
} }
} }
@@ -247,7 +240,7 @@ void InsertAnimator::Implementation::SetInsertPosition (
{ {
const sal_Int32 nColumnCount (mrView.GetLayouter().GetColumnCount()); const sal_Int32 nColumnCount (mrView.GetLayouter().GetColumnCount());
pCurrentRun->UpdateOffsets( pCurrentRun->UpdateOffsets(
nColumnCount > 1 ? maVisualInsertionIndices.B() : maVisualInsertionIndices.A(), rInsertPosition,
nColumnCount > 1 ? Size(rIconSize.Width(),0) : Size(0, rIconSize.Height()), nColumnCount > 1 ? Size(rIconSize.Width(),0) : Size(0, rIconSize.Height()),
mrView.GetLayouter()); mrView.GetLayouter());
maRuns.insert(pCurrentRun); maRuns.insert(pCurrentRun);
@@ -259,7 +252,7 @@ void InsertAnimator::Implementation::SetInsertPosition (
void InsertAnimator::Implementation::Reset (void) void InsertAnimator::Implementation::Reset (void)
{ {
SetInsertPosition(-1, Pair(-1,-1), Size(0,0)); SetInsertPosition(InsertPosition(), Size(0,0));
} }
@@ -267,10 +260,11 @@ void InsertAnimator::Implementation::Reset (void)
SharedPageObjectRun InsertAnimator::Implementation::GetRun ( SharedPageObjectRun InsertAnimator::Implementation::GetRun (
view::Layouter& rLayouter, view::Layouter& rLayouter,
const sal_Int32 nRowIndex, const InsertPosition& rInsertPosition,
const bool bCreate) const bool bCreate)
{ {
if (nRowIndex < 0) const sal_Int32 nRow (rInsertPosition.GetRow());
if (nRow < 0)
return SharedPageObjectRun(); return SharedPageObjectRun();
RunContainer::iterator iRun (maRuns.end()); RunContainer::iterator iRun (maRuns.end());
@@ -287,17 +281,17 @@ SharedPageObjectRun InsertAnimator::Implementation::GetRun (
} }
else else
{ {
iRun = FindRun(nRowIndex); iRun = FindRun(nRow);
if (iRun == maRuns.end() && bCreate) if (iRun == maRuns.end() && bCreate)
{ {
// Create a new run. // Create a new run.
const sal_Int32 nStartIndex (rLayouter.GetIndex(nRowIndex,0)); const sal_Int32 nStartIndex (rLayouter.GetIndex(nRow, 0));
const sal_Int32 nEndIndex (rLayouter.GetIndex(nRowIndex,rLayouter.GetColumnCount()-1)); const sal_Int32 nEndIndex (rLayouter.GetIndex(nRow, rLayouter.GetColumnCount()-1));
if (nStartIndex <= nEndIndex) if (nStartIndex <= nEndIndex)
{ {
iRun = maRuns.insert(SharedPageObjectRun(new PageObjectRun( iRun = maRuns.insert(SharedPageObjectRun(new PageObjectRun(
*this, *this,
nRowIndex, nRow,
nStartIndex, nStartIndex,
nEndIndex))).first; nEndIndex))).first;
OSL_ASSERT(iRun != maRuns.end()); OSL_ASSERT(iRun != maRuns.end());
@@ -334,7 +328,7 @@ void InsertAnimator::Implementation::RemoveRun (PageObjectRun* pRun)
if (pRun != NULL) if (pRun != NULL)
{ {
// Do not remove runs that show the space for the insertion indicator. // Do not remove runs that show the space for the insertion indicator.
if (pRun->mnInsertIndex == -1) if (pRun->mnLocalInsertIndex == -1)
maRuns.erase(FindRun(pRun->mnRunIndex)); maRuns.erase(FindRun(pRun->mnRunIndex));
} }
else else
@@ -355,7 +349,7 @@ PageObjectRun::PageObjectRun (
const sal_Int32 nStartIndex, const sal_Int32 nStartIndex,
const sal_Int32 nEndIndex) const sal_Int32 nEndIndex)
: mnRunIndex(nRunIndex), : mnRunIndex(nRunIndex),
mnInsertIndex(-1), mnLocalInsertIndex(-1),
mnStartIndex(nStartIndex), mnStartIndex(nStartIndex),
mnEndIndex(nEndIndex), mnEndIndex(nEndIndex),
maStartOffset(), maStartOffset(),
@@ -382,21 +376,25 @@ PageObjectRun::~PageObjectRun (void)
void PageObjectRun::UpdateOffsets( void PageObjectRun::UpdateOffsets(
const sal_Int32 nInsertIndex, const InsertPosition& rInsertPosition,
const Size& rRequiredSpace, const Size& rRequiredSpace,
const view::Layouter& rLayouter) const view::Layouter& rLayouter)
{ {
if (nInsertIndex != mnInsertIndex) const sal_Int32 nLocalInsertIndex(rLayouter.GetColumnCount()==1
? rInsertPosition.GetRow()
: rInsertPosition.GetColumn());
if (nLocalInsertIndex != mnLocalInsertIndex)
{ {
mnInsertIndex = nInsertIndex; mnLocalInsertIndex = nLocalInsertIndex;
model::SlideSorterModel& rModel (mrAnimatorAccess.GetModel()); model::SlideSorterModel& rModel (mrAnimatorAccess.GetModel());
Point aLeadingOffset; Point aLeadingOffset;
Point aTrailingOffset; Point aTrailingOffset;
const sal_Int32 nRunLength (mnEndIndex - mnStartIndex + 1);
const bool bUseX (rLayouter.GetColumnCount() > 1); const bool bUseX (rLayouter.GetColumnCount() > 1);
if (mnInsertIndex == 0) const sal_Int32 nRunLength (mnEndIndex - mnStartIndex + 1);
if (rInsertPosition.IsAtRunStart())
{ {
// Insertion position is at the left or top of the run.
const Rectangle aInnerBox (rLayouter.GetPageObjectLayouter()->GetBoundingBox( const Rectangle aInnerBox (rLayouter.GetPageObjectLayouter()->GetBoundingBox(
Point(0,0), Point(0,0),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
@@ -407,8 +405,9 @@ void PageObjectRun::UpdateOffsets(
else else
aTrailingOffset.Y() = ::std::max(0L, rRequiredSpace.Height()-aAvailableSpace.Y()); aTrailingOffset.Y() = ::std::max(0L, rRequiredSpace.Height()-aAvailableSpace.Y());
} }
else if (mnInsertIndex == nRunLength) else if (rInsertPosition.IsAtRunEnd() && rInsertPosition.IsExtraSpaceNeeded())
{ {
// Insertion position is at the right or bottom of the run.
const Rectangle aOuterBox (rLayouter.GetPageObjectBox(mnEndIndex)); const Rectangle aOuterBox (rLayouter.GetPageObjectBox(mnEndIndex));
const Rectangle aInnerBox (rLayouter.GetPageObjectLayouter()->GetBoundingBox( const Rectangle aInnerBox (rLayouter.GetPageObjectLayouter()->GetBoundingBox(
aOuterBox.TopLeft(), aOuterBox.TopLeft(),
@@ -420,14 +419,15 @@ void PageObjectRun::UpdateOffsets(
else else
aLeadingOffset.Y() = ::std::min(0L, aAvailableSpace.Y()-rRequiredSpace.Height()); aLeadingOffset.Y() = ::std::min(0L, aAvailableSpace.Y()-rRequiredSpace.Height());
} }
else if (mnInsertIndex > 0) else if ( ! rInsertPosition.IsAtRunEnd())
{ {
// Insertion position is somewhere in the middle of the run.
const Rectangle aBox1 (rLayouter.GetPageObjectLayouter()->GetBoundingBox( const Rectangle aBox1 (rLayouter.GetPageObjectLayouter()->GetBoundingBox(
rModel.GetPageDescriptor(mnStartIndex + nInsertIndex - 1), rModel.GetPageDescriptor(mnStartIndex + mnLocalInsertIndex - 1),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
const Rectangle aBox2 (rLayouter.GetPageObjectLayouter()->GetBoundingBox( const Rectangle aBox2 (rLayouter.GetPageObjectLayouter()->GetBoundingBox(
rModel.GetPageDescriptor(mnStartIndex + nInsertIndex), rModel.GetPageDescriptor(mnStartIndex + mnLocalInsertIndex),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
const Size aDelta ( const Size aDelta (
@@ -449,7 +449,7 @@ void PageObjectRun::UpdateOffsets(
model::SharedPageDescriptor pDescriptor(rModel.GetPageDescriptor(nIndex+mnStartIndex)); model::SharedPageDescriptor pDescriptor(rModel.GetPageDescriptor(nIndex+mnStartIndex));
if (pDescriptor) if (pDescriptor)
maStartOffset[nIndex] = pDescriptor->GetVisualState().GetLocationOffset(); maStartOffset[nIndex] = pDescriptor->GetVisualState().GetLocationOffset();
maEndOffset[nIndex] = nIndex < nInsertIndex maEndOffset[nIndex] = nIndex < mnLocalInsertIndex
? aLeadingOffset ? aLeadingOffset
: aTrailingOffset; : aTrailingOffset;
} }
@@ -460,6 +460,24 @@ void PageObjectRun::UpdateOffsets(
void PageObjectRun::ResetOffsets (void)
{
mnLocalInsertIndex = -1;
const sal_Int32 nRunLength (mnEndIndex - mnStartIndex + 1);
model::SlideSorterModel& rModel (mrAnimatorAccess.GetModel());
for (sal_Int32 nIndex=0; nIndex<nRunLength; ++nIndex)
{
model::SharedPageDescriptor pDescriptor(rModel.GetPageDescriptor(nIndex+mnStartIndex));
if (pDescriptor)
maStartOffset[nIndex] = pDescriptor->GetVisualState().GetLocationOffset();
maEndOffset[nIndex] = Point(0,0);
}
RestartAnimation();
}
void PageObjectRun::RestartAnimation (void) void PageObjectRun::RestartAnimation (void)
{ {
// Stop the current animation. // Stop the current animation.

View File

@@ -0,0 +1,449 @@
/*************************************************************************
*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* Copyright 2008 by Sun Microsystems, Inc.
*
* OpenOffice.org - a multi-platform office productivity suite
*
* This file is part of OpenOffice.org.
*
* OpenOffice.org is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License version 3
* only, as published by the Free Software Foundation.
*
* OpenOffice.org is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License version 3 for more details
* (a copy is included in the LICENSE file that accompanied this code).
*
* You should have received a copy of the GNU Lesser General Public License
* version 3 along with OpenOffice.org. If not, see
* <http://www.openoffice.org/license.html>
* for a copy of the LGPLv3 License.
*
************************************************************************/
#include "precompiled_sd.hxx"
#include "view/SlsInsertionIndicatorOverlay.hxx"
#include "SlideSorter.hxx"
#include "model/SlsPageEnumeration.hxx"
#include "view/SlideSorterView.hxx"
#include "view/SlsLayouter.hxx"
#include "view/SlsPageObjectLayouter.hxx"
#include "view/SlsTheme.hxx"
#include "cache/SlsPageCache.hxx"
#include "controller/SlsTransferable.hxx"
#include "SlsFramePainter.hxx"
#include "SlsLayeredDevice.hxx"
#include "DrawDocShell.hxx"
#include "drawdoc.hxx"
#include "sdpage.hxx"
#include "sdmod.hxx"
#include <vcl/virdev.hxx>
#include <basegfx/range/b2drectangle.hxx>
#include <basegfx/tools/canvastools.hxx>
#include <basegfx/polygon/b2dpolygon.hxx>
#include <basegfx/polygon/b2dpolygontools.hxx>
namespace {
static const double gnPreviewOffsetScale = 1.0 / 8.0;
Rectangle GrowRectangle (const Rectangle& rBox, const sal_Int32 nOffset)
{
return Rectangle (
rBox.Left() - nOffset,
rBox.Top() - nOffset,
rBox.Right() + nOffset,
rBox.Bottom() + nOffset);
}
sal_Int32 RoundToInt (const double nValue) { return sal_Int32(::rtl::math::round(nValue)); }
} // end of anonymous namespace
namespace sd { namespace slidesorter { namespace view {
//===== InsertionIndicatorOverlay ===========================================
const static sal_Int32 gnShadowBorder = 3;
const static sal_Int32 gnSuperScaleFactor = 1;
const static sal_Int32 gnAngle = 0; // measured in 10th of degrees
InsertionIndicatorOverlay::InsertionIndicatorOverlay (SlideSorter& rSlideSorter)
: mrSlideSorter(rSlideSorter),
mbIsVisible(false),
mnLayerIndex(2),
mpLayerInvalidator(),
maLocation(),
maIcon(),
maIconOffset(),
mpShadowPainter(new FramePainter(mrSlideSorter.GetTheme()->GetIcon(Theme::RawInsertShadow)))
{
}
InsertionIndicatorOverlay::~InsertionIndicatorOverlay (void)
{
Hide();
}
void InsertionIndicatorOverlay::Create (const controller::Transferable* pTransferable)
{
if (pTransferable == NULL)
return;
sal_Int32 nSelectionCount (0);
if (pTransferable->HasPageBookmarks())
nSelectionCount = pTransferable->GetPageBookmarks().Count();
else
{
DrawDocShell* pDataDocShell = dynamic_cast<DrawDocShell*>(&pTransferable->GetDocShell());
if (pDataDocShell != NULL)
{
SdDrawDocument* pDataDocument = pDataDocShell->GetDoc();
if (pDataDocument != NULL)
nSelectionCount = pDataDocument->GetSdPageCount(PK_STANDARD);
}
}
Create(pTransferable->GetRepresentatives(), nSelectionCount);
}
void InsertionIndicatorOverlay::Create (
const ::std::vector<Bitmap>& rRepresentatives,
const sal_Int32 nSelectionCount)
{
view::Layouter& rLayouter (mrSlideSorter.GetView().GetLayouter());
::boost::shared_ptr<view::PageObjectLayouter> pPageObjectLayouter (
rLayouter.GetPageObjectLayouter());
::boost::shared_ptr<view::Theme> pTheme (mrSlideSorter.GetTheme());
const Size aOriginalPreviewSize (pPageObjectLayouter->GetPreviewSize());
const double nPreviewScale (0.5);
const Size aPreviewSize (
RoundToInt(aOriginalPreviewSize.Width()*nPreviewScale),
RoundToInt(aOriginalPreviewSize.Height()*nPreviewScale));
const sal_Int32 nOffset (
RoundToInt(Min(aPreviewSize.Width(),aPreviewSize.Height()) * gnPreviewOffsetScale));
// Determine size and offset depending on the number of previews.
sal_Int32 nCount (rRepresentatives.size());
if (nCount > 0)
--nCount;
Size aIconSize(
aPreviewSize.Width() + 2 * gnShadowBorder + nCount*nOffset,
aPreviewSize.Height() + 2 * gnShadowBorder + nCount*nOffset);
maIconOffset = Point(gnShadowBorder, gnShadowBorder);
// Create virtual devices for bitmap and mask whose bitmaps later be
// combined to form the BitmapEx of the icon.
VirtualDevice aContent (
*mrSlideSorter.GetContentWindow(),
0,
0);
if (gnAngle != 0)
{
aIconSize = Size(
RoundToInt(
cos(gnAngle/1800.0*M_PI) * aIconSize.Width()
+ sin(gnAngle/1800.0*M_PI) * aIconSize.Height()),
RoundToInt(
sin(gnAngle/1800.0*M_PI) * aIconSize.Width()
+ cos(gnAngle/1800.0*M_PI) * aIconSize.Height()));
}
aContent.SetOutputSizePixel(aIconSize);
aContent.SetFillColor();
aContent.SetLineColor(pTheme->GetColor(Theme::PreviewBorder));
const Point aOffset = PaintRepresentatives(aContent, aPreviewSize, nOffset, rRepresentatives);
PaintPageCount(aContent, nSelectionCount, aPreviewSize, aOffset);
maIcon = aContent.GetBitmapEx(Point(0,0), aIconSize);
maIcon.Scale(aIconSize);
}
void InsertionIndicatorOverlay::SelectRepresentatives (
model::PageEnumeration& rSelection,
::std::vector<model::SharedPageDescriptor>& rDescriptors) const
{
sal_Int32 nCount (0);
while (rSelection.HasMoreElements())
{
if (nCount++ >= 3)
break;
rDescriptors.push_back(rSelection.GetNextElement());
}
}
Point InsertionIndicatorOverlay::PaintRepresentatives (
OutputDevice& rContent,
const Size aPreviewSize,
const sal_Int32 nOffset,
const ::std::vector<Bitmap>& rRepresentatives) const
{
const Point aOffset (0,rRepresentatives.size()==1 ? -nOffset : 0);
// Paint the pages.
Point aPageOffset (0,0);
double nTransparency (0);
for (sal_Int32 nIndex=2; nIndex>=0; --nIndex)
{
if (rRepresentatives.size() <= nIndex)
continue;
switch(nIndex)
{
case 0 :
aPageOffset = Point(0, nOffset);
nTransparency = 0.85;
break;
case 1:
aPageOffset = Point(nOffset, 0);
nTransparency = 0.75;
break;
case 2:
aPageOffset = Point(2*nOffset, 2*nOffset);
nTransparency = 0.65;
break;
}
aPageOffset += aOffset;
aPageOffset.X() += gnShadowBorder;
aPageOffset.Y() += gnShadowBorder;
::boost::shared_ptr<cache::PageCache> pPreviewCache (
mrSlideSorter.GetView().GetPreviewCache());
Bitmap aPreview (rRepresentatives[nIndex]);
const double nScale (double(aPreviewSize.Width())/double(aPreview.GetSizePixel().Width()));
const Size aSuperSampleSize(
aPreviewSize.Width()*gnSuperScaleFactor,
aPreviewSize.Height()*gnSuperScaleFactor);
if (gnAngle != 0)
{
aPreview.Scale(aSuperSampleSize, BMP_SCALE_INTERPOLATE);
aPreview.Rotate(gnAngle, Color(128,0,0,255));
aPreview.Scale(1.0/gnSuperScaleFactor,1.0/gnSuperScaleFactor, BMP_SCALE_INTERPOLATE);
}
else
{
aPreview.Scale(aPreviewSize, BMP_SCALE_INTERPOLATE);
}
rContent.DrawBitmapEx(aPageOffset, aPreview);
// Tone down the bitmap. The further back the darker it becomes.
Rectangle aBox (
aPageOffset.X(),
aPageOffset.Y(),
aPageOffset.X()+aPreviewSize.Width()-1,
aPageOffset.Y()+aPreviewSize.Height()-1);
rContent.SetFillColor(COL_BLACK);
rContent.SetLineColor();
rContent.DrawTransparent(
::basegfx::B2DPolyPolygon(::basegfx::tools::createPolygonFromRect(
::basegfx::B2DRectangle(aBox.Left(), aBox.Top(), aBox.Right()+1, aBox.Bottom()+1),
0,
0)),
nTransparency);
// Draw border around preview.
Rectangle aBorderBox (GrowRectangle(aBox, 1));
rContent.SetLineColor(COL_GRAY);
rContent.SetFillColor();
rContent.DrawRect(aBorderBox);
// Draw shadow around preview.
mpShadowPainter->PaintFrame(rContent, aBorderBox);
}
return aPageOffset;
}
void InsertionIndicatorOverlay::PaintPageCount (
OutputDevice& rDevice,
const sal_Int32 nSelectionCount,
const Size aPreviewSize,
const Point aFirstPageOffset) const
{
// Paint the number of slides.
::boost::shared_ptr<view::Theme> pTheme (mrSlideSorter.GetTheme());
::boost::shared_ptr<Font> pFont(Theme::GetFont(Theme::PageCountFont, rDevice));
if (pFont)
{
::rtl::OUString sNumber (::rtl::OUString::valueOf(nSelectionCount));
// Determine the size of the (painted) text and create a bounding
// box that centers the text on the first preview.
rDevice.SetFont(*pFont);
Rectangle aTextBox;
rDevice.GetTextBoundRect(aTextBox, sNumber);
Point aTextOffset (aTextBox.TopLeft());
Size aTextSize (aTextBox.GetSize());
// Place text inside the first page preview.
Point aTextLocation(aFirstPageOffset);
// Center the text.
aTextLocation += Point(
(aPreviewSize.Width()-aTextBox.GetWidth())/2,
(aPreviewSize.Height()-aTextBox.GetHeight())/2);
aTextBox = Rectangle(aTextLocation, aTextSize);
// Paint background, border and text.
static const sal_Int32 nBorder = 5;
rDevice.SetFillColor(pTheme->GetColor(Theme::Selection));
rDevice.SetLineColor(pTheme->GetColor(Theme::Selection));
rDevice.DrawRect(GrowRectangle(aTextBox, nBorder));
rDevice.SetFillColor();
rDevice.SetLineColor(COL_WHITE);
rDevice.DrawRect(GrowRectangle(aTextBox, nBorder-1));
rDevice.SetTextColor(COL_WHITE);
rDevice.DrawText(aTextBox.TopLeft()-aTextOffset, sNumber);
}
}
void InsertionIndicatorOverlay::SetLocation (const Point& rLocation)
{
const Point aTopLeft (
rLocation - Point(
maIcon.GetSizePixel().Width()/2,
maIcon.GetSizePixel().Height()/2));
if (maLocation != aTopLeft)
{
const Rectangle aOldBoundingBox (GetBoundingBox());
maLocation = aTopLeft;
if (mpLayerInvalidator && IsVisible())
{
mpLayerInvalidator->Invalidate(aOldBoundingBox);
mpLayerInvalidator->Invalidate(GetBoundingBox());
}
}
}
void InsertionIndicatorOverlay::Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea)
{
(void)rRepaintArea;
if ( ! IsVisible())
return;
rDevice.DrawImage(maLocation, maIcon);
}
void InsertionIndicatorOverlay::SetLayerInvalidator (const SharedILayerInvalidator& rpInvalidator)
{
mpLayerInvalidator = rpInvalidator;
if (mbIsVisible && mpLayerInvalidator)
mpLayerInvalidator->Invalidate(GetBoundingBox());
}
bool InsertionIndicatorOverlay::IsVisible (void) const
{
return mbIsVisible;
}
void InsertionIndicatorOverlay::Show (void)
{
if ( ! mbIsVisible)
{
mbIsVisible = true;
::boost::shared_ptr<LayeredDevice> pLayeredDevice (
mrSlideSorter.GetView().GetLayeredDevice());
if (pLayeredDevice)
{
pLayeredDevice->RegisterPainter(shared_from_this(), mnLayerIndex);
if (mpLayerInvalidator)
mpLayerInvalidator->Invalidate(GetBoundingBox());
}
}
}
void InsertionIndicatorOverlay::Hide (void)
{
if (mbIsVisible)
{
mbIsVisible = false;
::boost::shared_ptr<LayeredDevice> pLayeredDevice (
mrSlideSorter.GetView().GetLayeredDevice());
if (pLayeredDevice)
{
if (mpLayerInvalidator)
mpLayerInvalidator->Invalidate(GetBoundingBox());
pLayeredDevice->RemovePainter(shared_from_this(), mnLayerIndex);
}
}
}
Rectangle InsertionIndicatorOverlay::GetBoundingBox (void) const
{
return Rectangle(maLocation, maIcon.GetSizePixel());
}
Size InsertionIndicatorOverlay::GetSize (void) const
{
return Size(
maIcon.GetSizePixel().Width() + 10,
maIcon.GetSizePixel().Height() + 10);
}
} } } // end of namespace ::sd::slidesorter::view

View File

@@ -91,6 +91,7 @@ private:
}; };
} } } // end of namespace ::sd::slidesorter::view } } } // end of namespace ::sd::slidesorter::view
#endif #endif

View File

@@ -54,10 +54,12 @@ Layouter::Layouter (const SharedSdWindow& rpWindow)
mnPreferredWidth(200), mnPreferredWidth(200),
mnMaximalWidth(300), mnMaximalWidth(300),
mnMinimalColumnCount(1), mnMinimalColumnCount(1),
mnMaximalColumnCount(1), mnMaximalColumnCount(4),
mnPageCount(0), mnPageCount(0),
mnColumnCount(1), mnColumnCount(1),
mnRowCount(0), mnRowCount(0),
mnMaxColumnCount(0),
mnMaxRowCount(0),
maPageObjectSize(1,1), maPageObjectSize(1,1),
mbIsVertical(true) mbIsVertical(true)
{ {
@@ -211,6 +213,10 @@ bool Layouter::RearrangeHorizontal (
nPageCount)); nPageCount));
maPageObjectSize = mpPageObjectLayouter->GetPageObjectSize(); maPageObjectSize = mpPageObjectLayouter->GetPageObjectSize();
mnMaxColumnCount = (rWindowSize.Width() - mnLeftBorder - mnRightBorder)
/ (maPageObjectSize.Width() + mnHorizontalGap);
mnMaxRowCount = 1;
return true; return true;
} }
else else
@@ -289,6 +295,11 @@ bool Layouter::RearrangeVertical (
nPageCount)); nPageCount));
maPageObjectSize = mpPageObjectLayouter->GetPageObjectSize(); maPageObjectSize = mpPageObjectLayouter->GetPageObjectSize();
mnMaxColumnCount = (rWindowSize.Width() - mnLeftBorder - mnRightBorder)
/ (maPageObjectSize.Width() + mnHorizontalGap);
mnMaxRowCount = (rWindowSize.Height() - mnTopBorder - mnBottomBorder)
/ (maPageObjectSize.Height() + mnVerticalGap);
return true; return true;
} }
else else
@@ -462,15 +473,54 @@ Rectangle Layouter::GetPreviewBox (const sal_Int32 nIndex) const
Point Layouter::GetInsertionIndicatorLocation ( InsertPosition Layouter::GetInsertPosition (
const Pair& rVisualIndices, const Point& rModelPosition,
const Size& rIndicatorSize) const const Size& rIndicatorSize) const
{ {
if (rVisualIndices.B() < 0) InsertPosition aPosition;
// Determine logical position.
if (mnColumnCount == 1)
{
const sal_Int32 nY = rModelPosition.Y() - mnTopBorder + maPageObjectSize.Height()/2;
const sal_Int32 nRowHeight (maPageObjectSize.Height() + mnVerticalGap);
aPosition.mnRow = ::std::min(mnPageCount, nY / nRowHeight);
aPosition.mnColumn = 0;
aPosition.mnIndex = aPosition.mnRow;
aPosition.mbIsAtRunStart = (aPosition.mnRow == 0);
aPosition.mbIsAtRunEnd = (aPosition.mnRow == mnRowCount);
aPosition.mbIsExtraSpaceNeeded = (aPosition.mnRow >= mnMaxRowCount);
}
else
{
aPosition.mnRow = ::std::min(
mnRowCount-1,
GetRowAtPosition (rModelPosition.Y(), true, GM_BOTH));
const sal_Int32 nX = rModelPosition.X() - mnLeftBorder + maPageObjectSize.Width()/2;
const sal_Int32 nRowWidth (maPageObjectSize.Width() + mnHorizontalGap);
aPosition.mnColumn = ::std::min(mnColumnCount, nX / nRowWidth);
aPosition.mnIndex = aPosition.mnRow * mnColumnCount + aPosition.mnColumn;
aPosition.mbIsAtRunStart = (aPosition.mnColumn == 0);
aPosition.mbIsAtRunEnd = (aPosition.mnColumn == mnColumnCount);
if (aPosition.mnIndex >= mnPageCount)
{
aPosition.mnIndex = mnPageCount;
aPosition.mnRow = mnRowCount-1;
aPosition.mnColumn = mnPageCount%mnColumnCount;
aPosition.mbIsAtRunEnd = true;
}
aPosition.mbIsExtraSpaceNeeded = (aPosition.mnColumn >= mnMaxColumnCount);
}
// Determine visual position.
if (mnColumnCount == 1)
{ {
// Place indicator between rows of a single column of pages. // Place indicator between rows of a single column of pages.
if (rVisualIndices.A() == 0) if (aPosition.mbIsAtRunStart)
{ {
// Place indicator at the top of the column. // Place indicator at the top of the column.
const Rectangle aOuterBox (GetPageObjectBox(0)); const Rectangle aOuterBox (GetPageObjectBox(0));
@@ -478,71 +528,95 @@ Point Layouter::GetInsertionIndicatorLocation (
aOuterBox.TopLeft(), aOuterBox.TopLeft(),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
return Point(aPreviewBox.Center().X(), aOuterBox.Top()+rIndicatorSize.Height()/2); aPosition.maLocation.X() = aPreviewBox.Center().X();
aPosition.maLocation.Y() = aOuterBox.Top()+rIndicatorSize.Height()/2;
} }
else if (rVisualIndices.A() == mnRowCount) else if (aPosition.mbIsAtRunEnd)
{ {
// Place indicator at the bottom of the column.
const Rectangle aOuterBox (GetPageObjectBox(mnRowCount-1)); const Rectangle aOuterBox (GetPageObjectBox(mnRowCount-1));
const Rectangle aPreviewBox (mpPageObjectLayouter->GetBoundingBox( const Rectangle aPreviewBox (mpPageObjectLayouter->GetBoundingBox(
aOuterBox.TopLeft(), aOuterBox.TopLeft(),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
return Point(aPreviewBox.Center().X(), aOuterBox.Bottom()-rIndicatorSize.Height()/2); if (aPosition.mbIsExtraSpaceNeeded)
{
// Place indicator at the bottom of the column.
aPosition.maLocation.X() = aPreviewBox.Center().X();
aPosition.maLocation.Y() = aOuterBox.Bottom()-rIndicatorSize.Height()/2;
}
else
{
// Place indicator at the bottom of the column in the space
// that is available below the last page.
aPosition.maLocation.X() = aPreviewBox.Center().X();
aPosition.maLocation.Y() = aOuterBox.Bottom()+rIndicatorSize.Height()/2;
}
} }
else else
{ {
// Place indicator between two rows. // Place indicator between two rows.
const Rectangle aBox1 (mpPageObjectLayouter->GetBoundingBox( const Rectangle aBox1 (mpPageObjectLayouter->GetBoundingBox(
GetPageObjectBox(rVisualIndices.A()-1).TopLeft(), GetPageObjectBox(aPosition.mnRow-1).TopLeft(),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
const Rectangle aBox2 (mpPageObjectLayouter->GetBoundingBox( const Rectangle aBox2 (mpPageObjectLayouter->GetBoundingBox(
GetPageObjectBox(rVisualIndices.A()).TopLeft(), GetPageObjectBox(aPosition.mnRow).TopLeft(),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
return (aBox1.Center() + aBox2.Center() + Point(1,1)) / 2; aPosition.maLocation = (aBox1.Center() + aBox2.Center() + Point(1,1)) / 2;
} }
} }
else else
{ {
// Place indicator between columns in one row. // Place indicator between columns in one row.
const sal_Int32 nIndex (rVisualIndices.A() * mnColumnCount + rVisualIndices.B()); if (aPosition.mbIsAtRunStart)
if (rVisualIndices.B() == 0)
{ {
// Place indicator at the left of the row. // Place indicator at the left of the row.
const Rectangle aOuterBox (GetPageObjectBox(nIndex)); const Rectangle aOuterBox (GetPageObjectBox(aPosition.mnIndex));
const Rectangle aPreviewBox (mpPageObjectLayouter->GetBoundingBox( const Rectangle aPreviewBox (mpPageObjectLayouter->GetBoundingBox(
aOuterBox.TopLeft(), aOuterBox.TopLeft(),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
return Point(aOuterBox.Left()+rIndicatorSize.Width()/2, aPreviewBox.Center().Y()); aPosition.maLocation.X() = aOuterBox.Left()+rIndicatorSize.Width()/2;
aPosition.maLocation.Y() = aPreviewBox.Center().Y();
} }
else if (rVisualIndices.B() == mnColumnCount) else if (aPosition.mbIsAtRunEnd)
{
const Rectangle aOuterBox (GetPageObjectBox(aPosition.mnIndex-1));
const Rectangle aPreviewBox (mpPageObjectLayouter->GetBoundingBox(
aOuterBox.TopLeft(),
PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem));
if (aPosition.mbIsExtraSpaceNeeded)
{ {
// Place indicator at the end of the row. // Place indicator at the end of the row.
const Rectangle aOuterBox (GetPageObjectBox(nIndex-1)); aPosition.maLocation.X() = aOuterBox.Right()-rIndicatorSize.Width()/2;
const Rectangle aPreviewBox (mpPageObjectLayouter->GetBoundingBox( aPosition.maLocation.Y() = aPreviewBox.Center().Y();
aOuterBox.TopLeft(), }
PageObjectLayouter::Preview, else
PageObjectLayouter::WindowCoordinateSystem)); {
return Point(aOuterBox.Right()-rIndicatorSize.Width()/2, aPreviewBox.Center().Y()); // Place indicator at the end of the row in the available
// space at its right end.
aPosition.maLocation.X() = aOuterBox.Right()+rIndicatorSize.Width()/2;
aPosition.maLocation.Y() = aPreviewBox.Center().Y();
}
} }
else else
{ {
// Place indicator between two columns. // Place indicator between two columns.
const Rectangle aBox1 (mpPageObjectLayouter->GetBoundingBox( const Rectangle aBox1 (mpPageObjectLayouter->GetBoundingBox(
GetPageObjectBox(nIndex-1).TopLeft(), GetPageObjectBox(aPosition.mnIndex-1).TopLeft(),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
const Rectangle aBox2 (mpPageObjectLayouter->GetBoundingBox( const Rectangle aBox2 (mpPageObjectLayouter->GetBoundingBox(
GetPageObjectBox(nIndex).TopLeft(), GetPageObjectBox(aPosition.mnIndex).TopLeft(),
PageObjectLayouter::Preview, PageObjectLayouter::Preview,
PageObjectLayouter::WindowCoordinateSystem)); PageObjectLayouter::WindowCoordinateSystem));
return (aBox1.Center() + aBox2.Center() + Point(1,1)) / 2; aPosition.maLocation = (aBox1.Center() + aBox2.Center() + Point(1,1)) / 2;
} }
} }
return aPosition;
} }
@@ -581,31 +655,6 @@ sal_Int32 Layouter::GetIndexAtPoint (
sal_Int32 Layouter::GetVerticalInsertionIndex (const Point& rPosition) const
{
OSL_ASSERT(mnColumnCount == 1);
const sal_Int32 nY = rPosition.Y() - mnTopBorder + maPageObjectSize.Height()/2;
const sal_Int32 nRowHeight (maPageObjectSize.Height() + mnVerticalGap);
return nY / nRowHeight;
}
Pair Layouter::GetGridInsertionIndices (const Point& rPosition) const
{
const sal_Int32 nRow = GetRowAtPosition (rPosition.Y(), true, GM_BOTH);
const sal_Int32 nX = rPosition.X() - mnLeftBorder + maPageObjectSize.Width()/2;
const sal_Int32 nRowWidth (maPageObjectSize.Width() + mnHorizontalGap);
return Pair(nRow, nX / nRowWidth);
}
bool Layouter::IsVertical (void) const bool Layouter::IsVertical (void) const
{ {
return mbIsVertical; return mbIsVertical;
@@ -753,4 +802,59 @@ sal_Int32 Layouter::ResolvePositionInGap (
//===== InsertPosition ========================================================
InsertPosition::InsertPosition (void)
: mnRow(-1),
mnColumn(-1),
mnIndex(-1),
maLocation(0,0),
mbIsAtRunStart(false),
mbIsAtRunEnd(false),
mbIsExtraSpaceNeeded(false)
{
}
InsertPosition& InsertPosition::operator= (const InsertPosition& rInsertPosition)
{
if (this != &rInsertPosition)
{
mnRow = rInsertPosition.mnRow;
mnColumn = rInsertPosition.mnColumn;
mnIndex = rInsertPosition.mnIndex;
maLocation = rInsertPosition.maLocation;
mbIsAtRunStart = rInsertPosition.mbIsAtRunStart;
mbIsAtRunEnd = rInsertPosition.mbIsAtRunEnd;
mbIsExtraSpaceNeeded = rInsertPosition.mbIsExtraSpaceNeeded;
}
return *this;
}
bool InsertPosition::operator== (const InsertPosition& rInsertPosition) const
{
// Do not compare the geometrical information (maLocation).
return mnRow==rInsertPosition.mnRow
&& mnColumn==rInsertPosition.mnColumn
&& mnIndex==rInsertPosition.mnIndex
&& mbIsAtRunStart==rInsertPosition.mbIsAtRunStart
&& mbIsAtRunEnd==rInsertPosition.mbIsAtRunEnd
&& mbIsExtraSpaceNeeded==rInsertPosition.mbIsExtraSpaceNeeded;
}
bool InsertPosition::operator!= (const InsertPosition& rInsertPosition) const
{
return !operator==(rInsertPosition);
}
} } } // end of namespace ::sd::slidesorter::namespace } } } // end of namespace ::sd::slidesorter::namespace

View File

@@ -287,14 +287,14 @@ void PageObjectPainter::PaintPreview (
if (rpDescriptor->GetVisualState().GetCurrentVisualState() if (rpDescriptor->GetVisualState().GetCurrentVisualState()
== model::VisualState::VS_Excluded) == model::VisualState::VS_Excluded)
{ {
rDevice.SetFillColor(COL_BLACK); rDevice.SetFillColor(COL_GRAY);
rDevice.SetLineColor(); rDevice.SetLineColor();
rDevice.DrawTransparent( rDevice.DrawTransparent(
::basegfx::B2DPolyPolygon(::basegfx::tools::createPolygonFromRect( ::basegfx::B2DPolyPolygon(::basegfx::tools::createPolygonFromRect(
::basegfx::B2DRectangle(aBox.Left(), aBox.Top(), aBox.Right()+1, aBox.Bottom()+1), ::basegfx::B2DRectangle(aBox.Left(), aBox.Top(), aBox.Right()+1, aBox.Bottom()+1),
0, 0,
0)), 0)),
0.5); 0.3);
} }
} }
@@ -506,11 +506,6 @@ Bitmap PageObjectPainter::CreateBackgroundBitmap(
Rectangle aFrameBox (aBox.Left()-1,aBox.Top()-1,aBox.Right()+1,aBox.Bottom()+1); Rectangle aFrameBox (aBox.Left()-1,aBox.Top()-1,aBox.Right()+1,aBox.Bottom()+1);
mpShadowPainter->PaintFrame(aBitmapDevice, aFrameBox); mpShadowPainter->PaintFrame(aBitmapDevice, aFrameBox);
// Clear the area where the preview will later be painted.
aBitmapDevice.SetFillColor(mpTheme->GetColor(Theme::PageBackground));
aBitmapDevice.SetLineColor(mpTheme->GetColor(Theme::PageBackground));
aBitmapDevice.DrawRect(aBox);
return aBitmapDevice.GetBitmap (Point(0,0),aSize); return aBitmapDevice.GetBitmap (Point(0,0),aSize);
} }

View File

@@ -1,718 +0,0 @@
/*************************************************************************
*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* Copyright 2008 by Sun Microsystems, Inc.
*
* OpenOffice.org - a multi-platform office productivity suite
*
* $RCSfile: SlsViewOverlay.cxx,v $
* $Revision: 1.16 $
*
* This file is part of OpenOffice.org.
*
* OpenOffice.org is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License version 3
* only, as published by the Free Software Foundation.
*
* OpenOffice.org is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License version 3 for more details
* (a copy is included in the LICENSE file that accompanied this code).
*
* You should have received a copy of the GNU Lesser General Public License
* version 3 along with OpenOffice.org. If not, see
* <http://www.openoffice.org/license.html>
* for a copy of the LGPLv3 License.
*
************************************************************************/
#include "precompiled_sd.hxx"
#include "view/SlsViewOverlay.hxx"
#include "SlideSorter.hxx"
#include "SlideSorterViewShell.hxx"
#include "SlsLayeredDevice.hxx"
#include "SlsFramePainter.hxx"
#include "model/SlideSorterModel.hxx"
#include "model/SlsPageDescriptor.hxx"
#include "model/SlsPageEnumeration.hxx"
#include "view/SlideSorterView.hxx"
#include "view/SlsLayouter.hxx"
#include "view/SlsTheme.hxx"
#include "cache/SlsPageCache.hxx"
#include "ViewShell.hxx"
#include "ViewShellBase.hxx"
#include "UpdateLockManager.hxx"
#include "Window.hxx"
#include "sdpage.hxx"
#include "sdresid.hxx"
#include <basegfx/range/b2drectangle.hxx>
#include <basegfx/range/b2drange.hxx>
#include <basegfx/range/b2irange.hxx>
#include <basegfx/matrix/b2dhommatrix.hxx>
#include <basegfx/polygon/b2dpolygontools.hxx>
#include <basegfx/polygon/b2dpolypolygontools.hxx>
#include <basegfx/matrix/b2dhommatrixtools.hxx>
#include <basegfx/tools/canvastools.hxx>
#include <svx/sdr/overlay/overlaymanager.hxx>
#include <svx/svdpagv.hxx>
#include <svx/sdrpagewindow.hxx>
#include <vcl/svapp.hxx>
#include <vcl/bmpacc.hxx>
#include <rtl/math.hxx>
#include <drawinglayer/primitive2d/polygonprimitive2d.hxx>
#include <drawinglayer/primitive2d/polypolygonprimitive2d.hxx>
using namespace ::sdr::overlay;
using namespace ::basegfx;
#define A2S(pString) (::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(pString)))
namespace {
#define Amber 0x007fff
static const double gnPreviewOffsetScale = 1.0 / 8.0;
Rectangle GrowRectangle (const Rectangle& rBox, const sal_Int32 nOffset)
{
return Rectangle (
rBox.Left() - nOffset,
rBox.Top() - nOffset,
rBox.Right() + nOffset,
rBox.Bottom() + nOffset);
}
Rectangle ConvertRectangle (const B2DRectangle& rBox)
{
const B2IRange rIntegerBox (unotools::b2ISurroundingRangeFromB2DRange(rBox));
return Rectangle(
rIntegerBox.getMinX(),
rIntegerBox.getMinY(),
rIntegerBox.getMaxX(),
rIntegerBox.getMaxY());
}
sal_Int32 RoundToInt (const double nValue) { return sal_Int32(::rtl::math::round(nValue)); }
} // end of anonymous namespace
namespace sd { namespace slidesorter { namespace view {
//===== ViewOverlay =========================================================
ViewOverlay::ViewOverlay (
SlideSorter& rSlideSorter,
const ::boost::shared_ptr<LayeredDevice>& rpLayeredDevice)
: mrSlideSorter(rSlideSorter),
mpLayeredDevice(rpLayeredDevice),
mpSelectionRectangleOverlay(new SelectionRectangleOverlay(*this, 3)),
mpInsertionIndicatorOverlay(new InsertionIndicatorOverlay(*this, 4)),
mpSubstitutionOverlay(new SubstitutionOverlay(*this, 3))
{
}
ViewOverlay::~ViewOverlay (void)
{
}
::boost::shared_ptr<SelectionRectangleOverlay> ViewOverlay::GetSelectionRectangleOverlay (void)
{
return mpSelectionRectangleOverlay;
}
::boost::shared_ptr<InsertionIndicatorOverlay> ViewOverlay::GetInsertionIndicatorOverlay (void)
{
return mpInsertionIndicatorOverlay;
}
::boost::shared_ptr<SubstitutionOverlay> ViewOverlay::GetSubstitutionOverlay (void)
{
return mpSubstitutionOverlay;
}
SlideSorter& ViewOverlay::GetSlideSorter (void) const
{
return mrSlideSorter;
}
::boost::shared_ptr<LayeredDevice> ViewOverlay::GetLayeredDevice (void) const
{
return mpLayeredDevice;
}
//===== OverlayBase::Invalidator ==============================================
class OverlayBase::Invalidator
{
public:
Invalidator (OverlayBase& rOverlayObject)
: mrOverlayObject(rOverlayObject),
maOldBoundingBox(rOverlayObject.IsVisible()
? rOverlayObject.GetBoundingBox()
: Rectangle())
{
}
~Invalidator (void)
{
if ( ! maOldBoundingBox.IsEmpty())
mrOverlayObject.Invalidate(maOldBoundingBox);
if (mrOverlayObject.IsVisible())
mrOverlayObject.Invalidate(mrOverlayObject.GetBoundingBox());
}
private:
OverlayBase& mrOverlayObject;
const Rectangle maOldBoundingBox;
};
//===== OverlayBase =========================================================
OverlayBase::OverlayBase (
ViewOverlay& rViewOverlay,
const sal_Int32 nLayerIndex)
: mrViewOverlay(rViewOverlay),
mbIsVisible(false),
mnLayerIndex(nLayerIndex)
{
}
OverlayBase::~OverlayBase (void)
{
}
bool OverlayBase::IsVisible (void) const
{
return mbIsVisible;
}
void OverlayBase::SetIsVisible (const bool bIsVisible)
{
if (mbIsVisible != bIsVisible)
{
Invalidator aInvalidator (*this);
mbIsVisible = bIsVisible;
::boost::shared_ptr<LayeredDevice> pDevice (mrViewOverlay.GetLayeredDevice());
if (pDevice)
if (mbIsVisible)
{
pDevice->RegisterPainter(shared_from_this(), GetLayerIndex());
Invalidate(GetBoundingBox());
}
else
{
Invalidate(GetBoundingBox());
pDevice->RemovePainter(shared_from_this(), GetLayerIndex());
}
}
}
void OverlayBase::SetLayerInvalidator (const SharedILayerInvalidator& rpInvalidator)
{
if ( ! rpInvalidator)
Invalidate(GetBoundingBox());
mpLayerInvalidator = rpInvalidator;
if (mbIsVisible)
Invalidate(GetBoundingBox());
}
void OverlayBase::Invalidate (const Rectangle& rInvalidationBox)
{
if (mpLayerInvalidator)
mpLayerInvalidator->Invalidate(rInvalidationBox);
}
sal_Int32 OverlayBase::GetLayerIndex (void) const
{
return mnLayerIndex;
}
//===== SubstitutionOverlay =================================================
const sal_Int32 SubstitutionOverlay::mnCenterTransparency (60);
const sal_Int32 SubstitutionOverlay::mnSideTransparency (85);
const sal_Int32 SubstitutionOverlay::mnCornerTransparency (95);
SubstitutionOverlay::SubstitutionOverlay (
ViewOverlay& rViewOverlay,
const sal_Int32 nLayerIndex)
: OverlayBase(rViewOverlay, nLayerIndex),
maPosition(0,0)
{
}
SubstitutionOverlay::~SubstitutionOverlay (void)
{
}
void SubstitutionOverlay::Clear (void)
{
SetIsVisible(false);
}
void SubstitutionOverlay::SetAnchor (const Point& rAnchor)
{
(void)rAnchor;
}
void SubstitutionOverlay::Move (const Point& rOffset)
{
(void)rOffset;
}
void SubstitutionOverlay::SetPosition (const Point& rPosition)
{
(void)rPosition;
}
Point SubstitutionOverlay::GetPosition (void) const
{
return Point(0,0);
}
void SubstitutionOverlay::Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea)
{
(void)rDevice;
(void)rRepaintArea;
}
Rectangle SubstitutionOverlay::GetBoundingBox (void) const
{
return Rectangle();
}
//===== SelectionRectangleOverlay ===========================================
SelectionRectangleOverlay::SelectionRectangleOverlay (
ViewOverlay& rViewOverlay,
const sal_Int32 nLayerIndex)
: OverlayBase (rViewOverlay, nLayerIndex),
maAnchor(0,0),
maSecondCorner(0,0)
{
}
Rectangle SelectionRectangleOverlay::GetSelectionRectangle (void)
{
return Rectangle(maAnchor, maSecondCorner);
}
void SelectionRectangleOverlay::Start (const Point& rAnchor)
{
SetIsVisible(false);
maAnchor = rAnchor;
maSecondCorner = rAnchor;
}
void SelectionRectangleOverlay::Update (const Point& rSecondCorner)
{
Invalidator aInvalidator (*this);
maSecondCorner = rSecondCorner;
SetIsVisible(true);
}
void SelectionRectangleOverlay::Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea)
{
if ( ! IsVisible())
return;
rDevice.SetFillColor(Color(Amber));
rDevice.SetLineColor(Color(Amber));
const Rectangle aBox (
::std::min(maAnchor.X(), maSecondCorner.X()),
::std::min(maAnchor.Y(), maSecondCorner.Y()),
::std::max(maAnchor.X(), maSecondCorner.X()),
::std::max(maAnchor.Y(), maSecondCorner.Y()));
if (rRepaintArea.IsOver(aBox))
rDevice.DrawTransparent(
::basegfx::B2DPolyPolygon(
::basegfx::tools::createPolygonFromRect(
::basegfx::B2DRectangle(aBox.Left(), aBox.Top(), aBox.Right(), aBox.Bottom()),
5.0/aBox.GetWidth(),
5.0/aBox.GetHeight())),
0.5);
}
Rectangle SelectionRectangleOverlay::GetBoundingBox (void) const
{
return GrowRectangle(Rectangle(
::std::min(maAnchor.X(), maSecondCorner.X()),
::std::min(maAnchor.Y(), maSecondCorner.Y()),
::std::max(maAnchor.X(), maSecondCorner.X()),
::std::max(maAnchor.Y(), maSecondCorner.Y())),
+1);
}
//===== InsertionIndicatorOverlay ===========================================
const static sal_Int32 gnShadowBorder = 3;
InsertionIndicatorOverlay::InsertionIndicatorOverlay (
ViewOverlay& rViewOverlay,
const sal_Int32 nLayerIndex)
: OverlayBase (rViewOverlay, nLayerIndex),
maLocation(),
maIcon(),
mpShadowPainter(new FramePainter(
rViewOverlay.GetSlideSorter().GetTheme()->GetIcon(Theme::RawInsertShadow)))
{
}
void InsertionIndicatorOverlay::Create (model::PageEnumeration& rSelection)
{
view::Layouter& rLayouter (mrViewOverlay.GetSlideSorter().GetView().GetLayouter());
::boost::shared_ptr<view::PageObjectLayouter> pPageObjectLayouter (
rLayouter.GetPageObjectLayouter());
::boost::shared_ptr<view::Theme> pTheme (mrViewOverlay.GetSlideSorter().GetTheme());
const Size aOriginalPreviewSize (pPageObjectLayouter->GetPreviewSize());
const double nPreviewScale (0.5);
const Size aPreviewSize (
RoundToInt(aOriginalPreviewSize.Width()*nPreviewScale),
RoundToInt(aOriginalPreviewSize.Height()*nPreviewScale));
const sal_Int32 nOffset (
RoundToInt(Min(aPreviewSize.Width(),aPreviewSize.Height()) * gnPreviewOffsetScale));
::std::vector<model::SharedPageDescriptor> aDescriptors;
SelectRepresentatives(rSelection, aDescriptors);
// Determine size and offset depending on the number of previews.
sal_Int32 nCount (aDescriptors.size());
if (nCount > 0)
--nCount;
Size aIconSize(
aPreviewSize.Width() + 2 * gnShadowBorder + nCount*nOffset,
aPreviewSize.Height() + 2 * gnShadowBorder + nCount*nOffset);
maIconOffset = Point(gnShadowBorder, gnShadowBorder);
// Create virtual devices for bitmap and mask whose bitmaps later be
// combined to form the BitmapEx of the icon.
VirtualDevice aContent (
*mrViewOverlay.GetSlideSorter().GetContentWindow(),
0,
0);
aContent.SetOutputSizePixel(aIconSize);
aContent.SetFillColor();
aContent.SetLineColor(pTheme->GetColor(Theme::PreviewBorder));
const Point aOffset = PaintRepresentatives(aContent, aPreviewSize, nOffset, aDescriptors);
PaintPageCount(aContent, rSelection, aPreviewSize, aOffset);
maIcon = aContent.GetBitmapEx(Point(0,0), aIconSize);
}
void InsertionIndicatorOverlay::SelectRepresentatives (
model::PageEnumeration& rSelection,
::std::vector<model::SharedPageDescriptor>& rDescriptors) const
{
sal_Int32 nCount (0);
while (rSelection.HasMoreElements())
{
if (nCount++ >= 3)
break;
rDescriptors.push_back(rSelection.GetNextElement());
}
}
Point InsertionIndicatorOverlay::PaintRepresentatives (
OutputDevice& rContent,
const Size aPreviewSize,
const sal_Int32 nOffset,
const ::std::vector<model::SharedPageDescriptor>& rDescriptors) const
{
const Point aOffset (0,rDescriptors.size()==1 ? -nOffset : 0);
// Paint the pages.
Point aPageOffset (0,0);
double nTransparency (0);
for (sal_Int32 nIndex=2; nIndex>=0; --nIndex)
{
if (rDescriptors.size() <= nIndex)
continue;
switch(nIndex)
{
case 0 :
aPageOffset = Point(0, nOffset);
nTransparency = 0.85;
break;
case 1:
aPageOffset = Point(nOffset, 0);
nTransparency = 0.75;
break;
case 2:
aPageOffset = Point(2*nOffset, 2*nOffset);
nTransparency = 0.65;
break;
}
aPageOffset += aOffset;
aPageOffset.X() += gnShadowBorder;
aPageOffset.Y() += gnShadowBorder;
::boost::shared_ptr<cache::PageCache> pPreviewCache (
mrViewOverlay.GetSlideSorter().GetView().GetPreviewCache());
BitmapEx aPreview (pPreviewCache->GetPreviewBitmap(rDescriptors[nIndex]->GetPage()));
aPreview.Scale(aPreviewSize, BMP_SCALE_INTERPOLATE);
rContent.DrawBitmapEx(aPageOffset, aPreview);
// Tone down the bitmap. The further back the darker it becomes.
Rectangle aBox (
aPageOffset.X(),
aPageOffset.Y(),
aPageOffset.X()+aPreviewSize.Width()-1,
aPageOffset.Y()+aPreviewSize.Height()-1);
rContent.SetFillColor(COL_BLACK);
rContent.SetLineColor();
rContent.DrawTransparent(
::basegfx::B2DPolyPolygon(::basegfx::tools::createPolygonFromRect(
::basegfx::B2DRectangle(aBox.Left(), aBox.Top(), aBox.Right()+1, aBox.Bottom()+1),
0,
0)),
nTransparency);
// Draw border around preview.
Rectangle aBorderBox (GrowRectangle(aBox, 1));
rContent.SetLineColor(COL_GRAY);
rContent.SetFillColor();
rContent.DrawRect(aBorderBox);
// Draw shadow around preview.
mpShadowPainter->PaintFrame(rContent, aBorderBox);
}
return aPageOffset;
}
void InsertionIndicatorOverlay::PaintPageCount (
OutputDevice& rDevice,
model::PageEnumeration& rSelection,
const Size aPreviewSize,
const Point aFirstPageOffset) const
{
// Paint the number of slides.
::boost::shared_ptr<view::Theme> pTheme (mrViewOverlay.GetSlideSorter().GetTheme());
::boost::shared_ptr<Font> pFont(Theme::GetFont(Theme::PageCountFont, rDevice));
if (pFont)
{
// Count the elements in the selection and create a string for the
// result.
sal_Int32 nSelectionCount (0);
rSelection.Rewind();
while (rSelection.HasMoreElements())
{
rSelection.GetNextElement();
++nSelectionCount;
}
::rtl::OUString sNumber (::rtl::OUString::valueOf(nSelectionCount));
// Determine the size of the (painted) text and create a bounding
// box that centers the text on the first preview.
rDevice.SetFont(*pFont);
Rectangle aTextBox;
rDevice.GetTextBoundRect(aTextBox, sNumber);
Point aTextOffset (aTextBox.TopLeft());
Size aTextSize (aTextBox.GetSize());
// Place text inside the first page preview.
Point aTextLocation(aFirstPageOffset);
// Center the text.
aTextLocation += Point(
(aPreviewSize.Width()-aTextBox.GetWidth())/2,
(aPreviewSize.Height()-aTextBox.GetHeight())/2);
aTextBox = Rectangle(aTextLocation, aTextSize);
// Paint background, border and text.
static const sal_Int32 nBorder = 5;
rDevice.SetFillColor(pTheme->GetColor(Theme::Selection));
rDevice.SetLineColor(pTheme->GetColor(Theme::Selection));
rDevice.DrawRect(GrowRectangle(aTextBox, nBorder));
rDevice.SetFillColor();
rDevice.SetLineColor(COL_WHITE);
rDevice.DrawRect(GrowRectangle(aTextBox, nBorder-1));
rDevice.SetTextColor(COL_WHITE);
rDevice.DrawText(aTextBox.TopLeft()-aTextOffset, sNumber);
}
}
void InsertionIndicatorOverlay::Create (void)
{
}
void InsertionIndicatorOverlay::SetLocation (const Point& rLocation)
{
const Point aTopLeft (
rLocation - Point(
maIcon.GetSizePixel().Width()/2,
maIcon.GetSizePixel().Height()/2));
if (maLocation != aTopLeft)
{
Invalidator aInvalidator (*this);
maLocation = aTopLeft;
}
}
void InsertionIndicatorOverlay::Paint (
OutputDevice& rDevice,
const Rectangle& rRepaintArea)
{
(void)rRepaintArea;
if ( ! IsVisible())
return;
rDevice.DrawImage(maLocation, maIcon);
}
Rectangle InsertionIndicatorOverlay::GetBoundingBox (void) const
{
return Rectangle(maLocation, maIcon.GetSizePixel());
}
Size InsertionIndicatorOverlay::GetSize (void) const
{
return Size(
maIcon.GetSizePixel().Width() + 10,
maIcon.GetSizePixel().Height() + 10);
}
} } } // end of namespace ::sd::slidesorter::view

View File

@@ -57,13 +57,13 @@ SLOFILES = \
$(SLO)$/SlsFontProvider.obj \ $(SLO)$/SlsFontProvider.obj \
$(SLO)$/SlsFramePainter.obj \ $(SLO)$/SlsFramePainter.obj \
$(SLO)$/SlsInsertAnimator.obj \ $(SLO)$/SlsInsertAnimator.obj \
$(SLO)$/SlsInsertionIndicatorOverlay.obj\
$(SLO)$/SlsLayeredDevice.obj \ $(SLO)$/SlsLayeredDevice.obj \
$(SLO)$/SlsLayouter.obj \ $(SLO)$/SlsLayouter.obj \
$(SLO)$/SlsPageObjectLayouter.obj \ $(SLO)$/SlsPageObjectLayouter.obj \
$(SLO)$/SlsPageObjectPainter.obj \ $(SLO)$/SlsPageObjectPainter.obj \
$(SLO)$/SlsTheme.obj \ $(SLO)$/SlsTheme.obj \
$(SLO)$/SlsViewCacheContext.obj \ $(SLO)$/SlsViewCacheContext.obj
$(SLO)$/SlsViewOverlay.obj
# --- Tagets ------------------------------------------------------- # --- Tagets -------------------------------------------------------

View File

@@ -90,7 +90,7 @@
#include "TestPanel.hxx" #include "TestPanel.hxx"
#endif #endif
#define SHOW_COLOR_MENU //#define SHOW_COLOR_MENU
#ifdef SHOW_COLOR_MENU #ifdef SHOW_COLOR_MENU
#include "TestMenu.hxx" #include "TestMenu.hxx"
#endif #endif