diff options
Diffstat (limited to 'sd/source/ui/slidesorter/inc/view')
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlideSorterView.hxx | 225 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsILayerPainter.hxx | 53 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsInsertAnimator.hxx | 59 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsInsertionIndicatorOverlay.hxx | 101 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsLayouter.hxx | 237 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsPageObjectLayouter.hxx | 144 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsPageObjectPainter.hxx | 119 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsTheme.hxx | 135 | ||||
-rw-r--r-- | sd/source/ui/slidesorter/inc/view/SlsToolTip.hxx | 75 |
9 files changed, 1148 insertions, 0 deletions
diff --git a/sd/source/ui/slidesorter/inc/view/SlideSorterView.hxx b/sd/source/ui/slidesorter/inc/view/SlideSorterView.hxx new file mode 100644 index 000000000..0f3493ab3 --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlideSorterView.hxx @@ -0,0 +1,225 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <model/SlsPageDescriptor.hxx> +#include <model/SlsSharedPageDescriptor.hxx> +#include <view/SlsLayouter.hxx> +#include <view/SlsILayerPainter.hxx> +#include <o3tl/deleter.hxx> + +#include <View.hxx> +#include <tools/gen.hxx> +#include <vcl/region.hxx> +#include <memory> + +namespace sd::slidesorter::cache { class PageCache; } +namespace sd::slidesorter::model { class SlideSorterModel; } +namespace sd { class Window; } +namespace sd::slidesorter { class SlideSorter; } +namespace sd::slidesorter::view { + +class LayeredDevice; +class PageObjectPainter; +class ToolTip; + +class SlideSorterView final + : public sd::View +{ +public: + + /** Create a new view for the slide sorter. + @param rViewShell + This reference is simply passed to the base class and not used + by this class. + + */ + explicit SlideSorterView (SlideSorter& rSlideSorter); + void Init(); + + virtual ~SlideSorterView() override; + void Dispose(); + + SlideSorterView(const SlideSorterView&) = delete; + SlideSorterView& operator=(const SlideSorterView&) = delete; + + /** Set the general way of layouting the page objects. Note that this + method does not trigger any repaints or layouts. + */ + bool SetOrientation (const Layouter::Orientation eOrientation); + Layouter::Orientation GetOrientation() const { return meOrientation;} + + void RequestRepaint(); + void RequestRepaint (const model::SharedPageDescriptor& rDescriptor); + void RequestRepaint (const ::tools::Rectangle& rRepaintBox); + void RequestRepaint (const vcl::Region& rRepaintRegion); + + ::tools::Rectangle GetModelArea() const; + + /** Return the index of the page that is rendered at the given position. + @param rPosition + The position is expected to be in pixel coordinates. + @return + The returned index is -1 when there is no page object at the + given position. + */ + sal_Int32 GetPageIndexAtPoint (const Point& rPosition) const; + + view::Layouter& GetLayouter(); + + virtual void ModelHasChanged() override; + + /** This method is typically called before a model change takes place. + All references to model data are released. PostModelChange() has to + be called to complete the handling of the model change. When the + calls to Pre- and PostModelChange() are very close to each other you + may call HandleModelChange() instead. + */ + void PreModelChange(); + + /** This method is typically called after a model change took place. + References to model data are re-allocated. Call this method only + after PreModelChange() has been called. + */ + void PostModelChange(); + + /** This method is a convenience function that simply calls + PreModelChange() and then PostModelChange(). + */ + void HandleModelChange(); + + void HandleDrawModeChange(); + + void Resize(); + virtual void CompleteRedraw ( + OutputDevice* pDevice, + const vcl::Region& rPaintArea, + sdr::contact::ViewObjectContactRedirector* pRedirector = nullptr) override; + void Paint (OutputDevice& rDevice, const ::tools::Rectangle& rRepaintArea); + + virtual void ConfigurationChanged ( + utl::ConfigurationBroadcaster* pBroadcaster, + ConfigurationHints nHint) override; + + void HandleDataChangeEvent(); + + void Layout(); + /** This tells the view that it has to re-determine the visibility of + the page objects before painting them the next time. + */ + void InvalidatePageObjectVisibilities(); + + std::shared_ptr<cache::PageCache> const & GetPreviewCache(); + + /** Return the range of currently visible page objects including the + first and last one in that range. + @return + The returned pair of page object indices is empty when the + second index is lower than the first. + */ + Range const & GetVisiblePageRange(); + + /** Add a shape to the page. Typically used from inside + PostModelChange(). + */ + // void AddSdrObject (SdrObject& rObject); + + /** Add a listener that is called when the set of visible slides. + @param rListener + When this method is called multiple times for the same listener + the second and all following calls are ignored. Each listener + is added only once. + */ + void AddVisibilityChangeListener (const Link<LinkParamNone*,void>& rListener); + + /** Remove a listener that is called when the set of visible slides changes. + @param rListener + It is safe to pass a listener that was not added or has been + removed previously. Such calls are ignored. + */ + void RemoveVisibilityChangeListener (const Link<LinkParamNone*,void>& rListener); + + /** The page under the mouse is not highlighted in some contexts. Call + this method on context changes. + */ + void UpdatePageUnderMouse (); + void UpdatePageUnderMouse (const Point& rMousePosition); + void SetPageUnderMouse (const model::SharedPageDescriptor& rpDescriptor); + + bool SetState ( + const model::SharedPageDescriptor& rpDescriptor, + const model::PageDescriptor::State eState, + const bool bStateValue); + + void UpdateOrientation(); + + std::shared_ptr<PageObjectPainter> const & GetPageObjectPainter(); + const std::shared_ptr<LayeredDevice>& GetLayeredDevice() const { return mpLayeredDevice;} + + class DrawLock + { + public: + DrawLock (SlideSorter const & rSlideSorter); + ~DrawLock(); + /** When the DrawLock is disposed then it will not request a repaint + on destruction. + */ + void Dispose(); + private: + view::SlideSorterView& mrView; + VclPtr<sd::Window> mpWindow; + }; + + ToolTip& GetToolTip() const; + + virtual void DragFinished (sal_Int8 nDropAction) override; + +private: + SlideSorter& mrSlideSorter; + model::SlideSorterModel& mrModel; + bool mbIsDisposed; + ::std::unique_ptr<Layouter> mpLayouter; + bool mbPageObjectVisibilitiesValid; + std::shared_ptr<cache::PageCache> mpPreviewCache; + std::shared_ptr<LayeredDevice> mpLayeredDevice; + Range maVisiblePageRange; + Size maPreviewSize; + bool mbPreciousFlagUpdatePending; + Layouter::Orientation meOrientation; + model::SharedPageDescriptor mpPageUnderMouse; + std::shared_ptr<PageObjectPainter> mpPageObjectPainter; + vcl::Region maRedrawRegion; + SharedILayerPainter mpBackgroundPainter; + std::unique_ptr<ToolTip, o3tl::default_delete<ToolTip>> mpToolTip; + bool mbIsRearrangePending; + ::std::vector<Link<LinkParamNone*,void>> maVisibilityChangeListeners; + + /** Determine the visibility of all page objects. + */ + void DeterminePageObjectVisibilities(); + + void UpdatePreciousFlags(); + void RequestRearrange(); + void Rearrange(); +}; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsILayerPainter.hxx b/sd/source/ui/slidesorter/inc/view/SlsILayerPainter.hxx new file mode 100644 index 000000000..57b90af0a --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsILayerPainter.hxx @@ -0,0 +1,53 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <memory> + +class OutputDevice; +namespace tools { class Rectangle; } + +namespace sd::slidesorter::view { + +class ILayerInvalidator +{ +public: + virtual ~ILayerInvalidator() {} + + virtual void Invalidate (const ::tools::Rectangle& rInvalidationBox) = 0; +}; +typedef std::shared_ptr<ILayerInvalidator> SharedILayerInvalidator; + +class ILayerPainter +{ +public: + virtual ~ILayerPainter() {} + + virtual void SetLayerInvalidator ( + const SharedILayerInvalidator& rpInvalidator) = 0; + virtual void Paint ( + OutputDevice& rDevice, + const ::tools::Rectangle& rRepaintArea) = 0; +}; +typedef std::shared_ptr<ILayerPainter> SharedILayerPainter; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsInsertAnimator.hxx b/sd/source/ui/slidesorter/inc/view/SlsInsertAnimator.hxx new file mode 100644 index 000000000..c74d06cb9 --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsInsertAnimator.hxx @@ -0,0 +1,59 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <controller/SlsAnimator.hxx> +#include <memory> + +namespace sd::slidesorter::view +{ +class InsertPosition; + +/** Animate the positions of page objects to make room at the insert + position while a move or copy operation takes place. +*/ +class InsertAnimator +{ +public: + explicit InsertAnimator(SlideSorter& rSlideSorter); + InsertAnimator(const InsertAnimator&) = delete; + InsertAnimator& operator=(const InsertAnimator&) = delete; + + /** Set the position at which we have to make room for the display of an + icon. + */ + void SetInsertPosition(const InsertPosition& rInsertPosition); + + /** Restore the normal position of all page objects. + @param eMode + This flag controls whether to start an animation that ends in the + normal positions of all slides (AM_Animated) or to restore the + normal positions immediately (AM_Immediate). + */ + void Reset(const controller::Animator::AnimationMode eMode); + +private: + class Implementation; + std::shared_ptr<Implementation> mpImplementation; +}; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsInsertionIndicatorOverlay.hxx b/sd/source/ui/slidesorter/inc/view/SlsInsertionIndicatorOverlay.hxx new file mode 100644 index 000000000..3f4cc2218 --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsInsertionIndicatorOverlay.hxx @@ -0,0 +1,101 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <view/SlsILayerPainter.hxx> +#include <controller/SlsTransferableData.hxx> + +#include <tools/gen.hxx> +#include <vcl/bitmapex.hxx> +#include <memory> +#include <vector> + +class OutputDevice; +class SdTransferable; + +namespace sd::slidesorter { class SlideSorter; } + +namespace sd::slidesorter::view { + +class FramePainter; + +/** The insertion indicator is painted as a vertical or horizontal bar + in the space between slides. +*/ +class InsertionIndicatorOverlay final + : public ILayerPainter, + public std::enable_shared_from_this<InsertionIndicatorOverlay> +{ +public: + InsertionIndicatorOverlay (SlideSorter& rSlideSorter); + virtual ~InsertionIndicatorOverlay() override; + + virtual void SetLayerInvalidator (const SharedILayerInvalidator& rpInvalidator) override; + + void Create (const SdTransferable* 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() const; + + virtual void Paint ( + OutputDevice& rDevice, + const ::tools::Rectangle& rRepaintArea) override; + + bool IsVisible() const { return mbIsVisible;} + void Hide(); + void Show(); + + ::tools::Rectangle GetBoundingBox() const; + +private: + SlideSorter& mrSlideSorter; + bool mbIsVisible; + SharedILayerInvalidator mpLayerInvalidator; + // Center of the insertion indicator. + Point maLocation; + BitmapEx maIcon; + std::unique_ptr<FramePainter> mpShadowPainter; + + Point PaintRepresentatives ( + OutputDevice& rContent, + const Size& rPreviewSize, + const sal_Int32 nOffset, + const ::std::vector<controller::TransferableData::Representative>& rPages) const; + void PaintPageCount ( + OutputDevice& rDevice, + const sal_Int32 nSelectionCount, + const Size& rPreviewSize, + const Point& rFirstPageOffset) 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<controller::TransferableData::Representative>& rPages, + const sal_Int32 nSelectionCount); +}; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsLayouter.hxx b/sd/source/ui/slidesorter/inc/view/SlsLayouter.hxx new file mode 100644 index 000000000..b91ae83c5 --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsLayouter.hxx @@ -0,0 +1,237 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <vcl/vclptr.hxx> +#include <tools/gen.hxx> +#include <sal/types.h> +#include <memory> + +namespace sd { class Window; } +namespace sd::slidesorter::model { class SlideSorterModel; } +namespace sd::slidesorter::view { class PageObjectLayouter; } +namespace sd::slidesorter::view { class Theme; } + +namespace sd::slidesorter::view { + +class InsertPosition; + +/** Calculate the size and position of page objects displayed by a slide + sorter. The layouter takes into account various input values: + 1.) Size of the window in which the slide sorter is displayed. + 2.) Desired and minimal and maximal widths of page objects. + 3.) Minimal and maximal number of columns. + 4.) Vertical and horizontal gaps between objects in adjacent columns. + 5.) Borders around every page object. + 6.) Vertical and horizontal borders between enclosing page and outer + page objects. + From these, it calculates various output values: + 1.) The width of page objects. + 2.) The number of columns. + 3.) The size of the enclosing page. + + <p>Sizes and lengths are all in pixel except where explicitly stated + otherwise.</p> + + <p>The GetIndex... methods may return indices that are larger than or + equal to (zero based) the number of pages. This is so because the + number of pages is not known to the class instances. Indices are + calculated with reference to the general grid layout of page + objects.</p> +*/ +class Layouter +{ +public: + enum Orientation { HORIZONTAL, VERTICAL, GRID }; + + Layouter ( + sd::Window *rpWindow, + const std::shared_ptr<Theme>& rpTheme); + ~Layouter(); + + std::shared_ptr<PageObjectLayouter> const & GetPageObjectLayouter() const; + /** Set the interval of valid column counts. When nMinimalColumnCount + <= nMaximalColumnCount is not fulfilled then the call is ignored. + @param nMinimalColumnCount + The default value is 1. The question whether higher values make + any sense is left to the caller. + @param nMaximalColumnCount + The default value is 5. + */ + void SetColumnCount (sal_Int32 nMinimalColumnCount, + sal_Int32 nMaximalColumnCount); + + /** Central method of this class. It takes the input values and + calculates the output values. Both given sizes must not be 0 in any + dimension or the call is ignored. + @param eOrientation + This defines the generally layout and specifies whether there may + be more than one row or more than one column. + @param rWindowSize + The size of the window in pixels that the slide sorter is + displayed in. This can differ from the size of mpWindow during + detection of whether or not the scroll bars should be visible. + @param rPreviewModelSize + Size of each page in model coordinates. + @param rpWindow + The map mode of this window is adapted to the new layout of the + page objects. + @return + The return value indicates whether the Get... methods can be + used to obtain valid values (<TRUE/>). + */ + bool Rearrange ( + const Orientation eOrientation, + const Size& rWindowSize, + const Size& rPreviewModelSize, + const sal_uInt32 nPageCount); + + /** Return the number of columns. + */ + sal_Int32 GetColumnCount() const; + + sal_Int32 GetIndex (const sal_Int32 nRow, const sal_Int32 nColumn) const; + + Size const & GetPageObjectSize() const; + + /** Return the bounding box in window coordinates of the nIndex-th page + object. + */ + ::tools::Rectangle GetPageObjectBox ( + const sal_Int32 nIndex, + const bool bIncludeBorderAndGap) const; + + /** Return the bounding box in model coordinates of the page that + contains the given amount of page objects. + */ + ::tools::Rectangle GetTotalBoundingBox() const; + + /** Return the index of the first fully or partially visible page + object. This takes into account only the vertical dimension. + @return + The second index may be larger than the number of existing + page objects. + */ + Range GetRangeOfVisiblePageObjects (const ::tools::Rectangle& rVisibleArea) const; + + /** Return the index of the page object that is rendered at the given + point. + @param rPosition + The position is expected to be in model coordinates relative to + the page origin. + @param bIncludePageBorders + When <TRUE/> then include the page borders into the calculation, + i.e. when a point lies in the border of a page object but not on + the actual page area the index of that page is returned; + otherwise -1 would be returned to indicate that no page object + has been hit. + @param bClampToValidRange + When <TRUE/> then values outside the valid range [0,mnPageCount) + are mapped to 0 (when smaller than 0) or mnPageCount-1 when + equal to or larger than mnPageCount. + When <FALSE/> then -1 is returned for values outside the valid range. + @return + The returned index may be larger than the number of existing + page objects. + */ + sal_Int32 GetIndexAtPoint ( + const Point& rModelPosition, + const bool bIncludePageBorders, + const bool bClampToValidRange = true) const; + + /** Return an object that describes the logical and visual properties of + where to do an insert operation when the user would release the + mouse button at the given position after a drag operation and of + where and how to display an insertion indicator. + @param rModelPosition + 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. + @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 or at the top or + bottom of a column. + @param rModel + The model is used to get access to the selection states of the + pages. This in turn is used to determine the visual bounding + boxes. + */ + InsertPosition GetInsertPosition ( + const Point& rModelPosition, + const Size& rIndicatorSize, + model::SlideSorterModel const & rModel) const; + + Range GetValidHorizontalSizeRange() const; + Range GetValidVerticalSizeRange() const; + + class Implementation; + +private: + std::unique_ptr<Implementation> mpImplementation; + VclPtr<sd::Window> mpWindow; +}; + +/** Collect all values concerning the logical and visual properties of the + insertion position that is used for drag-and-drop and copy-and-paste. +*/ +class InsertPosition +{ +public: + InsertPosition(); + bool operator== (const InsertPosition& rInsertPosition) const; + bool operator!= (const InsertPosition& rInsertPosition) const; + + void SetLogicalPosition ( + const sal_Int32 nRow, + const sal_Int32 nColumn, + const sal_Int32 nIndex, + const bool bIsAtRunStart, + const bool bIsAtRunEnd, + const bool bIsExtraSpaceNeeded); + void SetGeometricalPosition( + const Point& rLocation, + const Point& rLeadingOffset, + const Point& rTrailingOffset); + + sal_Int32 GetRow() const { return mnRow; } + sal_Int32 GetColumn() const { return mnColumn; } + sal_Int32 GetIndex() const { return mnIndex; } + const Point& GetLocation() const { return maLocation; } + const Point& GetLeadingOffset() const { return maLeadingOffset; } + const Point& GetTrailingOffset() const { return maTrailingOffset; } + bool IsAtRunStart() const { return mbIsAtRunStart; } + bool IsAtRunEnd() const { return mbIsAtRunEnd; } + bool IsExtraSpaceNeeded() const { return mbIsExtraSpaceNeeded; } + +private: + sal_Int32 mnRow; + sal_Int32 mnColumn; + sal_Int32 mnIndex; + bool mbIsAtRunStart : 1; + bool mbIsAtRunEnd : 1; + bool mbIsExtraSpaceNeeded : 1; + Point maLocation; + Point maLeadingOffset; + Point maTrailingOffset; +}; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsPageObjectLayouter.hxx b/sd/source/ui/slidesorter/inc/view/SlsPageObjectLayouter.hxx new file mode 100644 index 000000000..8bb77a988 --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsPageObjectLayouter.hxx @@ -0,0 +1,144 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <model/SlsSharedPageDescriptor.hxx> +#include <tools/gen.hxx> +#include <vcl/image.hxx> + +namespace vcl { class Font; } +namespace sd { class Window; } + +namespace sd::slidesorter::view { + +/** In contrast to the Layouter that places page objects in the view, the + PageObjectLayouter places the parts of individual page objects like page + number area, borders, preview. +*/ +class PageObjectLayouter +{ +public: + /** Create a new PageObjectLayouter object. + @param rPageObjectSize + In general either the width or the height will be 0 in order to + signal that this size component has to be calculated from the other. + This calculation will make the preview as large as possible. + @param nPageCount + The page count is used to determine how wide the page number + area has to be, how many digits to except for the largest page number. + */ + PageObjectLayouter( + const Size& rPageObjectWindowSize, + const Size& rPreviewModelSize, + sd::Window *pWindow, + const sal_Int32 nPageCount); + ~PageObjectLayouter(); + + enum class Part { + // The focus indicator is painted outside the actual page object. + FocusIndicator, + // This is the outer bounding box that includes the preview, page + // number, title. + PageObject, + // Bounding box of the actual preview. + Preview, + // Bounding box of the page number. + PageNumber, + // Indicator whether or not there is a slide transition associated + // with this slide. + TransitionEffectIndicator, + // Indicator whether or not there is a custom animation associated + // with this slide. + CustomAnimationEffectIndicator + }; + /** Two coordinate systems are supported. They differ only in + translation not in scale. Both relate to pixel values in the window. + A position in the model coordinate system does not change when the window content is + scrolled up or down. In the window coordinate system (relative + to the top left point of the window)scrolling leads to different values. + */ + enum CoordinateSystem { + WindowCoordinateSystem, + ModelCoordinateSystem + }; + + /** Return the bounding box of the page object or one of its graphical + parts. + @param rWindow + This device is used to translate between model and window + coordinates. + @param rpPageDescriptor + The page for which to calculate the bounding box. This may be + NULL. When it is NULL then a generic bounding box is calculated + for the location (0,0). + @param ePart + The part of the page object for which to return the bounding + box. + @param eCoordinateSystem + The bounding box can be returned in model and in pixel + (window) coordinates. + @param bIgnoreLocation + Return a position ignoring the slides' location, ie. as if + we were the first slide. + */ + ::tools::Rectangle GetBoundingBox ( + const model::SharedPageDescriptor& rpPageDescriptor, + const Part ePart, + const CoordinateSystem eCoordinateSystem, + bool bIgnoreLocation = false); + + /// the size of the embedded preview: position independent, in window coordinate system + Size GetPreviewSize(); + + /// the maximum size of each tile, also position independent, in window coordinate system + Size GetGridMaxSize(); + + const Image& GetTransitionEffectIcon() const { return maTransitionEffectIcon;} + const Image& GetCustomAnimationEffectIcon() const { return maCustomAnimationEffectIcon;} + +private: + ::tools::Rectangle GetBoundingBox ( + const Point& rPageObjectLocation, + const Part ePart, + const CoordinateSystem eCoordinateSystem); + +private: + VclPtr<sd::Window> mpWindow; + ::tools::Rectangle maFocusIndicatorBoundingBox; + ::tools::Rectangle maPageObjectBoundingBox; + ::tools::Rectangle maPageNumberAreaBoundingBox; + ::tools::Rectangle maPreviewBoundingBox; + ::tools::Rectangle maTransitionEffectBoundingBox; + ::tools::Rectangle maCustomAnimationEffectBoundingBox; + const Image maTransitionEffectIcon; + const Image maCustomAnimationEffectIcon; + const std::shared_ptr<vcl::Font> mpPageNumberFont; + + Size GetPageNumberAreaSize (const int nPageCount); + ::tools::Rectangle CalculatePreviewBoundingBox ( + Size& rPageObjectSize, + const Size& rPreviewModelSize, + const sal_Int32 nPageNumberAreaWidth, + const sal_Int32 nFocusIndicatorWidth); +}; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsPageObjectPainter.hxx b/sd/source/ui/slidesorter/inc/view/SlsPageObjectPainter.hxx new file mode 100644 index 000000000..747c09500 --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsPageObjectPainter.hxx @@ -0,0 +1,119 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <model/SlsSharedPageDescriptor.hxx> +#include <view/SlsTheme.hxx> +#include <memory> + +namespace sd::slidesorter::cache { class PageCache; } +namespace sd::slidesorter { class SlideSorter; } + +namespace sd::slidesorter::view { + +class Layouter; +class PageObjectLayouter; +class FramePainter; + +class PageObjectPainter +{ +public: + PageObjectPainter (const SlideSorter& rSlideSorter); + ~PageObjectPainter(); + + void PaintPageObject ( + OutputDevice& rDevice, + const model::SharedPageDescriptor& rpDescriptor); + + /** Called when the theme changes, either because it is replaced with + another or because the system colors have changed. So, even when + the given theme is the same object as the one already in use by this + painter everything that depends on the theme is updated. + */ + void SetTheme (const std::shared_ptr<view::Theme>& rpTheme); + + /** Return a preview bitmap for the given page descriptor. When the + page is excluded from the show then the preview is marked + accordingly. + @rpDescriptor + Defines the page for which to return the preview. + @pReferenceDevice + When not <NULL/> then this reference device is used to created a + compatible bitmap. + @return + The returned bitmap may have a different size then the preview area. + */ + BitmapEx GetPreviewBitmap ( + const model::SharedPageDescriptor& rpDescriptor, + const OutputDevice* pReferenceDevice) const; + +private: + const Layouter& mrLayouter; + std::shared_ptr<cache::PageCache> mpCache; + std::shared_ptr<view::Theme> mpTheme; + std::shared_ptr<vcl::Font> mpPageNumberFont; + std::unique_ptr<FramePainter> mpShadowPainter; + std::unique_ptr<FramePainter> mpFocusBorderPainter; + + void PaintBackground ( + PageObjectLayouter *pPageObjectLayouter, + OutputDevice& rDevice, + const model::SharedPageDescriptor& rpDescriptor) const; + void PaintPreview ( + PageObjectLayouter *pPageObjectLayouter, + OutputDevice& rDevice, + const model::SharedPageDescriptor& rpDescriptor) const; + void PaintPageNumber ( + PageObjectLayouter *pPageObjectLayouter, + OutputDevice& rDevice, + const model::SharedPageDescriptor& rpDescriptor) const; + static void PaintTransitionEffect ( + PageObjectLayouter *pPageObjectLayouter, + OutputDevice& rDevice, + const model::SharedPageDescriptor& rpDescriptor); + static void PaintCustomAnimationEffect ( + PageObjectLayouter *pPageObjectLayouter, + OutputDevice& rDevice, + const model::SharedPageDescriptor& rpDescriptor); + void PaintBorder ( + OutputDevice& rDevice, + const Theme::GradientColorType eColorType, + const ::tools::Rectangle& rBox) const; + void PaintBackgroundDetail( + PageObjectLayouter *pPageObjectLayouter, + OutputDevice& rDevice, + const model::SharedPageDescriptor& rpDescriptor) const; + + static BitmapEx CreateMarkedPreview( + const Size& rSize, + const BitmapEx& rPreview, + const BitmapEx& rOverlay, + const OutputDevice* pReferenceDevice); + + /** Update the local pointer to the page object layouter to the + one owned by the general layouter. + Return <TRUE/> when after the call we have a valid page object layouter. + */ + bool UpdatePageObjectLayouter(); +}; + +} // end of namespace sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsTheme.hxx b/sd/source/ui/slidesorter/inc/view/SlsTheme.hxx new file mode 100644 index 000000000..efb7b2a3e --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsTheme.hxx @@ -0,0 +1,135 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <vcl/bitmapex.hxx> +#include <tools/color.hxx> + +#include <memory> + +namespace vcl { class Font; } + +namespace sd::slidesorter::controller { class Properties; } + +namespace sd::slidesorter::view { + +const int Theme_FocusIndicatorWidth = 3; + +/** Collection of colors and styles that are used to paint the slide sorter + view. +*/ +class Theme +{ +public: + Theme (const std::shared_ptr<controller::Properties>& rpProperties); + + /** Call this method to update some colors as response to a change of + a system color change. + */ + void Update ( + const std::shared_ptr<controller::Properties>& rpProperties); + + // BitmapEx GetInsertIndicatorIcon() const; + + enum FontType { + Font_PageNumber, + Font_PageCount + }; + static std::shared_ptr<vcl::Font> GetFont ( + const FontType eType, + const OutputDevice& rDevice); + + enum ColorType { + Color_Background, + Color_PageNumberDefault, + Color_PageNumberHover, + Color_PageNumberHighContrast, + Color_PageNumberBrightBackground, + Color_PageNumberDarkBackground, + Color_Selection, + Color_PreviewBorder, + Color_PageCountFontColor, + ColorType_Size_ + }; + Color GetColor (const ColorType eType); + + enum GradientColorType { + Gradient_NormalPage, + Gradient_SelectedPage, + Gradient_SelectedAndFocusedPage, + Gradient_MouseOverPage, + Gradient_MouseOverSelected, + Gradient_MouseOverSelectedAndFocusedPage, + Gradient_FocusedPage, + GradientColorType_Size_ + }; + enum class GradientColorClass { + Border1, + Border2, + Fill1, + Fill2 + }; + Color GetGradientColor ( + const GradientColorType eType, + const GradientColorClass eClass); + void SetGradient ( + const GradientColorType eType, + const Color aBaseColor, + const sal_Int32 nSaturationOverride, + const sal_Int32 nBrightnessOverride, + const sal_Int32 nFillStartOffset, + const sal_Int32 nFillEndOffset, + const sal_Int32 nBorderStartOffset, + const sal_Int32 nBorderEndOffset); + + enum IconType + { + Icon_RawShadow, + Icon_RawInsertShadow, + Icon_HideSlideOverlay, + Icon_FocusBorder, + IconType_Size_ + }; + const BitmapEx& GetIcon (const IconType eType); + +private: + class GradientDescriptor + { + public: + Color maFillColor1; + Color maFillColor2; + Color maBorderColor1; + Color maBorderColor2; + }; + Color maBackgroundColor; + ::std::vector<GradientDescriptor> maGradients; + ::std::vector<BitmapEx> maIcons; + ::std::vector<Color> maColor; + + GradientDescriptor& GetGradient (const GradientColorType eType); + /** Guarded initialization of the specified icon in the maIcons + container. + */ + void InitializeIcon(const IconType eType, const OUString& rResourceId); +}; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sd/source/ui/slidesorter/inc/view/SlsToolTip.hxx b/sd/source/ui/slidesorter/inc/view/SlsToolTip.hxx new file mode 100644 index 000000000..6c3557e64 --- /dev/null +++ b/sd/source/ui/slidesorter/inc/view/SlsToolTip.hxx @@ -0,0 +1,75 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <model/SlsSharedPageDescriptor.hxx> +#include <rtl/ustring.hxx> +#include <vcl/timer.hxx> + +namespace sd::slidesorter +{ +class SlideSorter; +} + +namespace sd::slidesorter::view +{ +/** Manage the display of tool tips. The tool tip text changes when the + mouse is moved from slide to slide or from button to button. + After the mouse enters a slide the first display of the tool tip is + delayed for a short time in order to not draw attention from the slide + or its button bar. +*/ +class ToolTip +{ +public: + ToolTip(SlideSorter& rSlideSorter); + ~ToolTip(); + + /** Set a new page. This modifies the default help text. After a page + change a timer is started to delay the display of the tool tip for + the new page. + @param rpPage + When this is empty then the tool tip is hidden. + */ + void SetPage(const model::SharedPageDescriptor& rpPage); + + /** Hide the tool tip. + @return + Returns whether the tool tip was visible at the time this method + was called. + */ + bool Hide(); + +private: + SlideSorter& mrSlideSorter; + model::SharedPageDescriptor mpDescriptor; + OUString msCurrentHelpText; + void* mnHelpWindowHandle; + Timer maShowTimer; + Timer maHiddenTimer; + + void DoShow(); + + DECL_LINK(DelayTrigger, Timer*, void); +}; + +} // end of namespace ::sd::slidesorter::view + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |