/* -*- 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 . */ #ifndef SC_FIELDWND_HXX #define SC_FIELDWND_HXX #include #include #include #include #include "address.hxx" #include "pivot.hxx" struct ScPivotField; class ScPivotLayoutDlg; class ScAccessibleDataPilotControl; extern const size_t PIVOTFIELD_INVALID; /** Type of the pivot table field window. */ enum ScPivotFieldType { PIVOTFIELDTYPE_PAGE = 0, /// Window for all page fields. PIVOTFIELDTYPE_COL, /// Window for all column fields. PIVOTFIELDTYPE_ROW, /// Window for all row fields. PIVOTFIELDTYPE_DATA, /// Window for all data fields. PIVOTFIELDTYPE_SELECT, /// Selection window with all fields. PIVOTFIELDTYPE_UNKNOWN }; /** * Represents a field area in the DataPilot layout dialog. This base class * handles storage of field names and the accessibility object. */ class ScDPFieldControlBase : public Control { protected: struct FieldName { rtl::OUString maText; bool mbFits; sal_uInt8 mnDupCount; FieldName(const rtl::OUString& rText, bool bFits, sal_uInt8 nDupCount = 0); FieldName(const FieldName& r); rtl::OUString getDisplayedText() const; }; typedef ::std::vector FieldNames; public: typedef boost::ptr_vector FuncDataType; struct FuncItem { SCCOL mnCol; sal_uInt16 mnFuncMask; }; /** * Custom scroll bar to pass the command event to its parent window. * We need this to pass the mouse wheel events to its parent field * control to have mouse wheel events appaer to be properly handled by the * scroll bar. */ class ScrollBar : public ::ScrollBar { public: ScrollBar(Window* pParent, WinBits nStyle); virtual void Command( const CommandEvent& rCEvt ); private: Window* mpParent; }; ScDPFieldControlBase( ScPivotLayoutDlg* pParent, const ResId& rResId, FixedText* pCaption, const char* pcHelpId); virtual ~ScDPFieldControlBase(); virtual void CalcSize() = 0; virtual bool IsValidIndex( size_t nIndex ) const = 0; /** @return The pixel position of a field (without bound check). */ virtual Point GetFieldPosition( size_t nIndex ) = 0; /** Calculates the field index at a specific pixel position. */ virtual size_t GetFieldIndex( const Point& rPos ) = 0; /** @return The pixel size of a field. */ virtual Size GetFieldSize() const = 0; /** @return The description of the control which is used for the accessibility objects. */ virtual String GetDescription() const = 0; /** @return The type of the FieldWindow. */ virtual ScPivotFieldType GetFieldType() const = 0; virtual void ScrollToShowSelection() = 0; virtual void ScrollToEnd() = 0; virtual void ResetScrollBar() = 0; virtual void HandleWheelScroll(long nNotch) = 0; /** @return The name of the control without shortcut. */ ::rtl::OUString GetName() const; void SetName(const ::rtl::OUString& rName); /** @return TRUE, if the field with the given index exists. */ bool IsExistingIndex( size_t nIndex ) const; void AppendField( const rtl::OUString& rText, const ScPivotFuncData& rFunc ); /** * Inserts a field using the specified pixel position. * * @param rPos The coordinates to insert the field. */ size_t AddField(const rtl::OUString& rText, const Point& rPos, const ScPivotFuncData& rFunc); bool MoveField(size_t nCurPos, const Point& rPos, size_t& rnIndex); /** Remove a field by specified index. */ void DeleteFieldByIndex( size_t nIndex ); /** Returns the number of existing fields. */ size_t GetFieldCount() const; bool IsEmpty() const; /** Removes all fields. */ void ClearFields(); /** Changes the text on an existing field. */ void SetFieldText(const rtl::OUString& rText, size_t nIndex, sal_uInt8 nDupCount); /** Returns the text of an existing field. */ rtl::OUString GetFieldText( size_t nIndex ) const; /** Calculates a field index at a specific pixel position. Returns in every case the index of an existing field. @param rnIndex The index of the field is returned here. @return TRUE, if the index value is valid. */ void GetExistingIndex( const Point& rPos, size_t& rnIndex ); size_t GetSelectedField() const; /** Selects the next field. Called i.e. after moving a field from SELECT area. */ void SelectNext(); /** Grabs focus and sets new selection. */ void GrabFocusAndSelect( size_t nIndex ); const ScPivotFuncData& GetFuncData(size_t nIndex) const; ScPivotFuncData& GetFuncData(size_t nIndex); void GetAllFuncItems(std::vector& rItems) const; sal_uInt8 GetNextDupCount(const ScPivotFuncData& rData, size_t nSelfIndex) const; void ConvertToPivotArray(std::vector& rFields) const; size_t GetFieldIndexByData( const ScPivotFuncData& rData ) const; virtual void Paint( const Rectangle& rRect ); protected: virtual void StateChanged( StateChangedType nStateChange ); virtual void DataChanged( const DataChangedEvent& rDCEvt ); virtual void KeyInput( const KeyEvent& rKEvt ); virtual void Command( const CommandEvent& rCEvt ); virtual void MouseButtonDown( const MouseEvent& rMEvt ); virtual void MouseButtonUp( const MouseEvent& rMEvt ); virtual void MouseMove( const MouseEvent& rMEvt ); virtual void GetFocus(); virtual void LoseFocus(); protected: FieldNames& GetFieldNames(); const FieldNames& GetFieldNames() const; virtual ::com::sun::star::uno::Reference< ::com::sun::star::accessibility::XAccessible > CreateAccessible(); void FieldFocusChanged(size_t nOldSelected, size_t nFieldSelected); /** Updates the tab stop style bits. */ void UpdateStyle(); /** Draw background color for the whole control area. */ void DrawBackground( OutputDevice& rDev ); /** Draw a single field button. */ void DrawField( OutputDevice& rDev, const Rectangle& rRect, FieldName& rText, bool bFocus ); void AppendPaintable(Window* p); void DrawPaintables(); void DrawInvertSelection(); Size GetStdFieldBtnSize() const; /** @return The new selection index after moving to the given direction. */ virtual size_t CalcNewFieldIndex( SCsCOL nDX, SCsROW nDY ) const = 0; /** * @param nIndex logical index of a field name, independent of scroll * offsets. * @return Display position of the button. The first displayed button is * always 0 no matter what the current scroll offset is. In case * the field specified by the index is outside the visible range, * INVALID_INDEX is returned. */ virtual size_t GetDisplayPosition(size_t nIndex) const = 0; /** Draws the complete control. */ virtual void Redraw() = 0; private: /** Moves the selected field to nDestIndex. */ void MoveField( size_t nDestIndex ); /** Moves the selected field to the given direction. */ void MoveFieldRel( SCsCOL nDX, SCsROW nDY ); /** Selects a field and adjusts scrolling position to make the field visible. */ void MoveSelection( size_t nSelectedIndex ); /** Selects a field at a new position relative to the current. */ void MoveSelection( SCsCOL nDX, SCsROW nDY ); sal_uInt8 GetNextDupCount(const rtl::OUString& rFieldText) const; private: typedef ::std::vector Paintables; Paintables maPaintables; FuncDataType maFuncData; FieldNames maFieldNames; /// String array of the field names and flags, if text fits into button. ScPivotLayoutDlg* mpDlg; FixedText* mpCaption; /// FixedText containing the name of the control. ::rtl::OUString maName; size_t mnFieldSelected; /// Currently selected field. // Hold a helpful reference while we work with our weakref. class AccessRef { com::sun::star::uno::Reference< ::com::sun::star::accessibility::XAccessible > mxRef; public: AccessRef( const com::sun::star::uno::WeakReference< ::com::sun::star::accessibility::XAccessible > & rAccessible ); ScAccessibleDataPilotControl *operator -> () const; bool is() { return mxRef.is(); } }; com::sun::star::uno::WeakReference< ::com::sun::star::accessibility::XAccessible > mxAccessible; }; // ============================================================================ /** * Base class for field control with a horizontal scroll bar at the bottom. * Page, column, data and select fields are derived from this class. */ class ScDPHorFieldControl : public ScDPFieldControlBase { protected: virtual size_t CalcNewFieldIndex(SCsCOL nDX, SCsROW nDY) const; virtual size_t GetDisplayPosition(size_t nIndex) const; virtual void Redraw(); public: ScDPHorFieldControl( ScPivotLayoutDlg* pDialog, const ResId& rResId, FixedText* pCaption, const char* pcHelpId); virtual ~ScDPHorFieldControl(); virtual void CalcSize(); virtual bool IsValidIndex( size_t nIndex ) const; virtual Point GetFieldPosition(size_t nIndex); virtual Size GetFieldSize() const; virtual size_t GetFieldIndex( const Point& rPos ); virtual String GetDescription() const; virtual void ScrollToEnd(); virtual void ScrollToShowSelection(); virtual void ResetScrollBar(); virtual void HandleWheelScroll(long nNotch); private: bool GetFieldBtnPosSize(size_t nPos, Point& rPos, Size& rSize); void HandleScroll(); DECL_LINK(ScrollHdl, void*); DECL_LINK(EndScrollHdl, void*); private: ScrollBar maScroll; size_t mnFieldBtnRowCount; size_t mnFieldBtnColCount; }; // ============================================================================ class ScDPPageFieldControl : public ScDPHorFieldControl { public: ScDPPageFieldControl( ScPivotLayoutDlg* pDialog, const ResId& rResId, FixedText* pCaption, const char* pcHelpId); virtual ~ScDPPageFieldControl(); virtual ScPivotFieldType GetFieldType() const; virtual String GetDescription() const; }; // ============================================================================ class ScDPColFieldControl : public ScDPHorFieldControl { public: ScDPColFieldControl( ScPivotLayoutDlg* pDialog, const ResId& rResId, FixedText* pCaption, const char* pcHelpId); virtual ~ScDPColFieldControl(); virtual ScPivotFieldType GetFieldType() const; virtual String GetDescription() const; }; // ============================================================================ /** * Row field control with a vertical scroll bar. */ class ScDPRowFieldControl : public ScDPFieldControlBase { public: ScDPRowFieldControl( ScPivotLayoutDlg* pDialog, const ResId& rResId, FixedText* pCaption, const char* pcHelpId); virtual ~ScDPRowFieldControl(); virtual void CalcSize(); virtual bool IsValidIndex( size_t nIndex ) const; virtual Point GetFieldPosition( size_t nIndex ); virtual Size GetFieldSize() const; virtual size_t GetFieldIndex( const Point& rPos ); virtual String GetDescription() const; virtual ScPivotFieldType GetFieldType() const; virtual void ScrollToEnd(); virtual void ScrollToShowSelection(); virtual void ResetScrollBar(); virtual void HandleWheelScroll(long nNotch); protected: virtual size_t CalcNewFieldIndex( SCsCOL nDX, SCsROW nDY ) const; virtual size_t GetDisplayPosition(size_t nIndex) const; virtual void Redraw(); private: bool GetFieldBtnPosSize(size_t nPos, Point& rPos, Size& rSize); void HandleScroll(); DECL_LINK(ScrollHdl, void*); DECL_LINK(EndScrollHdl, void*); private: ScDPFieldControlBase::ScrollBar maScroll; size_t mnColumnBtnCount; }; // ============================================================================ class ScDPSelectFieldControl : public ScDPHorFieldControl { public: ScDPSelectFieldControl( ScPivotLayoutDlg* pDialog, const ResId& rResId, FixedText* pCaption, const char* pcHelpId); virtual ~ScDPSelectFieldControl(); virtual ScPivotFieldType GetFieldType() const; virtual String GetDescription() const; }; // ============================================================================ class ScDPDataFieldControl : public ScDPHorFieldControl { public: ScDPDataFieldControl( ScPivotLayoutDlg* pParent, const ResId& rResId, FixedText* pCaption, const char* pcHelpId); virtual ~ScDPDataFieldControl(); virtual ScPivotFieldType GetFieldType() const; virtual Size GetFieldSize() const; virtual String GetDescription() const; }; #endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */