From 81d6b090a680d432e33e4de4be9906043eed1139 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 19 Jun 2009 19:51:20 +0000 Subject: #i100619# initial commit of patches from ooo-build that implement new datapilot field popup window. --- sc/source/ui/cctrl/dpcontrol.cxx | 1009 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 1009 insertions(+) create mode 100644 sc/source/ui/cctrl/dpcontrol.cxx (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx new file mode 100644 index 000000000000..d6aa21ab79bb --- /dev/null +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -0,0 +1,1009 @@ +/************************************************************************* + * + * 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: document.hxx,v $ + * $Revision: 1.115.36.9 $ + * + * 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 + * + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_sc.hxx" + +// INCLUDE --------------------------------------------------------------- + +#include "dpcontrol.hxx" + +#include "vcl/outdev.hxx" +#include "vcl/settings.hxx" +#include "vcl/wintypes.hxx" +#include "vcl/decoview.hxx" + +#define MENU_NOT_SELECTED 999 + +using ::rtl::OUString; +using ::rtl::OUStringHash; +using ::std::vector; +using ::std::hash_map; + +ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle) : + mpOutDev(pOutDev), + mpStyle(pStyle), + mbPopupButton(false), + mbHasHiddenMember(false) +{ +} + +ScDPFieldButton::~ScDPFieldButton() +{ +} + +void ScDPFieldButton::setText(const OUString& rText) +{ + maText = rText; +} + +void ScDPFieldButton::setBoundingBox(const Point& rPos, const Size& rSize) +{ + maPos = rPos; + maSize = rSize; +} + +void ScDPFieldButton::setDrawPopupButton(bool b) +{ + mbPopupButton = b; +} + +void ScDPFieldButton::setHasHiddenMember(bool b) +{ + mbHasHiddenMember = b; +} + +void ScDPFieldButton::draw() +{ + const long nMargin = 2; + + // Background + Rectangle aRect(maPos, maSize); + mpOutDev->SetLineColor(mpStyle->GetFaceColor()); + mpOutDev->SetFillColor(mpStyle->GetFaceColor()); + mpOutDev->DrawRect(aRect); + + // Border lines + mpOutDev->SetLineColor(mpStyle->GetLightColor()); + mpOutDev->DrawLine(Point(maPos), Point(maPos.X(), maPos.Y()+maSize.Height()-1)); + mpOutDev->DrawLine(Point(maPos), Point(maPos.X()+maSize.Width()-1, maPos.Y())); + + mpOutDev->SetLineColor(mpStyle->GetShadowColor()); + mpOutDev->DrawLine(Point(maPos.X(), maPos.Y()+maSize.Height()-1), + Point(maPos.X()+maSize.Width()-1, maPos.Y()+maSize.Height()-1)); + mpOutDev->DrawLine(Point(maPos.X()+maSize.Width()-1, maPos.Y()), + Point(maPos.X()+maSize.Width()-1, maPos.Y()+maSize.Height()-1)); + + // Field name + Font aTextFont( mpStyle->GetLabelFont() ); + aTextFont.SetHeight(12); + mpOutDev->SetFont(aTextFont); + + Point aTextPos = maPos; + long nTHeight = mpOutDev->GetTextHeight(); + aTextPos.setX(maPos.getX() + nMargin); + aTextPos.setY(maPos.getY() + (maSize.Height()-nTHeight)/2); + mpOutDev->DrawText(aTextPos, maText); + + if (mbPopupButton) + drawPopupButton(); +} + +void ScDPFieldButton::getPopupBoundingBox(Point& rPos, Size& rSize) const +{ + long nW = maSize.getWidth()*0.5; + long nH = maSize.getHeight(); + if (nW > 16) + nW = 16; + if (nH > 18) + nH = 18; + + rPos.setX(maPos.getX() + maSize.getWidth() - nW); + rPos.setY(maPos.getY() + maSize.getHeight() - nH); + rSize.setWidth(nW); + rSize.setHeight(nH); +} + +bool ScDPFieldButton::isPopupButton() const +{ + return mbPopupButton; +} + +void ScDPFieldButton::drawPopupButton() +{ + Point aPos; + Size aSize; + getPopupBoundingBox(aPos, aSize); + + // border lines + mpOutDev->SetLineColor(mpStyle->GetLightColor()); + mpOutDev->DrawLine(aPos, Point(aPos.X(), aPos.Y()+aSize.Height()-1)); + mpOutDev->DrawLine(aPos, Point(aPos.X()+aSize.Width()-1, aPos.Y())); + + mpOutDev->SetLineColor(mpStyle->GetShadowColor()); + mpOutDev->DrawLine(Point(aPos.X(), aPos.Y()+aSize.Height()-1), + Point(aPos.X()+aSize.Width()-1, aPos.Y()+aSize.Height()-1)); + mpOutDev->DrawLine(Point(aPos.X()+aSize.Width()-1, aPos.Y()), + Point(aPos.X()+aSize.Width()-1, aPos.Y()+aSize.Height()-1)); + + // the arrowhead + Color aArrowColor = mbHasHiddenMember ? mpStyle->GetHighlightLinkColor() : mpStyle->GetButtonTextColor(); + mpOutDev->SetLineColor(aArrowColor); + mpOutDev->SetFillColor(aArrowColor); + Point aCenter(aPos.X() + (aSize.Width() >> 1), aPos.Y() + (aSize.Height() >> 1)); + Point aPos1, aPos2; + aPos1.X() = aCenter.X() - 4; + aPos2.X() = aCenter.X() + 4; + aPos1.Y() = aCenter.Y() - 3; + aPos2.Y() = aCenter.Y() - 3; + + do + { + ++aPos1.X(); + --aPos2.X(); + ++aPos1.Y(); + ++aPos2.Y(); + mpOutDev->DrawLine(aPos1, aPos2); + } + while (aPos1 != aPos2); + + if (mbHasHiddenMember) + { + // tiny little box to display in presence of hidden member(s). + Point aBoxPos(aPos.X() + aSize.Width() - 5, aPos.Y() + aSize.Height() - 5); + Size aBoxSize(3, 3); + mpOutDev->DrawRect(Rectangle(aBoxPos, aBoxSize)); + } +} + +// ============================================================================ + +ScMenuFloatingWindow::MenuItem::MenuItem() : + mbEnabled(true), + mpAction(static_cast(NULL)), + mpSubMenuWin(static_cast(NULL)) +{ +} + +// ---------------------------------------------------------------------------- + +ScMenuFloatingWindow::SubMenuItem::SubMenuItem(ScMenuFloatingWindow* pParent) : + mpSubMenu(NULL), + mnMenuPos(MENU_NOT_SELECTED), + mpParent(pParent) +{ + maTimer.SetTimeoutHdl( LINK(this, ScMenuFloatingWindow::SubMenuItem, TimeoutHdl) ); + maTimer.SetTimeout(mpParent->GetSettings().GetMouseSettings().GetMenuDelay()); +} + +void ScMenuFloatingWindow::SubMenuItem::reset() +{ + mpSubMenu = NULL; + mnMenuPos = MENU_NOT_SELECTED; + maTimer.Stop(); +} + +IMPL_LINK( ScMenuFloatingWindow::SubMenuItem, TimeoutHdl, void*, EMPTYARG ) +{ + mpParent->handleMenuTimeout(this); + return 0; +} + +// ---------------------------------------------------------------------------- + +ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent) : + FloatingWindow(pParent, (WB_SYSTEMFLOATWIN|WB_SYSTEMWINDOW|WB_NOBORDER)), + maOpenTimer(this), + maCloseTimer(this), + mnSelectedMenu(MENU_NOT_SELECTED), + mnClickedMenu(MENU_NOT_SELECTED), + mpParentMenu(dynamic_cast(pParent)), + mpActiveSubMenu(NULL), + mbActionFired(false) +{ + // TODO: How do we get the right font to use here ? + const sal_uInt16 nPopupFontHeight = 12; + const StyleSettings& rStyle = GetSettings().GetStyleSettings(); + maLabelFont = rStyle.GetLabelFont(); + maLabelFont.SetHeight(nPopupFontHeight); + SetFont(maLabelFont); + + SetPopupModeEndHdl( LINK(this, ScMenuFloatingWindow, EndPopupHdl) ); +} + +ScMenuFloatingWindow::~ScMenuFloatingWindow() +{ + EndPopupMode(); +} + +void ScMenuFloatingWindow::MouseMove(const MouseEvent& rMEvt) +{ + const Point& rPos = rMEvt.GetPosPixel(); + size_t nSelectedMenu = getEnclosingMenuItem(rPos); + setSelectedMenuItem(nSelectedMenu); + + Window::MouseMove(rMEvt); +} + +void ScMenuFloatingWindow::MouseButtonDown(const MouseEvent& rMEvt) +{ + const Point& rPos = rMEvt.GetPosPixel(); + mnClickedMenu = getEnclosingMenuItem(rPos); + Window::MouseButtonDown(rMEvt); +} + +void ScMenuFloatingWindow::MouseButtonUp(const MouseEvent& rMEvt) +{ + executeMenu(mnClickedMenu); + mnClickedMenu = MENU_NOT_SELECTED; + Window::MouseButtonUp(rMEvt); +} + +void ScMenuFloatingWindow::KeyInput(const KeyEvent& rKEvt) +{ + const KeyCode& rKeyCode = rKEvt.GetKeyCode(); + bool bHandled = true; + size_t nSelectedMenu = mnSelectedMenu; + size_t nLastMenuPos = maMenuItems.size() - 1; + switch (rKeyCode.GetCode()) + { + case KEY_UP: + if (nSelectedMenu == MENU_NOT_SELECTED || nSelectedMenu == 0) + nSelectedMenu = nLastMenuPos; + else + --nSelectedMenu; + setSelectedMenuItem(nSelectedMenu, false); + break; + case KEY_DOWN: + if (nSelectedMenu == MENU_NOT_SELECTED || nSelectedMenu == nLastMenuPos) + nSelectedMenu = 0; + else + ++nSelectedMenu; + setSelectedMenuItem(nSelectedMenu, false); + break; + case KEY_LEFT: + if (mpParentMenu) + mpParentMenu->endSubMenu(); + break; + case KEY_RIGHT: + { + if (mnSelectedMenu >= maMenuItems.size() || mnSelectedMenu == MENU_NOT_SELECTED) + break; + + const MenuItem& rMenu = maMenuItems[mnSelectedMenu]; + if (!rMenu.mbEnabled || !rMenu.mpSubMenuWin) + break; + + maOpenTimer.mnMenuPos = mnSelectedMenu; + maOpenTimer.mpSubMenu = rMenu.mpSubMenuWin.get(); + launchSubMenu(true); + } + break; + case KEY_RETURN: + if (nSelectedMenu != MENU_NOT_SELECTED) + executeMenu(nSelectedMenu); + break; + default: + bHandled = false; + } + + if (!bHandled) + Window::KeyInput(rKEvt); +} + +void ScMenuFloatingWindow::Paint(const Rectangle& /*rRect*/) +{ + const StyleSettings& rStyle = GetSettings().GetStyleSettings(); + Color aBackColor = rStyle.GetMenuColor(); + Color aBorderColor = rStyle.GetShadowColor(); + + Rectangle aCtrlRect(Point(0, 0), GetOutputSizePixel()); + + // Window background + bool bNativeDrawn = true; + if (IsNativeControlSupported(CTRL_MENU_POPUP, PART_ENTIRE_CONTROL)) + { + SetClipRegion(); + bNativeDrawn = DrawNativeControl( + CTRL_MENU_POPUP, PART_ENTIRE_CONTROL, Region(aCtrlRect), CTRL_STATE_ENABLED, + ImplControlValue(), OUString()); + } + else + bNativeDrawn = false; + + if (!bNativeDrawn) + { + SetFillColor(aBackColor); + SetLineColor(aBorderColor); + DrawRect(aCtrlRect); + } + + // Menu items + SetTextColor(rStyle.GetMenuTextColor()); + drawAllMenuItems(); +} + +void ScMenuFloatingWindow::addMenuItem(const OUString& rText, bool bEnabled, Action* pAction) +{ + MenuItem aItem; + aItem.maText = rText; + aItem.mbEnabled = bEnabled; + aItem.mpAction.reset(pAction); + maMenuItems.push_back(aItem); +} + +ScMenuFloatingWindow* ScMenuFloatingWindow::addSubMenuItem(const OUString& rText, bool bEnabled) +{ + MenuItem aItem; + aItem.maText = rText; + aItem.mbEnabled = bEnabled; + aItem.mpSubMenuWin.reset(new ScMenuFloatingWindow(this)); + maMenuItems.push_back(aItem); + return aItem.mpSubMenuWin.get(); +} + +void ScMenuFloatingWindow::drawMenuItem(size_t nPos) +{ + if (nPos >= maMenuItems.size()) + return; + + Point aPos; + Size aSize; + getMenuItemPosSize(aPos, aSize, nPos); + + DecorationView aDecoView(this); + long nXOffset = 5; + long nYOffset = (aSize.Height() - maLabelFont.GetHeight())/2; + DrawCtrlText(Point(aPos.X()+nXOffset, aPos.Y() + nYOffset), maMenuItems[nPos].maText, 0, STRING_LEN, + maMenuItems[nPos].mbEnabled ? TEXT_DRAW_MNEMONIC : TEXT_DRAW_DISABLE); + + if (maMenuItems[nPos].mpSubMenuWin) + { + long nFontHeight = maLabelFont.GetHeight(); + Point aMarkerPos = aPos; + aMarkerPos.Y() += aSize.Height()/2 - nFontHeight/4 + 1; + aMarkerPos.X() += aSize.Width() - nFontHeight + nFontHeight/4; + Size aMarkerSize(nFontHeight/2, nFontHeight/2); + aDecoView.DrawSymbol(Rectangle(aMarkerPos, aMarkerSize), + SYMBOL_SPIN_RIGHT, GetTextColor(), 0); + } +} + +void ScMenuFloatingWindow::drawAllMenuItems() +{ + size_t n = maMenuItems.size(); + for (size_t i = 0; i < n; ++i) + highlightMenuItem(i, i == mnSelectedMenu); +} + +const Font& ScMenuFloatingWindow::getLabelFont() const +{ + return maLabelFont; +} + +void ScMenuFloatingWindow::executeMenu(size_t nPos) +{ + if (nPos >= maMenuItems.size()) + return; + + if (!maMenuItems[nPos].mpAction) + // no action is defined. + return; + + maMenuItems[nPos].mpAction->execute(); + mbActionFired = true; + EndPopupMode(); +} + +void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer) +{ + if (mnSelectedMenu != nPos) + { + selectMenuItem(mnSelectedMenu, false, bSubMenuTimer); + selectMenuItem(nPos, true, bSubMenuTimer); + mnSelectedMenu = nPos; + } +} + +size_t ScMenuFloatingWindow::getSelectedMenuItem() const +{ + return mnSelectedMenu; +} + +void ScMenuFloatingWindow::handleMenuTimeout(SubMenuItem* pTimer) +{ + if (pTimer == &maOpenTimer) + { + // Close any open submenu immediately. + if (maCloseTimer.mpSubMenu) + { + maCloseTimer.mpSubMenu->EndPopupMode(); + maCloseTimer.mpSubMenu = NULL; + maCloseTimer.maTimer.Stop(); + } + + launchSubMenu(false); + } + else if (pTimer == &maCloseTimer) + { + // end submenu. + if (maCloseTimer.mpSubMenu) + { + maOpenTimer.mpSubMenu = NULL; + + maCloseTimer.mpSubMenu->EndPopupMode(); + maCloseTimer.mpSubMenu = NULL; + + highlightMenuItem(maOpenTimer.mnMenuPos, false); + maOpenTimer.mnMenuPos = MENU_NOT_SELECTED; + } + } +} + +void ScMenuFloatingWindow::queueLaunchSubMenu(size_t nPos, ScMenuFloatingWindow* pMenu) +{ + if (!pMenu) + return; + + // Set the submenu on launch queue. + if (maOpenTimer.mpSubMenu) + { + if (maOpenTimer.mpSubMenu == pMenu) + { + if (pMenu == maCloseTimer.mpSubMenu) + maCloseTimer.reset(); + return; + } + + // new submenu is being requested. + queueCloseSubMenu(); + } + + maOpenTimer.mpSubMenu = pMenu; + maOpenTimer.mnMenuPos = nPos; + maOpenTimer.maTimer.Start(); +} + +void ScMenuFloatingWindow::queueCloseSubMenu() +{ + if (!maOpenTimer.mpSubMenu) + // There is no submenu to close. + return; + + // Stop any submenu on queue for opening. + maOpenTimer.maTimer.Stop(); + + maCloseTimer.mpSubMenu = maOpenTimer.mpSubMenu; + maCloseTimer.mnMenuPos = maOpenTimer.mnMenuPos; + maCloseTimer.maTimer.Start(); +} + +void ScMenuFloatingWindow::launchSubMenu(bool bSetMenuPos) +{ + Point aPos; + Size aSize; + getMenuItemPosSize(aPos, aSize, maOpenTimer.mnMenuPos); + ScMenuFloatingWindow* pSubMenu = maOpenTimer.mpSubMenu; + + if (!pSubMenu) + return; + + sal_uInt32 nOldFlags = GetPopupModeFlags(); + SetPopupModeFlags(nOldFlags | FLOATWIN_POPUPMODE_NOAPPFOCUSCLOSE); + pSubMenu->resetMenu(bSetMenuPos); + pSubMenu->StartPopupMode( + Rectangle(aPos,aSize), (FLOATWIN_POPUPMODE_RIGHT | FLOATWIN_POPUPMODE_GRABFOCUS)); + pSubMenu->AddPopupModeWindow(this); + SetPopupModeFlags(nOldFlags); +} + +void ScMenuFloatingWindow::endSubMenu() +{ + if (maOpenTimer.mpSubMenu) + { + maOpenTimer.mpSubMenu->EndPopupMode(); + maOpenTimer.mpSubMenu = NULL; + highlightMenuItem(maOpenTimer.mnMenuPos, true); + } +} + +void ScMenuFloatingWindow::notify(NotificationType eType) +{ + switch (eType) + { + case SUBMENU_FOCUSED: + // Cancel any request for ending submenu. + maCloseTimer.reset(); + if (mnSelectedMenu != maOpenTimer.mnMenuPos) + { + highlightMenuItem(maOpenTimer.mnMenuPos, true); + mnSelectedMenu = maOpenTimer.mnMenuPos; + } + break; + default: + ; + } +} + +void ScMenuFloatingWindow::resetMenu(bool bSetMenuPos) +{ + mnSelectedMenu = bSetMenuPos ? 0 : MENU_NOT_SELECTED; + resizeToFitMenuItems(); +} + +void ScMenuFloatingWindow::resizeToFitMenuItems() +{ + if (maMenuItems.empty()) + return; + + vector::const_iterator itr = maMenuItems.begin(), itrEnd = maMenuItems.end(); + long nTextWidth = 0; + for (; itr != itrEnd; ++itr) + nTextWidth = ::std::max(GetTextWidth(itr->maText), nTextWidth); + + size_t nLastPos = maMenuItems.size()-1; + Point aPos; + Size aSize; + getMenuItemPosSize(aPos, aSize, nLastPos); + aPos.X() += nTextWidth + 15; + aPos.Y() += aSize.Height() + 5; + SetOutputSizePixel(Size(aPos.X(), aPos.Y())); +} + +void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer) +{ + if (nPos >= maMenuItems.size() || nPos == MENU_NOT_SELECTED) + { + queueCloseSubMenu(); + return; + } + + if (!maMenuItems[nPos].mbEnabled) + { + queueCloseSubMenu(); + return; + } + + highlightMenuItem(nPos, bSelected); + + if (bSelected) + { + if (mpParentMenu) + mpParentMenu->notify(SUBMENU_FOCUSED); + + if (bSubMenuTimer) + { + if (maMenuItems[nPos].mpSubMenuWin) + { + ScMenuFloatingWindow* pSubMenu = maMenuItems[nPos].mpSubMenuWin.get(); + queueLaunchSubMenu(nPos, pSubMenu); + } + else + queueCloseSubMenu(); + } + } +} + +void ScMenuFloatingWindow::highlightMenuItem(size_t nPos, bool bSelected) +{ + const StyleSettings& rStyle = GetSettings().GetStyleSettings(); + Color aBackColor = rStyle.GetMenuColor(); + SetFillColor(aBackColor); + SetLineColor(aBackColor); + + Point aPos; + Size aSize; + getMenuItemPosSize(aPos, aSize, nPos); + Region aRegion(Rectangle(aPos,aSize)); + + if (IsNativeControlSupported(CTRL_MENU_POPUP, PART_ENTIRE_CONTROL)) + { + Push(PUSH_CLIPREGION); + IntersectClipRegion(Rectangle(aPos, aSize)); + Rectangle aCtrlRect(Point(0,0), GetOutputSizePixel()); + DrawNativeControl( + CTRL_MENU_POPUP, PART_ENTIRE_CONTROL, Region(aCtrlRect), CTRL_STATE_ENABLED, + ImplControlValue(), OUString()); + + Pop(); + } + + bool bNativeDrawn = true; + if (IsNativeControlSupported(CTRL_MENU_POPUP, PART_MENU_ITEM)) + { + ControlState nState = bSelected ? CTRL_STATE_SELECTED : 0; + if (maMenuItems[nPos].mbEnabled) + nState |= CTRL_STATE_ENABLED; + bNativeDrawn = DrawNativeControl( + CTRL_MENU_POPUP, PART_MENU_ITEM, aRegion, nState, ImplControlValue(), OUString()); + } + else + bNativeDrawn = false; + + if (!bNativeDrawn) + { + if (bSelected) + { + aBackColor = rStyle.GetMenuHighlightColor(); + SetFillColor(aBackColor); + SetLineColor(aBackColor); + } + DrawRect(Rectangle(aPos,aSize)); + } + + Color aTextColor = bSelected ? rStyle.GetMenuHighlightTextColor() : rStyle.GetMenuTextColor(); + SetTextColor(aTextColor); + drawMenuItem(nPos); +} + +void ScMenuFloatingWindow::getMenuItemPosSize(Point& rPos, Size& rSize, size_t nPos) const +{ + const sal_uInt16 nLeftMargin = 5; + const sal_uInt16 nTopMargin = 5; + const sal_uInt16 nMenuItemHeight = maLabelFont.GetHeight()*1.8; + + Size aWndSize = GetSizePixel(); + + Point aPos1(nLeftMargin, nTopMargin); + Size aSize1(aWndSize.Width() - nLeftMargin*2, nMenuItemHeight); + + rPos = aPos1; + rPos.Y() += aSize1.Height()*nPos; + rSize = aSize1; +} + +size_t ScMenuFloatingWindow::getEnclosingMenuItem(const Point& rPos) const +{ + size_t n = maMenuItems.size(); + for (size_t i = 0; i < n; ++i) + { + Point aPos; + Size aSize; + getMenuItemPosSize(aPos, aSize, i); + Rectangle aRect(aPos, aSize); + if (aRect.IsInside(rPos)) + return i; + } + return MENU_NOT_SELECTED; +} + +IMPL_LINK( ScMenuFloatingWindow, EndPopupHdl, void*, EMPTYARG ) +{ + if (mbActionFired && mpParentMenu) + mpParentMenu->EndPopupMode(); + + return 0; +} + +// ============================================================================ + +ScDPFieldPopupWindow::Member::Member() : + mbVisible(true) +{ +} + +// ---------------------------------------------------------------------------- + +ScDPFieldPopupWindow::CancelButton::CancelButton(ScDPFieldPopupWindow* pParent) : + ::CancelButton(pParent), mpParent(pParent) {} + +void ScDPFieldPopupWindow::CancelButton::Click() +{ + mpParent->EndPopupMode(); + ::CancelButton::Click(); +} + +// ---------------------------------------------------------------------------- + +ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : + ScMenuFloatingWindow(pParent), + maCheck0(this, 0), + maCheck1(this, 0), + maCheck2(this, 0), + maCheck3(this, 0), + maCheck4(this, 0), + maCheck5(this, 0), + maCheck6(this, 0), + maCheck7(this, 0), + maCheck8(this, 0), + maCheck9(this, 0), + maScrollBar(this, WB_VERT), + maBtnOk(this), + maBtnCancel(this), + mpExtendedData(NULL), + mpOKAction(NULL), + mnScrollPos(0) +{ + Point aPos; + Size aSize; + getSectionPosSize(aPos, aSize, WHOLE); + SetOutputSizePixel(aSize); + Size aOutSize = GetOutputSizePixel(); + + mpCheckPtr.reserve(10); + mpCheckPtr.push_back(&maCheck0); + mpCheckPtr.push_back(&maCheck1); + mpCheckPtr.push_back(&maCheck2); + mpCheckPtr.push_back(&maCheck3); + mpCheckPtr.push_back(&maCheck4); + mpCheckPtr.push_back(&maCheck5); + mpCheckPtr.push_back(&maCheck6); + mpCheckPtr.push_back(&maCheck7); + mpCheckPtr.push_back(&maCheck8); + mpCheckPtr.push_back(&maCheck9); + + getSectionPosSize(aPos, aSize, FIRST_LISTITEM); + for (vector::iterator itr = mpCheckPtr.begin(), itrEnd = mpCheckPtr.end(); + itr != itrEnd; ++itr) + { + CheckBox* p = *itr; + p->SetPosSizePixel(aPos, aSize); + p->SetFont(getLabelFont()); + p->SetClickHdl( LINK(this, ScDPFieldPopupWindow, CheckBoxHdl) ); + aPos.Y() += aSize.Height() + 1; + } + + getSectionPosSize(aPos, aSize, BTN_OK); + maBtnOk.SetPosSizePixel(aPos, aSize); + maBtnOk.SetFont(getLabelFont()); + maBtnOk.SetClickHdl( LINK(this, ScDPFieldPopupWindow, OKButtonHdl) ); + maBtnOk.Show(); + + getSectionPosSize(aPos, aSize, BTN_CANCEL); + maBtnCancel.SetPosSizePixel(aPos, aSize); + maBtnCancel.SetFont(getLabelFont()); + maBtnCancel.Show(); + + getSectionPosSize(aPos, aSize, SCROLL_BAR_V); + maScrollBar.SetPosSizePixel(aPos, aSize); + maScrollBar.SetPageSize(mpCheckPtr.size()); + maScrollBar.SetVisibleSize(mpCheckPtr.size()); + maScrollBar.SetLineSize(1); + maScrollBar.SetScrollHdl( LINK(this, ScDPFieldPopupWindow, ScrollHdl) ); + maScrollBar.EnableDrag(true); +} + +ScDPFieldPopupWindow::~ScDPFieldPopupWindow() +{ +} + +vector& ScDPFieldPopupWindow::getMembers() +{ + return maMembers; +} + +void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionType eType) const +{ + const sal_uInt16 nListBoxMargin = 5; + const sal_uInt16 nTopMargin = 5; + const sal_uInt16 nMenuHeight = 60; + const sal_uInt16 nBottomBtnAreaHeight = 50; + const sal_uInt16 nInnerItemMargin = 5; + const sal_uInt16 nScrollBarWidth = 17; + const sal_uInt16 nBtnWidth = 60; + const sal_uInt16 nBtnHeight = getLabelFont().GetHeight()*2; + const sal_uInt16 nBottomMargin = 10; + const sal_uInt16 nMenuListMargin = 20; + + Size aWndSize = Size(160, 330); + + switch (eType) + { + case WHOLE: + { + rPos = Point(0, 0); + rSize = aWndSize; + } + break; + case LISTBOX_AREA: + { + rPos = Point(nListBoxMargin, nTopMargin + nMenuHeight + nMenuListMargin); + rSize = Size( + aWndSize.Width() - nListBoxMargin*2, + aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight); + } + break; + case FIRST_LISTITEM: + { + rPos = Point(nListBoxMargin + nInnerItemMargin, + nTopMargin + nMenuHeight + nMenuListMargin + nInnerItemMargin); + rSize = Size( + aWndSize.Width() - nListBoxMargin*2 - nInnerItemMargin - nScrollBarWidth - 10, + 17); + } + break; + case BTN_OK: + { + long x = (aWndSize.Width() - nBtnWidth*2)/3; + long y = aWndSize.Height() - nBottomMargin - nBtnHeight; + rPos = Point(x, y); + rSize = Size(nBtnWidth, nBtnHeight); + } + break; + case BTN_CANCEL: + { + long x = (aWndSize.Width() - nBtnWidth*2)/3*2 + nBtnWidth; + long y = aWndSize.Height() - nBottomMargin - nBtnHeight; + rPos = Point(x, y); + rSize = Size(nBtnWidth, nBtnHeight); + } + break; + case SCROLL_BAR_V: + { + long x = aWndSize.Width() - nListBoxMargin - nInnerItemMargin - nScrollBarWidth; + long y = nTopMargin + nMenuHeight + nMenuListMargin + nInnerItemMargin; + rPos = Point(x, y); + long h = aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight - nInnerItemMargin*2; + rSize = Size(nScrollBarWidth, h); + } + break; + default: + ; + } +} + +void ScDPFieldPopupWindow::resetDisplayedItems() +{ + long nScrollPos = maScrollBar.GetThumbPos(); + if (nScrollPos < 0) + return; + + mnScrollPos = static_cast(nScrollPos); + size_t nCheckCount = mpCheckPtr.size(); + for (size_t i = 0; i < nCheckCount; ++i) + { + CheckBox* p = mpCheckPtr[i]; + p->SetText(maMembers[i+mnScrollPos].maName); + TriState nNewState = maMembers[i+mnScrollPos].mbVisible ? STATE_CHECK : STATE_NOCHECK; + p->SetState(nNewState); + } +} + +IMPL_LINK( ScDPFieldPopupWindow, CheckBoxHdl, CheckBox*, pCheck ) +{ + vector::const_iterator itr, itrBeg = mpCheckPtr.begin(), itrEnd = mpCheckPtr.end(); + for (itr = itrBeg; itr != itrEnd; ++itr) + { + if (*itr == pCheck) + { + size_t nIndex = ::std::distance(itrBeg, itr); + maMembers[nIndex+mnScrollPos].mbVisible = !maMembers[nIndex+mnScrollPos].mbVisible; + } + } + return 0; +} + +IMPL_LINK( ScDPFieldPopupWindow, OKButtonHdl, OKButton*, EMPTYARG ) +{ + close(true); + return 0; +} + +IMPL_LINK( ScDPFieldPopupWindow, ScrollHdl, ScrollBar*, EMPTYARG ) +{ + resetDisplayedItems(); + return 0; +} + +void ScDPFieldPopupWindow::MouseMove(const MouseEvent& rMEvt) +{ + ScMenuFloatingWindow::MouseMove(rMEvt); + + size_t nSelectedMenu = getSelectedMenuItem(); + if (nSelectedMenu == MENU_NOT_SELECTED) + queueCloseSubMenu(); +} + +void ScDPFieldPopupWindow::Paint(const Rectangle& rRect) +{ + ScMenuFloatingWindow::Paint(rRect); + + const StyleSettings& rStyle = GetSettings().GetStyleSettings(); + Color aMemberBackColor = rStyle.GetFieldColor(); + + // Member list box background + SetFillColor(aMemberBackColor); + Point aPos; + Size aSize; + getSectionPosSize(aPos, aSize, LISTBOX_AREA); + DrawRect(Rectangle(aPos,aSize)); +} + +void ScDPFieldPopupWindow::setMemberSize(size_t n) +{ + maMembers.reserve(n); +} + +void ScDPFieldPopupWindow::addMember(const OUString& rName, bool bVisible) +{ + Member aMember; + aMember.maName = rName; + aMember.mbVisible = bVisible; + maMembers.push_back(aMember); +} + +void ScDPFieldPopupWindow::initMembers() +{ + size_t nMemCount = maMembers.size(); + size_t nCheckCount = mpCheckPtr.size(); + bool bNeedsScroll = false; + if (nMemCount > nCheckCount) + { + nMemCount = nCheckCount; + bNeedsScroll = true; + } + + for (size_t i = 0; i < nMemCount; ++i) + { + CheckBox* p = mpCheckPtr[i]; + p->SetText(maMembers[i].maName); + p->Show(); + p->SetState(maMembers[i].mbVisible ? STATE_CHECK : STATE_NOCHECK); + } + if (bNeedsScroll) + { + maScrollBar.SetRange(Range(0, maMembers.size())); + maScrollBar.Show(); + } +} + +void ScDPFieldPopupWindow::getResult(hash_map& rResult) +{ + typedef hash_map ResultMap; + ResultMap aResult; + vector::const_iterator itr = maMembers.begin(), itrEnd = maMembers.end(); + for (; itr != itrEnd; ++itr) + aResult.insert(ResultMap::value_type(itr->maName, itr->mbVisible)); + rResult.swap(aResult); +} + +void ScDPFieldPopupWindow::close(bool bOK) +{ + if (bOK && mpOKAction.get()) + mpOKAction->execute(); + + EndPopupMode(); +} + +void ScDPFieldPopupWindow::setExtendedData(ExtendedData* p) +{ + mpExtendedData.reset(p); +} + +ScDPFieldPopupWindow::ExtendedData* ScDPFieldPopupWindow::getExtendedData() +{ + return mpExtendedData.get(); +} + +void ScDPFieldPopupWindow::setOKAction(Action* p) +{ + mpOKAction.reset(p); +} + -- cgit From 34310d90da930c12be486d88cc3a478fa650ba57 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 30 Jul 2009 00:40:07 +0000 Subject: Draw borders around the list member box. --- sc/source/ui/cctrl/dpcontrol.cxx | 2 ++ 1 file changed, 2 insertions(+) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index d6aa21ab79bb..b483f2bde957 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -927,9 +927,11 @@ void ScDPFieldPopupWindow::Paint(const Rectangle& rRect) const StyleSettings& rStyle = GetSettings().GetStyleSettings(); Color aMemberBackColor = rStyle.GetFieldColor(); + Color aBorderColor = rStyle.GetShadowColor(); // Member list box background SetFillColor(aMemberBackColor); + SetLineColor(aBorderColor); Point aPos; Size aSize; getSectionPosSize(aPos, aSize, LISTBOX_AREA); -- cgit From 58a98fbb38dc78eba9768cebfc1e6215fbe97306 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 30 Jul 2009 21:07:52 +0000 Subject: Used SvxCheckListBox to implement the check list box instead of rolling my own. --- sc/source/ui/cctrl/dpcontrol.cxx | 130 +++++++++------------------------------ 1 file changed, 28 insertions(+), 102 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index b483f2bde957..185671b3af97 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -724,17 +724,7 @@ void ScDPFieldPopupWindow::CancelButton::Click() ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : ScMenuFloatingWindow(pParent), - maCheck0(this, 0), - maCheck1(this, 0), - maCheck2(this, 0), - maCheck3(this, 0), - maCheck4(this, 0), - maCheck5(this, 0), - maCheck6(this, 0), - maCheck7(this, 0), - maCheck8(this, 0), - maCheck9(this, 0), - maScrollBar(this, WB_VERT), + maChecks(this, 0), maBtnOk(this), maBtnCancel(this), mpExtendedData(NULL), @@ -747,29 +737,6 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : SetOutputSizePixel(aSize); Size aOutSize = GetOutputSizePixel(); - mpCheckPtr.reserve(10); - mpCheckPtr.push_back(&maCheck0); - mpCheckPtr.push_back(&maCheck1); - mpCheckPtr.push_back(&maCheck2); - mpCheckPtr.push_back(&maCheck3); - mpCheckPtr.push_back(&maCheck4); - mpCheckPtr.push_back(&maCheck5); - mpCheckPtr.push_back(&maCheck6); - mpCheckPtr.push_back(&maCheck7); - mpCheckPtr.push_back(&maCheck8); - mpCheckPtr.push_back(&maCheck9); - - getSectionPosSize(aPos, aSize, FIRST_LISTITEM); - for (vector::iterator itr = mpCheckPtr.begin(), itrEnd = mpCheckPtr.end(); - itr != itrEnd; ++itr) - { - CheckBox* p = *itr; - p->SetPosSizePixel(aPos, aSize); - p->SetFont(getLabelFont()); - p->SetClickHdl( LINK(this, ScDPFieldPopupWindow, CheckBoxHdl) ); - aPos.Y() += aSize.Height() + 1; - } - getSectionPosSize(aPos, aSize, BTN_OK); maBtnOk.SetPosSizePixel(aPos, aSize); maBtnOk.SetFont(getLabelFont()); @@ -781,13 +748,10 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : maBtnCancel.SetFont(getLabelFont()); maBtnCancel.Show(); - getSectionPosSize(aPos, aSize, SCROLL_BAR_V); - maScrollBar.SetPosSizePixel(aPos, aSize); - maScrollBar.SetPageSize(mpCheckPtr.size()); - maScrollBar.SetVisibleSize(mpCheckPtr.size()); - maScrollBar.SetLineSize(1); - maScrollBar.SetScrollHdl( LINK(this, ScDPFieldPopupWindow, ScrollHdl) ); - maScrollBar.EnableDrag(true); + getSectionPosSize(aPos, aSize, LISTBOX_AREA_INNER); + maChecks.SetPosSizePixel(aPos, aSize); + maChecks.SetFont(getLabelFont()); + maChecks.Show(); } ScDPFieldPopupWindow::~ScDPFieldPopupWindow() @@ -802,6 +766,7 @@ vector& ScDPFieldPopupWindow::getMembers() void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionType eType) const { const sal_uInt16 nListBoxMargin = 5; + const sal_uInt16 nListBoxInnerPadding = 5; const sal_uInt16 nTopMargin = 5; const sal_uInt16 nMenuHeight = 60; const sal_uInt16 nBottomBtnAreaHeight = 50; @@ -822,7 +787,7 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy rSize = aWndSize; } break; - case LISTBOX_AREA: + case LISTBOX_AREA_OUTER: { rPos = Point(nListBoxMargin, nTopMargin + nMenuHeight + nMenuListMargin); rSize = Size( @@ -830,6 +795,15 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight); } break; + case LISTBOX_AREA_INNER: + { + rPos = Point(nListBoxMargin + nListBoxInnerPadding, + nTopMargin + nMenuHeight + nMenuListMargin + nListBoxInnerPadding); + rSize = Size( + aWndSize.Width() - nListBoxMargin*2 - nListBoxInnerPadding*2, + aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight - nListBoxInnerPadding*2); + } + break; case FIRST_LISTITEM: { rPos = Point(nListBoxMargin + nInnerItemMargin, @@ -869,49 +843,12 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy } } -void ScDPFieldPopupWindow::resetDisplayedItems() -{ - long nScrollPos = maScrollBar.GetThumbPos(); - if (nScrollPos < 0) - return; - - mnScrollPos = static_cast(nScrollPos); - size_t nCheckCount = mpCheckPtr.size(); - for (size_t i = 0; i < nCheckCount; ++i) - { - CheckBox* p = mpCheckPtr[i]; - p->SetText(maMembers[i+mnScrollPos].maName); - TriState nNewState = maMembers[i+mnScrollPos].mbVisible ? STATE_CHECK : STATE_NOCHECK; - p->SetState(nNewState); - } -} - -IMPL_LINK( ScDPFieldPopupWindow, CheckBoxHdl, CheckBox*, pCheck ) -{ - vector::const_iterator itr, itrBeg = mpCheckPtr.begin(), itrEnd = mpCheckPtr.end(); - for (itr = itrBeg; itr != itrEnd; ++itr) - { - if (*itr == pCheck) - { - size_t nIndex = ::std::distance(itrBeg, itr); - maMembers[nIndex+mnScrollPos].mbVisible = !maMembers[nIndex+mnScrollPos].mbVisible; - } - } - return 0; -} - IMPL_LINK( ScDPFieldPopupWindow, OKButtonHdl, OKButton*, EMPTYARG ) { close(true); return 0; } -IMPL_LINK( ScDPFieldPopupWindow, ScrollHdl, ScrollBar*, EMPTYARG ) -{ - resetDisplayedItems(); - return 0; -} - void ScDPFieldPopupWindow::MouseMove(const MouseEvent& rMEvt) { ScMenuFloatingWindow::MouseMove(rMEvt); @@ -929,12 +866,13 @@ void ScDPFieldPopupWindow::Paint(const Rectangle& rRect) Color aMemberBackColor = rStyle.GetFieldColor(); Color aBorderColor = rStyle.GetShadowColor(); + Point aPos; + Size aSize; + getSectionPosSize(aPos, aSize, LISTBOX_AREA_OUTER); + // Member list box background SetFillColor(aMemberBackColor); SetLineColor(aBorderColor); - Point aPos; - Size aSize; - getSectionPosSize(aPos, aSize, LISTBOX_AREA); DrawRect(Rectangle(aPos,aSize)); } @@ -954,25 +892,10 @@ void ScDPFieldPopupWindow::addMember(const OUString& rName, bool bVisible) void ScDPFieldPopupWindow::initMembers() { size_t nMemCount = maMembers.size(); - size_t nCheckCount = mpCheckPtr.size(); - bool bNeedsScroll = false; - if (nMemCount > nCheckCount) - { - nMemCount = nCheckCount; - bNeedsScroll = true; - } - for (size_t i = 0; i < nMemCount; ++i) { - CheckBox* p = mpCheckPtr[i]; - p->SetText(maMembers[i].maName); - p->Show(); - p->SetState(maMembers[i].mbVisible ? STATE_CHECK : STATE_NOCHECK); - } - if (bNeedsScroll) - { - maScrollBar.SetRange(Range(0, maMembers.size())); - maScrollBar.Show(); + maChecks.InsertEntry(maMembers[i].maName); + maChecks.CheckEntryPos(i, maMembers[i].mbVisible); } } @@ -980,9 +903,12 @@ void ScDPFieldPopupWindow::getResult(hash_map& rRe { typedef hash_map ResultMap; ResultMap aResult; - vector::const_iterator itr = maMembers.begin(), itrEnd = maMembers.end(); - for (; itr != itrEnd; ++itr) - aResult.insert(ResultMap::value_type(itr->maName, itr->mbVisible)); + size_t n = maMembers.size(); + for (size_t i = 0; i < n; ++i) + { + bool bState = maChecks.IsChecked(i); + aResult.insert(ResultMap::value_type(maMembers[i].maName, bState)); + } rResult.swap(aResult); } -- cgit From 4c1e7fbbd53c669ae6f274a24a7ac73c7107ceaf Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 30 Jul 2009 21:11:57 +0000 Subject: Removed unused code after the switch to SvxCheckListBox. --- sc/source/ui/cctrl/dpcontrol.cxx | 20 -------------------- 1 file changed, 20 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 185671b3af97..945fd0b1e358 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -770,8 +770,6 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy const sal_uInt16 nTopMargin = 5; const sal_uInt16 nMenuHeight = 60; const sal_uInt16 nBottomBtnAreaHeight = 50; - const sal_uInt16 nInnerItemMargin = 5; - const sal_uInt16 nScrollBarWidth = 17; const sal_uInt16 nBtnWidth = 60; const sal_uInt16 nBtnHeight = getLabelFont().GetHeight()*2; const sal_uInt16 nBottomMargin = 10; @@ -804,15 +802,6 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight - nListBoxInnerPadding*2); } break; - case FIRST_LISTITEM: - { - rPos = Point(nListBoxMargin + nInnerItemMargin, - nTopMargin + nMenuHeight + nMenuListMargin + nInnerItemMargin); - rSize = Size( - aWndSize.Width() - nListBoxMargin*2 - nInnerItemMargin - nScrollBarWidth - 10, - 17); - } - break; case BTN_OK: { long x = (aWndSize.Width() - nBtnWidth*2)/3; @@ -829,15 +818,6 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy rSize = Size(nBtnWidth, nBtnHeight); } break; - case SCROLL_BAR_V: - { - long x = aWndSize.Width() - nListBoxMargin - nInnerItemMargin - nScrollBarWidth; - long y = nTopMargin + nMenuHeight + nMenuListMargin + nInnerItemMargin; - rPos = Point(x, y); - long h = aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight - nInnerItemMargin*2; - rSize = Size(nScrollBarWidth, h); - } - break; default: ; } -- cgit From e5fb7fa24c796e7e608e6aa392ef8fb1900a4ee7 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 30 Jul 2009 23:10:58 +0000 Subject: removed unused method. --- sc/source/ui/cctrl/dpcontrol.cxx | 5 ----- 1 file changed, 5 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 945fd0b1e358..9365a923dc44 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -758,11 +758,6 @@ ScDPFieldPopupWindow::~ScDPFieldPopupWindow() { } -vector& ScDPFieldPopupWindow::getMembers() -{ - return maMembers; -} - void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionType eType) const { const sal_uInt16 nListBoxMargin = 5; -- cgit From 69e8adefda15685dc09b7af00fd6743c1937c4c7 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 31 Jul 2009 02:57:58 +0000 Subject: Implemented "toggle all" check box per IBM's spec. --- sc/source/ui/cctrl/dpcontrol.cxx | 138 +++++++++++++++++++++++++++++++++++---- 1 file changed, 124 insertions(+), 14 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 9365a923dc44..18cc9089e108 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -34,11 +34,13 @@ // INCLUDE --------------------------------------------------------------- #include "dpcontrol.hxx" +#include "dpcontrol.hrc" #include "vcl/outdev.hxx" #include "vcl/settings.hxx" #include "vcl/wintypes.hxx" #include "vcl/decoview.hxx" +#include "strload.hxx" #define MENU_NOT_SELECTED 999 @@ -725,12 +727,15 @@ void ScDPFieldPopupWindow::CancelButton::Click() ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : ScMenuFloatingWindow(pParent), maChecks(this, 0), + maChkToggleAll(this, 0), maBtnOk(this), maBtnCancel(this), mpExtendedData(NULL), mpOKAction(NULL), - mnScrollPos(0) + mePrevToggleAllState(STATE_DONTKNOW) { + const StyleSettings& rStyle = GetSettings().GetStyleSettings(); + Point aPos; Size aSize; getSectionPosSize(aPos, aSize, WHOLE); @@ -751,7 +756,16 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : getSectionPosSize(aPos, aSize, LISTBOX_AREA_INNER); maChecks.SetPosSizePixel(aPos, aSize); maChecks.SetFont(getLabelFont()); + maChecks.SetCheckButtonHdl( LINK(this, ScDPFieldPopupWindow, CheckHdl) ); maChecks.Show(); + + getSectionPosSize(aPos, aSize, CHECK_TOGGLE_ALL); + maChkToggleAll.SetPosSizePixel(aPos, aSize); + maChkToggleAll.SetFont(getLabelFont()); + maChkToggleAll.SetText(ScRscStrLoader(RID_POPUP_FILTER, STR_BTN_TOGGLE_ALL).GetString()); + maChkToggleAll.SetControlBackground(rStyle.GetMenuColor()); + maChkToggleAll.SetClickHdl( LINK(this, ScDPFieldPopupWindow, TriStateHdl) ); + maChkToggleAll.Show(); } ScDPFieldPopupWindow::~ScDPFieldPopupWindow() @@ -760,18 +774,28 @@ ScDPFieldPopupWindow::~ScDPFieldPopupWindow() void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionType eType) const { - const sal_uInt16 nListBoxMargin = 5; + // constant parameters. + const sal_uInt16 nListBoxMargin = 5; // horizontal distance from the side of the dialog to the listbox border. const sal_uInt16 nListBoxInnerPadding = 5; const sal_uInt16 nTopMargin = 5; const sal_uInt16 nMenuHeight = 60; - const sal_uInt16 nBottomBtnAreaHeight = 50; + const sal_uInt16 nSingleItemBtnAreaHeight = 30; // height of the middle area below the list box where the single-action buttons are. + const sal_uInt16 nBottomBtnAreaHeight = 50; // height of the bottom area where the OK and Cancel buttons are. const sal_uInt16 nBtnWidth = 60; - const sal_uInt16 nBtnHeight = getLabelFont().GetHeight()*2; + const sal_uInt16 nLabelHeight = getLabelFont().GetHeight(); + const sal_uInt16 nBtnHeight = nLabelHeight*2; const sal_uInt16 nBottomMargin = 10; const sal_uInt16 nMenuListMargin = 20; Size aWndSize = Size(160, 330); + // parameters calculated from constants. + const sal_uInt16 nListBoxWidth = aWndSize.Width() - nListBoxMargin*2; + const sal_uInt16 nListBoxHeight = aWndSize.Height() - nTopMargin - nMenuHeight - + nMenuListMargin - nSingleItemBtnAreaHeight - nBottomBtnAreaHeight; + + const sal_uInt16 nSingleBtnAreaY = nTopMargin + nMenuHeight + nListBoxHeight + nMenuListMargin - 1; + switch (eType) { case WHOLE: @@ -783,18 +807,33 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy case LISTBOX_AREA_OUTER: { rPos = Point(nListBoxMargin, nTopMargin + nMenuHeight + nMenuListMargin); - rSize = Size( - aWndSize.Width() - nListBoxMargin*2, - aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight); + rSize = Size(nListBoxWidth, nListBoxHeight); } break; case LISTBOX_AREA_INNER: { - rPos = Point(nListBoxMargin + nListBoxInnerPadding, - nTopMargin + nMenuHeight + nMenuListMargin + nListBoxInnerPadding); - rSize = Size( - aWndSize.Width() - nListBoxMargin*2 - nListBoxInnerPadding*2, - aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight - nListBoxInnerPadding*2); + rPos = Point(nListBoxMargin, nTopMargin + nMenuHeight + nMenuListMargin); + rPos.X() += nListBoxInnerPadding; + rPos.Y() += nListBoxInnerPadding; + + rSize = Size(nListBoxWidth, nListBoxHeight); + rSize.Width() -= nListBoxInnerPadding*2; + rSize.Height() -= nListBoxInnerPadding*2; + } + break; + case SINGLE_BTN_AREA: + { + rPos = Point(nListBoxMargin, nSingleBtnAreaY); + rSize = Size(nListBoxWidth, nSingleItemBtnAreaHeight); + } + break; + case CHECK_TOGGLE_ALL: + { + long h = nLabelHeight*3/2; // check box height is heuristically 150% of the text height. + rPos = Point(nListBoxMargin, nSingleBtnAreaY); + rPos.X() += 5; + rPos.Y() += (nSingleItemBtnAreaHeight - h)/2; + rSize = Size(70, h); } break; case BTN_OK: @@ -818,12 +857,58 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy } } +void ScDPFieldPopupWindow::setAllMemberState(bool bSet) +{ + size_t n = maMembers.size(); + for (size_t i = 0; i < n; ++i) + maChecks.CheckEntryPos(i, bSet); +} + IMPL_LINK( ScDPFieldPopupWindow, OKButtonHdl, OKButton*, EMPTYARG ) { close(true); return 0; } +IMPL_LINK( ScDPFieldPopupWindow, TriStateHdl, TriStateBox*, EMPTYARG ) +{ + switch (mePrevToggleAllState) + { + case STATE_NOCHECK: + maChkToggleAll.SetState(STATE_CHECK); + setAllMemberState(true); + break; + case STATE_CHECK: + maChkToggleAll.SetState(STATE_NOCHECK); + setAllMemberState(false); + break; + case STATE_DONTKNOW: + default: + maChkToggleAll.SetState(STATE_CHECK); + setAllMemberState(true); + break; + } + + mePrevToggleAllState = maChkToggleAll.GetState(); + return 0; +} + +IMPL_LINK( ScDPFieldPopupWindow, CheckHdl, SvTreeListBox*, EMPTYARG ) +{ + size_t nNumChecked = maChecks.GetCheckedEntryCount(); + if (nNumChecked == maMembers.size()) + // all members visible + maChkToggleAll.SetState(STATE_CHECK); + else if (nNumChecked == 0) + // no members visible + maChkToggleAll.SetState(STATE_NOCHECK); + else + maChkToggleAll.SetState(STATE_DONTKNOW); + + mePrevToggleAllState = maChkToggleAll.GetState(); + return 0; +} + void ScDPFieldPopupWindow::MouseMove(const MouseEvent& rMEvt) { ScMenuFloatingWindow::MouseMove(rMEvt); @@ -849,6 +934,11 @@ void ScDPFieldPopupWindow::Paint(const Rectangle& rRect) SetFillColor(aMemberBackColor); SetLineColor(aBorderColor); DrawRect(Rectangle(aPos,aSize)); + + // Single-action button box + getSectionPosSize(aPos, aSize, SINGLE_BTN_AREA); + SetFillColor(rStyle.GetMenuColor()); + DrawRect(Rectangle(aPos,aSize)); } void ScDPFieldPopupWindow::setMemberSize(size_t n) @@ -866,11 +956,31 @@ void ScDPFieldPopupWindow::addMember(const OUString& rName, bool bVisible) void ScDPFieldPopupWindow::initMembers() { - size_t nMemCount = maMembers.size(); - for (size_t i = 0; i < nMemCount; ++i) + size_t n = maMembers.size(); + size_t nVisMemCount = 0; + for (size_t i = 0; i < n; ++i) { maChecks.InsertEntry(maMembers[i].maName); maChecks.CheckEntryPos(i, maMembers[i].mbVisible); + if (maMembers[i].mbVisible) + ++nVisMemCount; + } + if (nVisMemCount == n) + { + // all members visible + maChkToggleAll.SetState(STATE_CHECK); + mePrevToggleAllState = STATE_CHECK; + } + else if (nVisMemCount == 0) + { + // no members visible + maChkToggleAll.SetState(STATE_NOCHECK); + mePrevToggleAllState = STATE_NOCHECK; + } + else + { + maChkToggleAll.SetState(STATE_DONTKNOW); + mePrevToggleAllState = STATE_DONTKNOW; } } -- cgit From 8dca6ccdde0d337c113217562c3a9f594ddbc155 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 31 Jul 2009 04:56:38 +0000 Subject: Implemented single-select buttons. It's fully functional. --- sc/source/ui/cctrl/dpcontrol.cxx | 52 ++++++++++++++++++++++++++++++++++++---- 1 file changed, 48 insertions(+), 4 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 18cc9089e108..848d0c60250c 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -728,6 +728,8 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : ScMenuFloatingWindow(pParent), maChecks(this, 0), maChkToggleAll(this, 0), + maBtnSelectSingle (this, 0), + maBtnUnselectSingle(this, 0), maBtnOk(this), maBtnCancel(this), mpExtendedData(NULL), @@ -745,7 +747,7 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : getSectionPosSize(aPos, aSize, BTN_OK); maBtnOk.SetPosSizePixel(aPos, aSize); maBtnOk.SetFont(getLabelFont()); - maBtnOk.SetClickHdl( LINK(this, ScDPFieldPopupWindow, OKButtonHdl) ); + maBtnOk.SetClickHdl( LINK(this, ScDPFieldPopupWindow, ButtonHdl) ); maBtnOk.Show(); getSectionPosSize(aPos, aSize, BTN_CANCEL); @@ -766,6 +768,18 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : maChkToggleAll.SetControlBackground(rStyle.GetMenuColor()); maChkToggleAll.SetClickHdl( LINK(this, ScDPFieldPopupWindow, TriStateHdl) ); maChkToggleAll.Show(); + + getSectionPosSize(aPos, aSize, BTN_SINGLE_SELECT); + maBtnSelectSingle.SetPosSizePixel(aPos, aSize); + maBtnSelectSingle.SetModeImage(Image(ScResId(RID_IMG_SELECT_CURRENT)), BMP_COLOR_NORMAL); + maBtnSelectSingle.SetClickHdl( LINK(this, ScDPFieldPopupWindow, ButtonHdl) ); + maBtnSelectSingle.Show(); + + getSectionPosSize(aPos, aSize, BTN_SINGLE_UNSELECT); + maBtnUnselectSingle.SetPosSizePixel(aPos, aSize); + maBtnUnselectSingle.SetModeImage(Image(ScResId(RID_IMG_UNSELECT_CURRENT)), BMP_COLOR_NORMAL); + maBtnUnselectSingle.SetClickHdl( LINK(this, ScDPFieldPopupWindow, ButtonHdl) ); + maBtnUnselectSingle.Show(); } ScDPFieldPopupWindow::~ScDPFieldPopupWindow() @@ -779,7 +793,7 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy const sal_uInt16 nListBoxInnerPadding = 5; const sal_uInt16 nTopMargin = 5; const sal_uInt16 nMenuHeight = 60; - const sal_uInt16 nSingleItemBtnAreaHeight = 30; // height of the middle area below the list box where the single-action buttons are. + const sal_uInt16 nSingleItemBtnAreaHeight = 32; // height of the middle area below the list box where the single-action buttons are. const sal_uInt16 nBottomBtnAreaHeight = 50; // height of the bottom area where the OK and Cancel buttons are. const sal_uInt16 nBtnWidth = 60; const sal_uInt16 nLabelHeight = getLabelFont().GetHeight(); @@ -836,6 +850,24 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy rSize = Size(70, h); } break; + case BTN_SINGLE_SELECT: + { + long h = 26; + rPos = Point(nListBoxMargin, nSingleBtnAreaY); + rPos.X() += 75; + rPos.Y() += (nSingleItemBtnAreaHeight - h)/2; + rSize = Size(h, h); + } + break; + case BTN_SINGLE_UNSELECT: + { + long h = 26; + rPos = Point(nListBoxMargin, nSingleBtnAreaY); + rPos.X() += 75 + h + 10; + rPos.Y() += (nSingleItemBtnAreaHeight - h)/2; + rSize = Size(h, h); + } + break; case BTN_OK: { long x = (aWndSize.Width() - nBtnWidth*2)/3; @@ -864,9 +896,21 @@ void ScDPFieldPopupWindow::setAllMemberState(bool bSet) maChecks.CheckEntryPos(i, bSet); } -IMPL_LINK( ScDPFieldPopupWindow, OKButtonHdl, OKButton*, EMPTYARG ) +void ScDPFieldPopupWindow::selectCurrentMemberOnly(bool bSet) +{ + setAllMemberState(!bSet); + sal_uInt16 nSelected = maChecks.GetSelectEntryPos(); + maChecks.CheckEntryPos(nSelected, bSet); +} + +IMPL_LINK( ScDPFieldPopupWindow, ButtonHdl, Button*, pBtn ) { - close(true); + if (pBtn == &maBtnOk) + close(true); + else if (pBtn == &maBtnSelectSingle) + selectCurrentMemberOnly(true); + else if (pBtn == &maBtnUnselectSingle) + selectCurrentMemberOnly(false); return 0; } -- cgit From 10607279f3091b644156ed82f651fc9d3ce8372d Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 31 Jul 2009 05:09:14 +0000 Subject: Quick help strings for the single-selection buttons per spec from IBM. --- sc/source/ui/cctrl/dpcontrol.cxx | 2 ++ 1 file changed, 2 insertions(+) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 848d0c60250c..bc36abb7d182 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -771,12 +771,14 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : getSectionPosSize(aPos, aSize, BTN_SINGLE_SELECT); maBtnSelectSingle.SetPosSizePixel(aPos, aSize); + maBtnSelectSingle.SetQuickHelpText(ScRscStrLoader(RID_POPUP_FILTER, STR_BTN_SELECT_CURRENT).GetString()); maBtnSelectSingle.SetModeImage(Image(ScResId(RID_IMG_SELECT_CURRENT)), BMP_COLOR_NORMAL); maBtnSelectSingle.SetClickHdl( LINK(this, ScDPFieldPopupWindow, ButtonHdl) ); maBtnSelectSingle.Show(); getSectionPosSize(aPos, aSize, BTN_SINGLE_UNSELECT); maBtnUnselectSingle.SetPosSizePixel(aPos, aSize); + maBtnUnselectSingle.SetQuickHelpText(ScRscStrLoader(RID_POPUP_FILTER, STR_BTN_UNSELECT_CURRENT).GetString()); maBtnUnselectSingle.SetModeImage(Image(ScResId(RID_IMG_UNSELECT_CURRENT)), BMP_COLOR_NORMAL); maBtnUnselectSingle.SetClickHdl( LINK(this, ScDPFieldPopupWindow, ButtonHdl) ); maBtnUnselectSingle.Show(); -- cgit From fef2f67ef7f3d49cc5b9bab8b2f21e2004cdfb16 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 31 Jul 2009 05:14:59 +0000 Subject: Don't forget to update the toggle-all check box after each single selection. --- sc/source/ui/cctrl/dpcontrol.cxx | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index bc36abb7d182..2edfc2a91e05 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -910,9 +910,15 @@ IMPL_LINK( ScDPFieldPopupWindow, ButtonHdl, Button*, pBtn ) if (pBtn == &maBtnOk) close(true); else if (pBtn == &maBtnSelectSingle) + { selectCurrentMemberOnly(true); + CheckHdl(&maChecks); + } else if (pBtn == &maBtnUnselectSingle) + { selectCurrentMemberOnly(false); + CheckHdl(&maChecks); + } return 0; } @@ -939,8 +945,11 @@ IMPL_LINK( ScDPFieldPopupWindow, TriStateHdl, TriStateBox*, EMPTYARG ) return 0; } -IMPL_LINK( ScDPFieldPopupWindow, CheckHdl, SvTreeListBox*, EMPTYARG ) +IMPL_LINK( ScDPFieldPopupWindow, CheckHdl, SvTreeListBox*, pChecks ) { + if (pChecks != &maChecks) + return 0; + size_t nNumChecked = maChecks.GetCheckedEntryCount(); if (nNumChecked == maMembers.size()) // all members visible -- cgit From 05b32c409e8984e3e24ee2a20d4bc21683f0b600 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 31 Jul 2009 19:21:20 +0000 Subject: Draw black border around the popup arrow. It looks better this way. --- sc/source/ui/cctrl/dpcontrol.cxx | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 2edfc2a91e05..726c6dd660bd 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -144,16 +144,21 @@ void ScDPFieldButton::drawPopupButton() Size aSize; getPopupBoundingBox(aPos, aSize); + // outer black border + mpOutDev->SetLineColor(COL_BLACK); + mpOutDev->SetFillColor(); + mpOutDev->DrawRect(Rectangle(aPos, aSize)); + // border lines mpOutDev->SetLineColor(mpStyle->GetLightColor()); - mpOutDev->DrawLine(aPos, Point(aPos.X(), aPos.Y()+aSize.Height()-1)); - mpOutDev->DrawLine(aPos, Point(aPos.X()+aSize.Width()-1, aPos.Y())); + mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+1), Point(aPos.X()+1, aPos.Y()+aSize.Height()-2)); + mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+1), Point(aPos.X()+aSize.Width()-2, aPos.Y()+1)); mpOutDev->SetLineColor(mpStyle->GetShadowColor()); - mpOutDev->DrawLine(Point(aPos.X(), aPos.Y()+aSize.Height()-1), - Point(aPos.X()+aSize.Width()-1, aPos.Y()+aSize.Height()-1)); - mpOutDev->DrawLine(Point(aPos.X()+aSize.Width()-1, aPos.Y()), - Point(aPos.X()+aSize.Width()-1, aPos.Y()+aSize.Height()-1)); + mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+aSize.Height()-2), + Point(aPos.X()+aSize.Width()-2, aPos.Y()+aSize.Height()-2)); + mpOutDev->DrawLine(Point(aPos.X()+aSize.Width()-2, aPos.Y()+1), + Point(aPos.X()+aSize.Width()-2, aPos.Y()+aSize.Height()-2)); // the arrowhead Color aArrowColor = mbHasHiddenMember ? mpStyle->GetHighlightLinkColor() : mpStyle->GetButtonTextColor(); -- cgit From ba3f18f4ab3a93264fd67ce956dfad96e74249f5 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 31 Jul 2009 19:47:48 +0000 Subject: Draw the autofilter arrow button the same way as the field popup button. This will temporarily break autofilter's push animation and mouse pointer hit analysis. Also made the popup button a little wider. --- sc/source/ui/cctrl/dpcontrol.cxx | 71 ++++++++++++++++++++++------------------ 1 file changed, 40 insertions(+), 31 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 726c6dd660bd..db05af97b8df 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -52,6 +52,7 @@ using ::std::hash_map; ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle) : mpOutDev(pOutDev), mpStyle(pStyle), + mbBaseButton(true), mbPopupButton(false), mbHasHiddenMember(false) { @@ -72,6 +73,11 @@ void ScDPFieldButton::setBoundingBox(const Point& rPos, const Size& rSize) maSize = rSize; } +void ScDPFieldButton::setDrawBaseButton(bool b) +{ + mbBaseButton = b; +} + void ScDPFieldButton::setDrawPopupButton(bool b) { mbPopupButton = b; @@ -86,33 +92,36 @@ void ScDPFieldButton::draw() { const long nMargin = 2; - // Background - Rectangle aRect(maPos, maSize); - mpOutDev->SetLineColor(mpStyle->GetFaceColor()); - mpOutDev->SetFillColor(mpStyle->GetFaceColor()); - mpOutDev->DrawRect(aRect); - - // Border lines - mpOutDev->SetLineColor(mpStyle->GetLightColor()); - mpOutDev->DrawLine(Point(maPos), Point(maPos.X(), maPos.Y()+maSize.Height()-1)); - mpOutDev->DrawLine(Point(maPos), Point(maPos.X()+maSize.Width()-1, maPos.Y())); - - mpOutDev->SetLineColor(mpStyle->GetShadowColor()); - mpOutDev->DrawLine(Point(maPos.X(), maPos.Y()+maSize.Height()-1), - Point(maPos.X()+maSize.Width()-1, maPos.Y()+maSize.Height()-1)); - mpOutDev->DrawLine(Point(maPos.X()+maSize.Width()-1, maPos.Y()), - Point(maPos.X()+maSize.Width()-1, maPos.Y()+maSize.Height()-1)); - - // Field name - Font aTextFont( mpStyle->GetLabelFont() ); - aTextFont.SetHeight(12); - mpOutDev->SetFont(aTextFont); - - Point aTextPos = maPos; - long nTHeight = mpOutDev->GetTextHeight(); - aTextPos.setX(maPos.getX() + nMargin); - aTextPos.setY(maPos.getY() + (maSize.Height()-nTHeight)/2); - mpOutDev->DrawText(aTextPos, maText); + if (mbBaseButton) + { + // Background + Rectangle aRect(maPos, maSize); + mpOutDev->SetLineColor(mpStyle->GetFaceColor()); + mpOutDev->SetFillColor(mpStyle->GetFaceColor()); + mpOutDev->DrawRect(aRect); + + // Border lines + mpOutDev->SetLineColor(mpStyle->GetLightColor()); + mpOutDev->DrawLine(Point(maPos), Point(maPos.X(), maPos.Y()+maSize.Height()-1)); + mpOutDev->DrawLine(Point(maPos), Point(maPos.X()+maSize.Width()-1, maPos.Y())); + + mpOutDev->SetLineColor(mpStyle->GetShadowColor()); + mpOutDev->DrawLine(Point(maPos.X(), maPos.Y()+maSize.Height()-1), + Point(maPos.X()+maSize.Width()-1, maPos.Y()+maSize.Height()-1)); + mpOutDev->DrawLine(Point(maPos.X()+maSize.Width()-1, maPos.Y()), + Point(maPos.X()+maSize.Width()-1, maPos.Y()+maSize.Height()-1)); + + // Field name + Font aTextFont( mpStyle->GetLabelFont() ); + aTextFont.SetHeight(12); + mpOutDev->SetFont(aTextFont); + + Point aTextPos = maPos; + long nTHeight = mpOutDev->GetTextHeight(); + aTextPos.setX(maPos.getX() + nMargin); + aTextPos.setY(maPos.getY() + (maSize.Height()-nTHeight)/2); + mpOutDev->DrawText(aTextPos, maText); + } if (mbPopupButton) drawPopupButton(); @@ -122,8 +131,8 @@ void ScDPFieldButton::getPopupBoundingBox(Point& rPos, Size& rSize) const { long nW = maSize.getWidth()*0.5; long nH = maSize.getHeight(); - if (nW > 16) - nW = 16; + if (nW > 18) + nW = 18; if (nH > 18) nH = 18; @@ -144,9 +153,9 @@ void ScDPFieldButton::drawPopupButton() Size aSize; getPopupBoundingBox(aPos, aSize); - // outer black border + // Background & outer black border mpOutDev->SetLineColor(COL_BLACK); - mpOutDev->SetFillColor(); + mpOutDev->SetFillColor(mpStyle->GetFaceColor()); mpOutDev->DrawRect(Rectangle(aPos, aSize)); // border lines -- cgit From 41eedbe32033a7d11c1027a5561f46453324d105 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Sat, 1 Aug 2009 01:27:21 +0000 Subject: Button pressing animation for autofilter buttons. --- sc/source/ui/cctrl/dpcontrol.cxx | 46 +++++++++++++++++++++++++++++++--------- 1 file changed, 36 insertions(+), 10 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index db05af97b8df..2239a4c96a2c 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -54,7 +54,8 @@ ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pSt mpStyle(pStyle), mbBaseButton(true), mbPopupButton(false), - mbHasHiddenMember(false) + mbHasHiddenMember(false), + mbPopupPressed(false) { } @@ -88,9 +89,16 @@ void ScDPFieldButton::setHasHiddenMember(bool b) mbHasHiddenMember = b; } +void ScDPFieldButton::setPopupPressed(bool b) +{ + mbPopupPressed = b; +} + void ScDPFieldButton::draw() { const long nMargin = 2; + bool bOldMapEnablaed = mpOutDev->IsMapModeEnabled(); + mpOutDev->EnableMapMode(false); if (mbBaseButton) { @@ -125,6 +133,8 @@ void ScDPFieldButton::draw() if (mbPopupButton) drawPopupButton(); + + mpOutDev->EnableMapMode(bOldMapEnablaed); } void ScDPFieldButton::getPopupBoundingBox(Point& rPos, Size& rSize) const @@ -158,16 +168,19 @@ void ScDPFieldButton::drawPopupButton() mpOutDev->SetFillColor(mpStyle->GetFaceColor()); mpOutDev->DrawRect(Rectangle(aPos, aSize)); - // border lines - mpOutDev->SetLineColor(mpStyle->GetLightColor()); - mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+1), Point(aPos.X()+1, aPos.Y()+aSize.Height()-2)); - mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+1), Point(aPos.X()+aSize.Width()-2, aPos.Y()+1)); + if (!mbPopupPressed) + { + // border lines + mpOutDev->SetLineColor(mpStyle->GetLightColor()); + mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+1), Point(aPos.X()+1, aPos.Y()+aSize.Height()-2)); + mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+1), Point(aPos.X()+aSize.Width()-2, aPos.Y()+1)); - mpOutDev->SetLineColor(mpStyle->GetShadowColor()); - mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+aSize.Height()-2), - Point(aPos.X()+aSize.Width()-2, aPos.Y()+aSize.Height()-2)); - mpOutDev->DrawLine(Point(aPos.X()+aSize.Width()-2, aPos.Y()+1), - Point(aPos.X()+aSize.Width()-2, aPos.Y()+aSize.Height()-2)); + mpOutDev->SetLineColor(mpStyle->GetShadowColor()); + mpOutDev->DrawLine(Point(aPos.X()+1, aPos.Y()+aSize.Height()-2), + Point(aPos.X()+aSize.Width()-2, aPos.Y()+aSize.Height()-2)); + mpOutDev->DrawLine(Point(aPos.X()+aSize.Width()-2, aPos.Y()+1), + Point(aPos.X()+aSize.Width()-2, aPos.Y()+aSize.Height()-2)); + } // the arrowhead Color aArrowColor = mbHasHiddenMember ? mpStyle->GetHighlightLinkColor() : mpStyle->GetButtonTextColor(); @@ -180,6 +193,14 @@ void ScDPFieldButton::drawPopupButton() aPos1.Y() = aCenter.Y() - 3; aPos2.Y() = aCenter.Y() - 3; + if (mbPopupPressed) + { + aPos1.X() += 1; + aPos2.X() += 1; + aPos1.Y() += 1; + aPos2.Y() += 1; + } + do { ++aPos1.X(); @@ -194,6 +215,11 @@ void ScDPFieldButton::drawPopupButton() { // tiny little box to display in presence of hidden member(s). Point aBoxPos(aPos.X() + aSize.Width() - 5, aPos.Y() + aSize.Height() - 5); + if (mbPopupPressed) + { + aBoxPos.X() += 1; + aBoxPos.Y() += 1; + } Size aBoxSize(3, 3); mpOutDev->DrawRect(Rectangle(aBoxPos, aBoxSize)); } -- cgit From a1f35730b44c135dbb0883e2df1ee1a817a815a2 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Mon, 3 Aug 2009 19:44:11 +0000 Subject: Fixed text zooming issue where the text was not scaling properly per current zoom level. --- sc/source/ui/cctrl/dpcontrol.cxx | 20 ++++++++++++++++---- 1 file changed, 16 insertions(+), 4 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 2239a4c96a2c..ca90e6624caa 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -48,8 +48,9 @@ using ::rtl::OUString; using ::rtl::OUStringHash; using ::std::vector; using ::std::hash_map; +using ::std::auto_ptr; -ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle) : +ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle, const Fraction* pZoomX, const Fraction* pZoomY) : mpOutDev(pOutDev), mpStyle(pStyle), mbBaseButton(true), @@ -57,6 +58,15 @@ ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pSt mbHasHiddenMember(false), mbPopupPressed(false) { + if (pZoomX) + maZoomX = *pZoomX; + else + maZoomX = Fraction(1, 1); + + if (pZoomY) + maZoomY = *pZoomY; + else + maZoomY = Fraction(1, 1); } ScDPFieldButton::~ScDPFieldButton() @@ -119,13 +129,15 @@ void ScDPFieldButton::draw() mpOutDev->DrawLine(Point(maPos.X()+maSize.Width()-1, maPos.Y()), Point(maPos.X()+maSize.Width()-1, maPos.Y()+maSize.Height()-1)); - // Field name + // Field name. Font aTextFont( mpStyle->GetLabelFont() ); - aTextFont.SetHeight(12); + double fFontHeight = 12.0; + fFontHeight *= static_cast(maZoomY.GetNumerator()) / static_cast(maZoomY.GetDenominator()); + aTextFont.SetHeight(fFontHeight); mpOutDev->SetFont(aTextFont); Point aTextPos = maPos; - long nTHeight = mpOutDev->GetTextHeight(); + long nTHeight = static_cast(fFontHeight); aTextPos.setX(maPos.getX() + nMargin); aTextPos.setY(maPos.getY() + (maSize.Height()-nTHeight)/2); mpOutDev->DrawText(aTextPos, maText); -- cgit From 8802d45ff2523326cef7bf62cee92cd3809ada86 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Mon, 3 Aug 2009 20:27:28 +0000 Subject: Launch the popup window right-aligned with the cell if the cell is wider than the width of the popup. --- sc/source/ui/cctrl/dpcontrol.cxx | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index ca90e6624caa..0060a9341ec3 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -786,6 +786,7 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : maBtnCancel(this), mpExtendedData(NULL), mpOKAction(NULL), + maWndSize(160, 330), mePrevToggleAllState(STATE_DONTKNOW) { const StyleSettings& rStyle = GetSettings().GetStyleSettings(); @@ -855,11 +856,9 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy const sal_uInt16 nBottomMargin = 10; const sal_uInt16 nMenuListMargin = 20; - Size aWndSize = Size(160, 330); - // parameters calculated from constants. - const sal_uInt16 nListBoxWidth = aWndSize.Width() - nListBoxMargin*2; - const sal_uInt16 nListBoxHeight = aWndSize.Height() - nTopMargin - nMenuHeight - + const sal_uInt16 nListBoxWidth = maWndSize.Width() - nListBoxMargin*2; + const sal_uInt16 nListBoxHeight = maWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nSingleItemBtnAreaHeight - nBottomBtnAreaHeight; const sal_uInt16 nSingleBtnAreaY = nTopMargin + nMenuHeight + nListBoxHeight + nMenuListMargin - 1; @@ -869,7 +868,7 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy case WHOLE: { rPos = Point(0, 0); - rSize = aWndSize; + rSize = maWndSize; } break; case LISTBOX_AREA_OUTER: @@ -924,16 +923,16 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy break; case BTN_OK: { - long x = (aWndSize.Width() - nBtnWidth*2)/3; - long y = aWndSize.Height() - nBottomMargin - nBtnHeight; + long x = (maWndSize.Width() - nBtnWidth*2)/3; + long y = maWndSize.Height() - nBottomMargin - nBtnHeight; rPos = Point(x, y); rSize = Size(nBtnWidth, nBtnHeight); } break; case BTN_CANCEL: { - long x = (aWndSize.Width() - nBtnWidth*2)/3*2 + nBtnWidth; - long y = aWndSize.Height() - nBottomMargin - nBtnHeight; + long x = (maWndSize.Width() - nBtnWidth*2)/3*2 + nBtnWidth; + long y = maWndSize.Height() - nBottomMargin - nBtnHeight; rPos = Point(x, y); rSize = Size(nBtnWidth, nBtnHeight); } @@ -1091,6 +1090,11 @@ void ScDPFieldPopupWindow::initMembers() } } +const Size& ScDPFieldPopupWindow::getWindowSize() const +{ + return maWndSize; +} + void ScDPFieldPopupWindow::getResult(hash_map& rResult) { typedef hash_map ResultMap; -- cgit From 9c22409f2648758e69a9de4ae49c2ba9bab24a3b Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 20 Aug 2009 04:28:30 +0000 Subject: My first cut on implementing accessibility for the new datapilot field popup window. This is still work-in-progress, with lots of debug statements everywhere. --- sc/source/ui/cctrl/dpcontrol.cxx | 229 ++++++++++++++++++++++++++++++++++++--- 1 file changed, 212 insertions(+), 17 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 0060a9341ec3..df8658eb1f6b 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -41,14 +41,86 @@ #include "vcl/wintypes.hxx" #include "vcl/decoview.hxx" #include "strload.hxx" +#include "global.hxx" + +#include "AccessibleFilterMenu.hxx" +#include "AccessibleFilterTopWindow.hxx" + +#include #define MENU_NOT_SELECTED 999 +using ::com::sun::star::uno::Reference; +using ::com::sun::star::accessibility::XAccessible; using ::rtl::OUString; using ::rtl::OUStringHash; using ::std::vector; using ::std::hash_map; using ::std::auto_ptr; +//using ::std::for_each; + + +#include +#include +#include + +namespace { + +class StackPrinter +{ +public: + explicit StackPrinter(const char* msg) : + msMsg(msg) + { + fprintf(stdout, "%s: --begin\n", msMsg.c_str()); + mfStartTime = getTime(); + } + + ~StackPrinter() + { + double fEndTime = getTime(); + fprintf(stdout, "%s: --end (duration: %g sec)\n", msMsg.c_str(), (fEndTime-mfStartTime)); + } + + void printTime(int line) const + { + double fEndTime = getTime(); + fprintf(stdout, "%s: --(%d) (duration: %g sec)\n", msMsg.c_str(), line, (fEndTime-mfStartTime)); + } + +private: + double getTime() const + { + timeval tv; + gettimeofday(&tv, NULL); + return tv.tv_sec + tv.tv_usec / 1000000.0; + } + + ::std::string msMsg; + double mfStartTime; +}; + +} + +//namespace { +// +//class AppendAccessibleMenuItems : public ::std::unary_function +//{ +//public: +// explicit AppendAccessibleMenuItems(ScAccessibleFilterMenu* pAccMenu) : +// mnPos(0), mpAccMenu(pAccMenu) {} +// +// void operator() (const ScMenuFloatingWindow::MenuItem& rItem) +// { +// mpAccMenu->appendMenuItem(rItem.maText, rItem.mbEnabled, mnPos++); +// } +// +//private: +// size_t mnPos; +// ScAccessibleFilterMenu* mpAccMenu; +//}; +// +//} ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle, const Fraction* pZoomX, const Fraction* pZoomY) : mpOutDev(pOutDev), @@ -272,16 +344,19 @@ IMPL_LINK( ScMenuFloatingWindow::SubMenuItem, TimeoutHdl, void*, EMPTYARG ) // ---------------------------------------------------------------------------- -ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent) : +ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc) : FloatingWindow(pParent, (WB_SYSTEMFLOATWIN|WB_SYSTEMWINDOW|WB_NOBORDER)), maOpenTimer(this), maCloseTimer(this), + maName(OUString::createFromAscii("ScMenuFloatingWindow")), mnSelectedMenu(MENU_NOT_SELECTED), mnClickedMenu(MENU_NOT_SELECTED), + mpDoc(pDoc), mpParentMenu(dynamic_cast(pParent)), mpActiveSubMenu(NULL), mbActionFired(false) { + fprintf(stdout, "***** ScMenuFloatingWindow::ScMenuFloatingWindow: ctor (%p) parent = %p\n", this, pParent); // TODO: How do we get the right font to use here ? const sal_uInt16 nPopupFontHeight = 12; const StyleSettings& rStyle = GetSettings().GetStyleSettings(); @@ -289,6 +364,7 @@ ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent) : maLabelFont.SetHeight(nPopupFontHeight); SetFont(maLabelFont); + SetText(OUString::createFromAscii("ScMenuFloatingWindow")); SetPopupModeEndHdl( LINK(this, ScMenuFloatingWindow, EndPopupHdl) ); } @@ -404,6 +480,30 @@ void ScMenuFloatingWindow::Paint(const Rectangle& /*rRect*/) drawAllMenuItems(); } +Reference ScMenuFloatingWindow::CreateAccessible() +{ + if (!mxAccessible.is()) + { + StackPrinter __stack_printer__("ScMenuFloatingWindow::CreateAccessible (create new)"); + Reference xAccParent = mpParentMenu ? + mpParentMenu->GetAccessible() : GetAccessibleParentWindow()->GetAccessible(); + + mxAccessible.set(new ScAccessibleFilterMenu(xAccParent, this, maName, getDoc())); + ScAccessibleFilterMenu* p = static_cast( + mxAccessible.get()); + +// for_each(maMenuItems.begin(), maMenuItems.end(), AppendAccessibleMenuItems(p)); + vector::const_iterator itr, itrBeg = maMenuItems.begin(), itrEnd = maMenuItems.end(); + for (itr = itrBeg; itr != itrEnd; ++itr) + { + size_t nPos = ::std::distance(itrBeg, itr); + p->appendMenuItem(itr->maText, itr->mbEnabled, nPos); + } + } + + return mxAccessible; +} + void ScMenuFloatingWindow::addMenuItem(const OUString& rText, bool bEnabled, Action* pAction) { MenuItem aItem; @@ -418,7 +518,8 @@ ScMenuFloatingWindow* ScMenuFloatingWindow::addSubMenuItem(const OUString& rText MenuItem aItem; aItem.maText = rText; aItem.mbEnabled = bEnabled; - aItem.mpSubMenuWin.reset(new ScMenuFloatingWindow(this)); + aItem.mpSubMenuWin.reset(new ScMenuFloatingWindow(this, mpDoc)); + aItem.mpSubMenuWin->setName(rText); maMenuItems.push_back(aItem); return aItem.mpSubMenuWin.get(); } @@ -430,7 +531,7 @@ void ScMenuFloatingWindow::drawMenuItem(size_t nPos) Point aPos; Size aSize; - getMenuItemPosSize(aPos, aSize, nPos); + getMenuItemPosSize(nPos, aPos, aSize); DecorationView aDecoView(this); long nXOffset = 5; @@ -476,17 +577,19 @@ void ScMenuFloatingWindow::executeMenu(size_t nPos) EndPopupMode(); } -void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer) +void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, bool bNotifyAccessible) { + StackPrinter __stack_printer__("******************** ScMenuFloatingWindow::setSelectedMenuItem ********************"); + fprintf(stdout, "ScMenuFloatingWindow::setSelectedMenuItem: pos = %d\n", nPos); if (mnSelectedMenu != nPos) { - selectMenuItem(mnSelectedMenu, false, bSubMenuTimer); - selectMenuItem(nPos, true, bSubMenuTimer); + selectMenuItem(mnSelectedMenu, false, bSubMenuTimer, bNotifyAccessible); + selectMenuItem(nPos, true, bSubMenuTimer, bNotifyAccessible); mnSelectedMenu = nPos; } } -size_t ScMenuFloatingWindow::getSelectedMenuItem() const +size_t ScMenuFloatingWindow::getSelectedMenuPos() const { return mnSelectedMenu; } @@ -563,7 +666,7 @@ void ScMenuFloatingWindow::launchSubMenu(bool bSetMenuPos) { Point aPos; Size aSize; - getMenuItemPosSize(aPos, aSize, maOpenTimer.mnMenuPos); + getMenuItemPosSize(maOpenTimer.mnMenuPos, aPos, aSize); ScMenuFloatingWindow* pSubMenu = maOpenTimer.mpSubMenu; if (!pSubMenu) @@ -588,6 +691,21 @@ void ScMenuFloatingWindow::endSubMenu() } } +void ScMenuFloatingWindow::fillMenuItemsToAccessible(ScAccessibleFilterMenu* pAccMenu) const +{ + vector::const_iterator itr, itrBeg = maMenuItems.begin(), itrEnd = maMenuItems.end(); + for (itr = itrBeg; itr != itrEnd; ++itr) + { + size_t nPos = ::std::distance(itrBeg, itr); + pAccMenu->appendMenuItem(itr->maText, itr->mbEnabled, nPos); + } +} + +ScDocument* ScMenuFloatingWindow::getDoc() +{ + return mpDoc; +} + void ScMenuFloatingWindow::notify(NotificationType eType) { switch (eType) @@ -608,8 +726,9 @@ void ScMenuFloatingWindow::notify(NotificationType eType) void ScMenuFloatingWindow::resetMenu(bool bSetMenuPos) { - mnSelectedMenu = bSetMenuPos ? 0 : MENU_NOT_SELECTED; resizeToFitMenuItems(); + if (bSetMenuPos) + setSelectedMenuItem(0, false, true); } void ScMenuFloatingWindow::resizeToFitMenuItems() @@ -625,14 +744,15 @@ void ScMenuFloatingWindow::resizeToFitMenuItems() size_t nLastPos = maMenuItems.size()-1; Point aPos; Size aSize; - getMenuItemPosSize(aPos, aSize, nLastPos); + getMenuItemPosSize(nLastPos, aPos, aSize); aPos.X() += nTextWidth + 15; aPos.Y() += aSize.Height() + 5; SetOutputSizePixel(Size(aPos.X(), aPos.Y())); } -void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer) +void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer, bool bNotifyAccessible) { + fprintf(stdout, "ScMenuFloatingWindow::selectMenuItem: pos = %d selected = %d\n", nPos, bSelected); if (nPos >= maMenuItems.size() || nPos == MENU_NOT_SELECTED) { queueCloseSubMenu(); @@ -663,6 +783,64 @@ void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSub queueCloseSubMenu(); } } + + if (bNotifyAccessible && mxAccessible.is()) + { + ScAccessibleFilterMenu* p = static_cast(mxAccessible.get()); + p->selectMenuItem(nPos, bSelected); + } +} + +void ScMenuFloatingWindow::clearSelectedMenuItem(bool bNotifyAccessible) +{ + selectMenuItem(mnSelectedMenu, false, false, bNotifyAccessible); + + if (bNotifyAccessible && mxAccessible.is()) + { + ScAccessibleFilterMenu* p = static_cast(mxAccessible.get()); + p->selectMenuItem(mnSelectedMenu, false); + } + + mnSelectedMenu = MENU_NOT_SELECTED; +} + +ScMenuFloatingWindow* ScMenuFloatingWindow::getSubMenuWindow(size_t nPos) const +{ + if (maMenuItems.size() <= nPos) + return NULL; + + return maMenuItems[nPos].mpSubMenuWin.get(); +} + +size_t ScMenuFloatingWindow::getMenuItemCount() const +{ + return maMenuItems.size(); +} + +OUString ScMenuFloatingWindow::getMenuItemName(size_t nPos) const +{ + if (maMenuItems.size() <= nPos) + return ScGlobal::GetEmptyString(); + + return maMenuItems[nPos].maText; +} + +bool ScMenuFloatingWindow::isMenuItemEnabled(size_t nPos) const +{ + if (maMenuItems.size() <= nPos) + return false; + + return maMenuItems[nPos].mbEnabled; +} + +void ScMenuFloatingWindow::setName(const OUString& rName) +{ + maName = rName; +} + +const OUString& ScMenuFloatingWindow::getName() const +{ + return maName; } void ScMenuFloatingWindow::highlightMenuItem(size_t nPos, bool bSelected) @@ -674,7 +852,7 @@ void ScMenuFloatingWindow::highlightMenuItem(size_t nPos, bool bSelected) Point aPos; Size aSize; - getMenuItemPosSize(aPos, aSize, nPos); + getMenuItemPosSize(nPos, aPos, aSize); Region aRegion(Rectangle(aPos,aSize)); if (IsNativeControlSupported(CTRL_MENU_POPUP, PART_ENTIRE_CONTROL)) @@ -717,7 +895,7 @@ void ScMenuFloatingWindow::highlightMenuItem(size_t nPos, bool bSelected) drawMenuItem(nPos); } -void ScMenuFloatingWindow::getMenuItemPosSize(Point& rPos, Size& rSize, size_t nPos) const +void ScMenuFloatingWindow::getMenuItemPosSize(size_t nPos, Point& rPos, Size& rSize) const { const sal_uInt16 nLeftMargin = 5; const sal_uInt16 nTopMargin = 5; @@ -740,7 +918,7 @@ size_t ScMenuFloatingWindow::getEnclosingMenuItem(const Point& rPos) const { Point aPos; Size aSize; - getMenuItemPosSize(aPos, aSize, i); + getMenuItemPosSize(i, aPos, aSize); Rectangle aRect(aPos, aSize); if (aRect.IsInside(rPos)) return i; @@ -776,8 +954,8 @@ void ScDPFieldPopupWindow::CancelButton::Click() // ---------------------------------------------------------------------------- -ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) : - ScMenuFloatingWindow(pParent), +ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent, ScDocument* pDoc) : + ScMenuFloatingWindow(pParent, pDoc), maChecks(this, 0), maChkToggleAll(this, 0), maBtnSelectSingle (this, 0), @@ -1019,7 +1197,7 @@ void ScDPFieldPopupWindow::MouseMove(const MouseEvent& rMEvt) { ScMenuFloatingWindow::MouseMove(rMEvt); - size_t nSelectedMenu = getSelectedMenuItem(); + size_t nSelectedMenu = getSelectedMenuPos(); if (nSelectedMenu == MENU_NOT_SELECTED) queueCloseSubMenu(); } @@ -1047,6 +1225,23 @@ void ScDPFieldPopupWindow::Paint(const Rectangle& rRect) DrawRect(Rectangle(aPos,aSize)); } +Reference ScDPFieldPopupWindow::CreateAccessible() +{ + if (!mxAccessible.is()) + { + mxAccessible.set(new ScAccessibleFilterTopWindow( + GetAccessibleParentWindow()->GetAccessible(), this, getName(), getDoc())); + ScAccessibleFilterTopWindow* pAccTop = static_cast(mxAccessible.get()); + Reference xAccMenu = pAccTop->getAccessibleChildMenu(); + ScAccessibleFilterMenu* pAccMenu = static_cast(xAccMenu.get()); + fillMenuItemsToAccessible(pAccMenu); + + pAccTop->setAccessibleChildListBox(maChecks.CreateAccessible()); + } + + return mxAccessible; +} + void ScDPFieldPopupWindow::setMemberSize(size_t n) { maMembers.reserve(n); -- cgit From fb89c0d1df93909faeaa080359e77b1f35eed572 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 20 Aug 2009 17:36:00 +0000 Subject: Added accessible objects for the remainder of the standard widgets. --- sc/source/ui/cctrl/dpcontrol.cxx | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index df8658eb1f6b..66915b3878e7 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -1236,7 +1236,18 @@ Reference ScDPFieldPopupWindow::CreateAccessible() ScAccessibleFilterMenu* pAccMenu = static_cast(xAccMenu.get()); fillMenuItemsToAccessible(pAccMenu); - pAccTop->setAccessibleChildListBox(maChecks.CreateAccessible()); + pAccTop->setAccessibleChild( + maChecks.CreateAccessible(), ScAccessibleFilterTopWindow::LISTBOX); + pAccTop->setAccessibleChild( + maChkToggleAll.CreateAccessible(), ScAccessibleFilterTopWindow::TOGGLE_ALL); + pAccTop->setAccessibleChild( + maBtnSelectSingle.CreateAccessible(), ScAccessibleFilterTopWindow::SINGLE_ON_BTN); + pAccTop->setAccessibleChild( + maBtnUnselectSingle.CreateAccessible(), ScAccessibleFilterTopWindow::SINGLE_OFF_BTN); + pAccTop->setAccessibleChild( + maBtnOk.CreateAccessible(), ScAccessibleFilterTopWindow::OK_BTN); + pAccTop->setAccessibleChild( + maBtnCancel.CreateAccessible(), ScAccessibleFilterTopWindow::CANCEL_BTN); } return mxAccessible; -- cgit From 4a08bf44d06f9e075ae578b062c01673eb7edf97 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 20 Aug 2009 20:23:05 +0000 Subject: removed all my printf statements. --- sc/source/ui/cctrl/dpcontrol.cxx | 76 +++------------------------------------- 1 file changed, 4 insertions(+), 72 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 66915b3878e7..685ead25b47e 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -57,70 +57,6 @@ using ::rtl::OUStringHash; using ::std::vector; using ::std::hash_map; using ::std::auto_ptr; -//using ::std::for_each; - - -#include -#include -#include - -namespace { - -class StackPrinter -{ -public: - explicit StackPrinter(const char* msg) : - msMsg(msg) - { - fprintf(stdout, "%s: --begin\n", msMsg.c_str()); - mfStartTime = getTime(); - } - - ~StackPrinter() - { - double fEndTime = getTime(); - fprintf(stdout, "%s: --end (duration: %g sec)\n", msMsg.c_str(), (fEndTime-mfStartTime)); - } - - void printTime(int line) const - { - double fEndTime = getTime(); - fprintf(stdout, "%s: --(%d) (duration: %g sec)\n", msMsg.c_str(), line, (fEndTime-mfStartTime)); - } - -private: - double getTime() const - { - timeval tv; - gettimeofday(&tv, NULL); - return tv.tv_sec + tv.tv_usec / 1000000.0; - } - - ::std::string msMsg; - double mfStartTime; -}; - -} - -//namespace { -// -//class AppendAccessibleMenuItems : public ::std::unary_function -//{ -//public: -// explicit AppendAccessibleMenuItems(ScAccessibleFilterMenu* pAccMenu) : -// mnPos(0), mpAccMenu(pAccMenu) {} -// -// void operator() (const ScMenuFloatingWindow::MenuItem& rItem) -// { -// mpAccMenu->appendMenuItem(rItem.maText, rItem.mbEnabled, mnPos++); -// } -// -//private: -// size_t mnPos; -// ScAccessibleFilterMenu* mpAccMenu; -//}; -// -//} ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle, const Fraction* pZoomX, const Fraction* pZoomY) : mpOutDev(pOutDev), @@ -344,7 +280,7 @@ IMPL_LINK( ScMenuFloatingWindow::SubMenuItem, TimeoutHdl, void*, EMPTYARG ) // ---------------------------------------------------------------------------- -ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc) : +ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc, USHORT nMenuStackLevel) : FloatingWindow(pParent, (WB_SYSTEMFLOATWIN|WB_SYSTEMWINDOW|WB_NOBORDER)), maOpenTimer(this), maCloseTimer(this), @@ -356,7 +292,8 @@ ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc) : mpActiveSubMenu(NULL), mbActionFired(false) { - fprintf(stdout, "***** ScMenuFloatingWindow::ScMenuFloatingWindow: ctor (%p) parent = %p\n", this, pParent); + SetMenuStackLevel(nMenuStackLevel); + // TODO: How do we get the right font to use here ? const sal_uInt16 nPopupFontHeight = 12; const StyleSettings& rStyle = GetSettings().GetStyleSettings(); @@ -484,7 +421,6 @@ Reference ScMenuFloatingWindow::CreateAccessible() { if (!mxAccessible.is()) { - StackPrinter __stack_printer__("ScMenuFloatingWindow::CreateAccessible (create new)"); Reference xAccParent = mpParentMenu ? mpParentMenu->GetAccessible() : GetAccessibleParentWindow()->GetAccessible(); @@ -492,7 +428,6 @@ Reference ScMenuFloatingWindow::CreateAccessible() ScAccessibleFilterMenu* p = static_cast( mxAccessible.get()); -// for_each(maMenuItems.begin(), maMenuItems.end(), AppendAccessibleMenuItems(p)); vector::const_iterator itr, itrBeg = maMenuItems.begin(), itrEnd = maMenuItems.end(); for (itr = itrBeg; itr != itrEnd; ++itr) { @@ -518,7 +453,7 @@ ScMenuFloatingWindow* ScMenuFloatingWindow::addSubMenuItem(const OUString& rText MenuItem aItem; aItem.maText = rText; aItem.mbEnabled = bEnabled; - aItem.mpSubMenuWin.reset(new ScMenuFloatingWindow(this, mpDoc)); + aItem.mpSubMenuWin.reset(new ScMenuFloatingWindow(this, mpDoc, GetMenuStackLevel()+1)); aItem.mpSubMenuWin->setName(rText); maMenuItems.push_back(aItem); return aItem.mpSubMenuWin.get(); @@ -579,8 +514,6 @@ void ScMenuFloatingWindow::executeMenu(size_t nPos) void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, bool bNotifyAccessible) { - StackPrinter __stack_printer__("******************** ScMenuFloatingWindow::setSelectedMenuItem ********************"); - fprintf(stdout, "ScMenuFloatingWindow::setSelectedMenuItem: pos = %d\n", nPos); if (mnSelectedMenu != nPos) { selectMenuItem(mnSelectedMenu, false, bSubMenuTimer, bNotifyAccessible); @@ -752,7 +685,6 @@ void ScMenuFloatingWindow::resizeToFitMenuItems() void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer, bool bNotifyAccessible) { - fprintf(stdout, "ScMenuFloatingWindow::selectMenuItem: pos = %d selected = %d\n", nPos, bSelected); if (nPos >= maMenuItems.size() || nPos == MENU_NOT_SELECTED) { queueCloseSubMenu(); -- cgit From e50abfc572a020718f9460d7f836b2c514b377d0 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 21 Aug 2009 00:12:46 +0000 Subject: Let's not duplicate menu's selected state with the accessible object; we can easily query the Window instance for that. This also fixed a crasher when accessing menus from accerciser. --- sc/source/ui/cctrl/dpcontrol.cxx | 34 +++++++++++++--------------------- 1 file changed, 13 insertions(+), 21 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 685ead25b47e..541d573f4e23 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -424,7 +424,7 @@ Reference ScMenuFloatingWindow::CreateAccessible() Reference xAccParent = mpParentMenu ? mpParentMenu->GetAccessible() : GetAccessibleParentWindow()->GetAccessible(); - mxAccessible.set(new ScAccessibleFilterMenu(xAccParent, this, maName, getDoc())); + mxAccessible.set(new ScAccessibleFilterMenu(xAccParent, this, maName, 999, getDoc())); ScAccessibleFilterMenu* p = static_cast( mxAccessible.get()); @@ -512,12 +512,12 @@ void ScMenuFloatingWindow::executeMenu(size_t nPos) EndPopupMode(); } -void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, bool bNotifyAccessible) +void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer) { if (mnSelectedMenu != nPos) { - selectMenuItem(mnSelectedMenu, false, bSubMenuTimer, bNotifyAccessible); - selectMenuItem(nPos, true, bSubMenuTimer, bNotifyAccessible); + selectMenuItem(mnSelectedMenu, false, bSubMenuTimer); + selectMenuItem(nPos, true, bSubMenuTimer); mnSelectedMenu = nPos; } } @@ -661,7 +661,7 @@ void ScMenuFloatingWindow::resetMenu(bool bSetMenuPos) { resizeToFitMenuItems(); if (bSetMenuPos) - setSelectedMenuItem(0, false, true); + setSelectedMenuItem(0, false); } void ScMenuFloatingWindow::resizeToFitMenuItems() @@ -683,7 +683,7 @@ void ScMenuFloatingWindow::resizeToFitMenuItems() SetOutputSizePixel(Size(aPos.X(), aPos.Y())); } -void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer, bool bNotifyAccessible) +void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer) { if (nPos >= maMenuItems.size() || nPos == MENU_NOT_SELECTED) { @@ -715,24 +715,11 @@ void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSub queueCloseSubMenu(); } } - - if (bNotifyAccessible && mxAccessible.is()) - { - ScAccessibleFilterMenu* p = static_cast(mxAccessible.get()); - p->selectMenuItem(nPos, bSelected); - } } -void ScMenuFloatingWindow::clearSelectedMenuItem(bool bNotifyAccessible) +void ScMenuFloatingWindow::clearSelectedMenuItem() { - selectMenuItem(mnSelectedMenu, false, false, bNotifyAccessible); - - if (bNotifyAccessible && mxAccessible.is()) - { - ScAccessibleFilterMenu* p = static_cast(mxAccessible.get()); - p->selectMenuItem(mnSelectedMenu, false); - } - + selectMenuItem(mnSelectedMenu, false, false); mnSelectedMenu = MENU_NOT_SELECTED; } @@ -765,6 +752,11 @@ bool ScMenuFloatingWindow::isMenuItemEnabled(size_t nPos) const return maMenuItems[nPos].mbEnabled; } +bool ScMenuFloatingWindow::isMenuItemSelected(size_t nPos) const +{ + return nPos == mnSelectedMenu; +} + void ScMenuFloatingWindow::setName(const OUString& rName) { maName = rName; -- cgit From 4d56fc68ec3803dc6d009acaacd975f83384d5f8 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 21 Aug 2009 01:19:38 +0000 Subject: renamed structs. --- sc/source/ui/cctrl/dpcontrol.cxx | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 541d573f4e23..17f75371a306 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -247,7 +247,7 @@ void ScDPFieldButton::drawPopupButton() // ============================================================================ -ScMenuFloatingWindow::MenuItem::MenuItem() : +ScMenuFloatingWindow::MenuItemData::MenuItemData() : mbEnabled(true), mpAction(static_cast(NULL)), mpSubMenuWin(static_cast(NULL)) @@ -256,23 +256,23 @@ ScMenuFloatingWindow::MenuItem::MenuItem() : // ---------------------------------------------------------------------------- -ScMenuFloatingWindow::SubMenuItem::SubMenuItem(ScMenuFloatingWindow* pParent) : +ScMenuFloatingWindow::SubMenuItemData::SubMenuItemData(ScMenuFloatingWindow* pParent) : mpSubMenu(NULL), mnMenuPos(MENU_NOT_SELECTED), mpParent(pParent) { - maTimer.SetTimeoutHdl( LINK(this, ScMenuFloatingWindow::SubMenuItem, TimeoutHdl) ); + maTimer.SetTimeoutHdl( LINK(this, ScMenuFloatingWindow::SubMenuItemData, TimeoutHdl) ); maTimer.SetTimeout(mpParent->GetSettings().GetMouseSettings().GetMenuDelay()); } -void ScMenuFloatingWindow::SubMenuItem::reset() +void ScMenuFloatingWindow::SubMenuItemData::reset() { mpSubMenu = NULL; mnMenuPos = MENU_NOT_SELECTED; maTimer.Stop(); } -IMPL_LINK( ScMenuFloatingWindow::SubMenuItem, TimeoutHdl, void*, EMPTYARG ) +IMPL_LINK( ScMenuFloatingWindow::SubMenuItemData, TimeoutHdl, void*, EMPTYARG ) { mpParent->handleMenuTimeout(this); return 0; @@ -364,7 +364,7 @@ void ScMenuFloatingWindow::KeyInput(const KeyEvent& rKEvt) if (mnSelectedMenu >= maMenuItems.size() || mnSelectedMenu == MENU_NOT_SELECTED) break; - const MenuItem& rMenu = maMenuItems[mnSelectedMenu]; + const MenuItemData& rMenu = maMenuItems[mnSelectedMenu]; if (!rMenu.mbEnabled || !rMenu.mpSubMenuWin) break; @@ -428,7 +428,7 @@ Reference ScMenuFloatingWindow::CreateAccessible() ScAccessibleFilterMenu* p = static_cast( mxAccessible.get()); - vector::const_iterator itr, itrBeg = maMenuItems.begin(), itrEnd = maMenuItems.end(); + vector::const_iterator itr, itrBeg = maMenuItems.begin(), itrEnd = maMenuItems.end(); for (itr = itrBeg; itr != itrEnd; ++itr) { size_t nPos = ::std::distance(itrBeg, itr); @@ -441,7 +441,7 @@ Reference ScMenuFloatingWindow::CreateAccessible() void ScMenuFloatingWindow::addMenuItem(const OUString& rText, bool bEnabled, Action* pAction) { - MenuItem aItem; + MenuItemData aItem; aItem.maText = rText; aItem.mbEnabled = bEnabled; aItem.mpAction.reset(pAction); @@ -450,7 +450,7 @@ void ScMenuFloatingWindow::addMenuItem(const OUString& rText, bool bEnabled, Act ScMenuFloatingWindow* ScMenuFloatingWindow::addSubMenuItem(const OUString& rText, bool bEnabled) { - MenuItem aItem; + MenuItemData aItem; aItem.maText = rText; aItem.mbEnabled = bEnabled; aItem.mpSubMenuWin.reset(new ScMenuFloatingWindow(this, mpDoc, GetMenuStackLevel()+1)); @@ -527,7 +527,7 @@ size_t ScMenuFloatingWindow::getSelectedMenuPos() const return mnSelectedMenu; } -void ScMenuFloatingWindow::handleMenuTimeout(SubMenuItem* pTimer) +void ScMenuFloatingWindow::handleMenuTimeout(SubMenuItemData* pTimer) { if (pTimer == &maOpenTimer) { @@ -626,7 +626,7 @@ void ScMenuFloatingWindow::endSubMenu() void ScMenuFloatingWindow::fillMenuItemsToAccessible(ScAccessibleFilterMenu* pAccMenu) const { - vector::const_iterator itr, itrBeg = maMenuItems.begin(), itrEnd = maMenuItems.end(); + vector::const_iterator itr, itrBeg = maMenuItems.begin(), itrEnd = maMenuItems.end(); for (itr = itrBeg; itr != itrEnd; ++itr) { size_t nPos = ::std::distance(itrBeg, itr); @@ -669,7 +669,7 @@ void ScMenuFloatingWindow::resizeToFitMenuItems() if (maMenuItems.empty()) return; - vector::const_iterator itr = maMenuItems.begin(), itrEnd = maMenuItems.end(); + vector::const_iterator itr = maMenuItems.begin(), itrEnd = maMenuItems.end(); long nTextWidth = 0; for (; itr != itrEnd; ++itr) nTextWidth = ::std::max(GetTextWidth(itr->maText), nTextWidth); -- cgit From 4ac8aba5a707967c29fc19edeaf8aedc70b63097 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 21 Aug 2009 18:34:11 +0000 Subject: Ensure correct menu hierarchy when selecting an arbitrary menu item from the accessible object. --- sc/source/ui/cctrl/dpcontrol.cxx | 178 +++++++++++++++++++++++++++++++-------- 1 file changed, 143 insertions(+), 35 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 17f75371a306..10cec6fff069 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -58,6 +58,49 @@ using ::std::vector; using ::std::hash_map; using ::std::auto_ptr; + +#include +#include +#include + +namespace { + +class StackPrinter +{ +public: + explicit StackPrinter(const char* msg) : + msMsg(msg) + { + fprintf(stdout, "%s: --begin\n", msMsg.c_str()); + mfStartTime = getTime(); + } + + ~StackPrinter() + { + double fEndTime = getTime(); + fprintf(stdout, "%s: --end (duration: %g sec)\n", msMsg.c_str(), (fEndTime-mfStartTime)); + } + + void printTime(int line) const + { + double fEndTime = getTime(); + fprintf(stdout, "%s: --(%d) (duration: %g sec)\n", msMsg.c_str(), line, (fEndTime-mfStartTime)); + } + +private: + double getTime() const + { + timeval tv; + gettimeofday(&tv, NULL); + return tv.tv_sec + tv.tv_usec / 1000000.0; + } + + ::std::string msMsg; + double mfStartTime; +}; + +} + ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle, const Fraction* pZoomX, const Fraction* pZoomY) : mpOutDev(pOutDev), mpStyle(pStyle), @@ -314,7 +357,7 @@ void ScMenuFloatingWindow::MouseMove(const MouseEvent& rMEvt) { const Point& rPos = rMEvt.GetPosPixel(); size_t nSelectedMenu = getEnclosingMenuItem(rPos); - setSelectedMenuItem(nSelectedMenu); + setSelectedMenuItem(nSelectedMenu, true, false); Window::MouseMove(rMEvt); } @@ -346,14 +389,14 @@ void ScMenuFloatingWindow::KeyInput(const KeyEvent& rKEvt) nSelectedMenu = nLastMenuPos; else --nSelectedMenu; - setSelectedMenuItem(nSelectedMenu, false); + setSelectedMenuItem(nSelectedMenu, false, false); break; case KEY_DOWN: if (nSelectedMenu == MENU_NOT_SELECTED || nSelectedMenu == nLastMenuPos) nSelectedMenu = 0; else ++nSelectedMenu; - setSelectedMenuItem(nSelectedMenu, false); + setSelectedMenuItem(nSelectedMenu, false, false); break; case KEY_LEFT: if (mpParentMenu) @@ -512,14 +555,35 @@ void ScMenuFloatingWindow::executeMenu(size_t nPos) EndPopupMode(); } -void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer) +void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, bool bEnsureSubMenu) { - if (mnSelectedMenu != nPos) + StackPrinter __stack_printer__("ScMenuFloatingWindow::setSelectedMenuItem"); + if (mnSelectedMenu == nPos) + // nothing to do. + return; + + if (bEnsureSubMenu) { - selectMenuItem(mnSelectedMenu, false, bSubMenuTimer); - selectMenuItem(nPos, true, bSubMenuTimer); - mnSelectedMenu = nPos; + fprintf(stdout, "ScMenuFloatingWindow::setSelectedMenuItem: (ensuring...) selected menu = %d\n", mnSelectedMenu); + // Dismiss any child popup menu windows. + if (mnSelectedMenu < maMenuItems.size() && + maMenuItems[mnSelectedMenu].mpSubMenuWin && + maMenuItems[mnSelectedMenu].mpSubMenuWin->IsVisible()) + { + maMenuItems[mnSelectedMenu].mpSubMenuWin->ensureSubMenuNotVisible(); + } + + // The popup is not visible, yet a menu item is selected. The request + // most likely comes from the accessible object. Make sure this + // window, as well as all its parent windows are visible. + if (!IsVisible() && mpParentMenu) + mpParentMenu->ensureSubMenuVisible(this); } + + selectMenuItem(mnSelectedMenu, false, bSubMenuTimer); + selectMenuItem(nPos, true, bSubMenuTimer); + mnSelectedMenu = nPos; + fprintf(stdout, "ScMenuFloatingWindow::setSelectedMenuItem: selected menu = %d\n", mnSelectedMenu); } size_t ScMenuFloatingWindow::getSelectedMenuPos() const @@ -607,10 +671,12 @@ void ScMenuFloatingWindow::launchSubMenu(bool bSetMenuPos) sal_uInt32 nOldFlags = GetPopupModeFlags(); SetPopupModeFlags(nOldFlags | FLOATWIN_POPUPMODE_NOAPPFOCUSCLOSE); - pSubMenu->resetMenu(bSetMenuPos); + pSubMenu->resizeToFitMenuItems(); // set the size before launching the popup to get it positioned correctly. pSubMenu->StartPopupMode( Rectangle(aPos,aSize), (FLOATWIN_POPUPMODE_RIGHT | FLOATWIN_POPUPMODE_GRABFOCUS)); pSubMenu->AddPopupModeWindow(this); + if (bSetMenuPos) + pSubMenu->setSelectedMenuItem(0, false, false); // select menu item after the popup becomes fully visible. SetPopupModeFlags(nOldFlags); } @@ -639,31 +705,6 @@ ScDocument* ScMenuFloatingWindow::getDoc() return mpDoc; } -void ScMenuFloatingWindow::notify(NotificationType eType) -{ - switch (eType) - { - case SUBMENU_FOCUSED: - // Cancel any request for ending submenu. - maCloseTimer.reset(); - if (mnSelectedMenu != maOpenTimer.mnMenuPos) - { - highlightMenuItem(maOpenTimer.mnMenuPos, true); - mnSelectedMenu = maOpenTimer.mnMenuPos; - } - break; - default: - ; - } -} - -void ScMenuFloatingWindow::resetMenu(bool bSetMenuPos) -{ - resizeToFitMenuItems(); - if (bSetMenuPos) - setSelectedMenuItem(0, false); -} - void ScMenuFloatingWindow::resizeToFitMenuItems() { if (maMenuItems.empty()) @@ -702,7 +743,7 @@ void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSub if (bSelected) { if (mpParentMenu) - mpParentMenu->notify(SUBMENU_FOCUSED); + mpParentMenu->setSubMenuFocused(this); if (bSubMenuTimer) { @@ -721,6 +762,7 @@ void ScMenuFloatingWindow::clearSelectedMenuItem() { selectMenuItem(mnSelectedMenu, false, false); mnSelectedMenu = MENU_NOT_SELECTED; + fprintf(stdout, "ScMenuFloatingWindow::clearSelectedMenuItem: here\n"); } ScMenuFloatingWindow* ScMenuFloatingWindow::getSubMenuWindow(size_t nPos) const @@ -769,6 +811,9 @@ const OUString& ScMenuFloatingWindow::getName() const void ScMenuFloatingWindow::highlightMenuItem(size_t nPos, bool bSelected) { + if (nPos == MENU_NOT_SELECTED) + return; + const StyleSettings& rStyle = GetSettings().GetStyleSettings(); Color aBackColor = rStyle.GetMenuColor(); SetFillColor(aBackColor); @@ -850,6 +895,69 @@ size_t ScMenuFloatingWindow::getEnclosingMenuItem(const Point& rPos) const return MENU_NOT_SELECTED; } +size_t ScMenuFloatingWindow::getSubMenuPos(ScMenuFloatingWindow* pSubMenu) +{ + size_t n = maMenuItems.size(); + for (size_t i = 0; i < n; ++i) + { + if (maMenuItems[i].mpSubMenuWin.get() == pSubMenu) + return i; + } + return MENU_NOT_SELECTED; +} + +void ScMenuFloatingWindow::setSubMenuFocused(ScMenuFloatingWindow* pSubMenu) +{ + maCloseTimer.reset(); + size_t nMenuPos = getSubMenuPos(pSubMenu); + if (mnSelectedMenu != nMenuPos) + { + highlightMenuItem(nMenuPos, true); + mnSelectedMenu = nMenuPos; + } +} + +void ScMenuFloatingWindow::ensureSubMenuVisible(ScMenuFloatingWindow* pSubMenu) +{ + StackPrinter __stack_printer__("ScMenuFloatingWindow::ensureSubMenuVisible"); + if (mpParentMenu) + mpParentMenu->ensureSubMenuVisible(this); + + if (pSubMenu->IsVisible()) + return; + + // Find the menu position of the submenu. + size_t nMenuPos = getSubMenuPos(pSubMenu); + if (nMenuPos != MENU_NOT_SELECTED) + { + setSelectedMenuItem(nMenuPos, false, false); + + Point aPos; + Size aSize; + getMenuItemPosSize(nMenuPos, aPos, aSize); + + sal_uInt32 nOldFlags = GetPopupModeFlags(); + SetPopupModeFlags(nOldFlags | FLOATWIN_POPUPMODE_NOAPPFOCUSCLOSE); + pSubMenu->resizeToFitMenuItems(); // set the size before launching the popup to get it positioned correctly. + pSubMenu->StartPopupMode( + Rectangle(aPos,aSize), (FLOATWIN_POPUPMODE_RIGHT | FLOATWIN_POPUPMODE_GRABFOCUS)); + pSubMenu->AddPopupModeWindow(this); + SetPopupModeFlags(nOldFlags); + } +} + +void ScMenuFloatingWindow::ensureSubMenuNotVisible() +{ + if (mnSelectedMenu <= maMenuItems.size() && + maMenuItems[mnSelectedMenu].mpSubMenuWin && + maMenuItems[mnSelectedMenu].mpSubMenuWin->IsVisible()) + { + maMenuItems[mnSelectedMenu].mpSubMenuWin->ensureSubMenuNotVisible(); + } + + EndPopupMode(); +} + IMPL_LINK( ScMenuFloatingWindow, EndPopupHdl, void*, EMPTYARG ) { if (mbActionFired && mpParentMenu) -- cgit From 2a2abd3243d8c46612970595a6e6836d7e4e7f0a Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 21 Aug 2009 18:35:29 +0000 Subject: forgot to remove debug statements. --- sc/source/ui/cctrl/dpcontrol.cxx | 48 ---------------------------------------- 1 file changed, 48 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 10cec6fff069..3d51baf73a96 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -58,49 +58,6 @@ using ::std::vector; using ::std::hash_map; using ::std::auto_ptr; - -#include -#include -#include - -namespace { - -class StackPrinter -{ -public: - explicit StackPrinter(const char* msg) : - msMsg(msg) - { - fprintf(stdout, "%s: --begin\n", msMsg.c_str()); - mfStartTime = getTime(); - } - - ~StackPrinter() - { - double fEndTime = getTime(); - fprintf(stdout, "%s: --end (duration: %g sec)\n", msMsg.c_str(), (fEndTime-mfStartTime)); - } - - void printTime(int line) const - { - double fEndTime = getTime(); - fprintf(stdout, "%s: --(%d) (duration: %g sec)\n", msMsg.c_str(), line, (fEndTime-mfStartTime)); - } - -private: - double getTime() const - { - timeval tv; - gettimeofday(&tv, NULL); - return tv.tv_sec + tv.tv_usec / 1000000.0; - } - - ::std::string msMsg; - double mfStartTime; -}; - -} - ScDPFieldButton::ScDPFieldButton(OutputDevice* pOutDev, const StyleSettings* pStyle, const Fraction* pZoomX, const Fraction* pZoomY) : mpOutDev(pOutDev), mpStyle(pStyle), @@ -557,14 +514,12 @@ void ScMenuFloatingWindow::executeMenu(size_t nPos) void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, bool bEnsureSubMenu) { - StackPrinter __stack_printer__("ScMenuFloatingWindow::setSelectedMenuItem"); if (mnSelectedMenu == nPos) // nothing to do. return; if (bEnsureSubMenu) { - fprintf(stdout, "ScMenuFloatingWindow::setSelectedMenuItem: (ensuring...) selected menu = %d\n", mnSelectedMenu); // Dismiss any child popup menu windows. if (mnSelectedMenu < maMenuItems.size() && maMenuItems[mnSelectedMenu].mpSubMenuWin && @@ -583,7 +538,6 @@ void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, selectMenuItem(mnSelectedMenu, false, bSubMenuTimer); selectMenuItem(nPos, true, bSubMenuTimer); mnSelectedMenu = nPos; - fprintf(stdout, "ScMenuFloatingWindow::setSelectedMenuItem: selected menu = %d\n", mnSelectedMenu); } size_t ScMenuFloatingWindow::getSelectedMenuPos() const @@ -762,7 +716,6 @@ void ScMenuFloatingWindow::clearSelectedMenuItem() { selectMenuItem(mnSelectedMenu, false, false); mnSelectedMenu = MENU_NOT_SELECTED; - fprintf(stdout, "ScMenuFloatingWindow::clearSelectedMenuItem: here\n"); } ScMenuFloatingWindow* ScMenuFloatingWindow::getSubMenuWindow(size_t nPos) const @@ -919,7 +872,6 @@ void ScMenuFloatingWindow::setSubMenuFocused(ScMenuFloatingWindow* pSubMenu) void ScMenuFloatingWindow::ensureSubMenuVisible(ScMenuFloatingWindow* pSubMenu) { - StackPrinter __stack_printer__("ScMenuFloatingWindow::ensureSubMenuVisible"); if (mpParentMenu) mpParentMenu->ensureSubMenuVisible(this); -- cgit From ed33032301907f6888b49cacb61ec10f78dee9ae Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 21 Aug 2009 19:03:06 +0000 Subject: Supported execution of menu items from the accessible object. --- sc/source/ui/cctrl/dpcontrol.cxx | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 3d51baf73a96..bcf01317d3de 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -328,7 +328,7 @@ void ScMenuFloatingWindow::MouseButtonDown(const MouseEvent& rMEvt) void ScMenuFloatingWindow::MouseButtonUp(const MouseEvent& rMEvt) { - executeMenu(mnClickedMenu); + executeMenuItem(mnClickedMenu); mnClickedMenu = MENU_NOT_SELECTED; Window::MouseButtonUp(rMEvt); } @@ -375,7 +375,7 @@ void ScMenuFloatingWindow::KeyInput(const KeyEvent& rKEvt) break; case KEY_RETURN: if (nSelectedMenu != MENU_NOT_SELECTED) - executeMenu(nSelectedMenu); + executeMenuItem(nSelectedMenu); break; default: bHandled = false; @@ -498,7 +498,7 @@ const Font& ScMenuFloatingWindow::getLabelFont() const return maLabelFont; } -void ScMenuFloatingWindow::executeMenu(size_t nPos) +void ScMenuFloatingWindow::executeMenuItem(size_t nPos) { if (nPos >= maMenuItems.size()) return; -- cgit From 9dffba7f4b3e7bb139993ab7e94b6c20965ef9ab Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 21 Aug 2009 19:17:39 +0000 Subject: When a menu action is fired via accessible object, we need to make sure that all the popup windows get dismissed. --- sc/source/ui/cctrl/dpcontrol.cxx | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index bcf01317d3de..cd7aca9acc2f 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -289,8 +289,7 @@ ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc, US mnClickedMenu(MENU_NOT_SELECTED), mpDoc(pDoc), mpParentMenu(dynamic_cast(pParent)), - mpActiveSubMenu(NULL), - mbActionFired(false) + mpActiveSubMenu(NULL) { SetMenuStackLevel(nMenuStackLevel); @@ -508,8 +507,7 @@ void ScMenuFloatingWindow::executeMenuItem(size_t nPos) return; maMenuItems[nPos].mpAction->execute(); - mbActionFired = true; - EndPopupMode(); + terminateAllPopupMenus(); } void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, bool bEnsureSubMenu) @@ -910,12 +908,11 @@ void ScMenuFloatingWindow::ensureSubMenuNotVisible() EndPopupMode(); } -IMPL_LINK( ScMenuFloatingWindow, EndPopupHdl, void*, EMPTYARG ) +void ScMenuFloatingWindow::terminateAllPopupMenus() { - if (mbActionFired && mpParentMenu) - mpParentMenu->EndPopupMode(); - - return 0; + EndPopupMode(); + if (mpParentMenu) + mpParentMenu->terminateAllPopupMenus(); } // ============================================================================ -- cgit From 514d004f7422f4103d8574b7339c22345a5e6c7c Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Fri, 21 Aug 2009 20:19:55 +0000 Subject: fixed a build breakage. --- sc/source/ui/cctrl/dpcontrol.cxx | 1 - 1 file changed, 1 deletion(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index cd7aca9acc2f..ab3123718d40 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -301,7 +301,6 @@ ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc, US SetFont(maLabelFont); SetText(OUString::createFromAscii("ScMenuFloatingWindow")); - SetPopupModeEndHdl( LINK(this, ScMenuFloatingWindow, EndPopupHdl) ); } ScMenuFloatingWindow::~ScMenuFloatingWindow() -- cgit From aa18040a8e2db3b1c51e6de4ea34f73efa96a447 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Sat, 22 Aug 2009 03:13:19 +0000 Subject: code cleanup. --- sc/source/ui/cctrl/dpcontrol.cxx | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index ab3123718d40..ce45f0c1b504 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -48,8 +48,6 @@ #include -#define MENU_NOT_SELECTED 999 - using ::com::sun::star::uno::Reference; using ::com::sun::star::accessibility::XAccessible; using ::rtl::OUString; @@ -280,6 +278,8 @@ IMPL_LINK( ScMenuFloatingWindow::SubMenuItemData, TimeoutHdl, void*, EMPTYARG ) // ---------------------------------------------------------------------------- +size_t ScMenuFloatingWindow::MENU_NOT_SELECTED = 999; + ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc, USHORT nMenuStackLevel) : FloatingWindow(pParent, (WB_SYSTEMFLOATWIN|WB_SYSTEMWINDOW|WB_NOBORDER)), maOpenTimer(this), @@ -537,7 +537,7 @@ void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, mnSelectedMenu = nPos; } -size_t ScMenuFloatingWindow::getSelectedMenuPos() const +size_t ScMenuFloatingWindow::getSelectedMenuItem() const { return mnSelectedMenu; } @@ -1177,7 +1177,7 @@ void ScDPFieldPopupWindow::MouseMove(const MouseEvent& rMEvt) { ScMenuFloatingWindow::MouseMove(rMEvt); - size_t nSelectedMenu = getSelectedMenuPos(); + size_t nSelectedMenu = getSelectedMenuItem(); if (nSelectedMenu == MENU_NOT_SELECTED) queueCloseSubMenu(); } @@ -1240,6 +1240,8 @@ void ScDPFieldPopupWindow::setMemberSize(size_t n) void ScDPFieldPopupWindow::addMember(const OUString& rName, bool bVisible) { + fprintf(stdout, "ScDPFieldPopupWindow::addMember: name = '%s' visible = %d\n", + rtl::OUStringToOString(rName, RTL_TEXTENCODING_UTF8).getStr(), bVisible); Member aMember; aMember.maName = rName; aMember.mbVisible = bVisible; -- cgit From fd7c4e6b7c51ccb702bb7b383ad14d573ebb3a48 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Sat, 22 Aug 2009 04:04:35 +0000 Subject: forgot to remove debug statement. --- sc/source/ui/cctrl/dpcontrol.cxx | 2 -- 1 file changed, 2 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index ce45f0c1b504..ca3d5d3d93ae 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -1240,8 +1240,6 @@ void ScDPFieldPopupWindow::setMemberSize(size_t n) void ScDPFieldPopupWindow::addMember(const OUString& rName, bool bVisible) { - fprintf(stdout, "ScDPFieldPopupWindow::addMember: name = '%s' visible = %d\n", - rtl::OUStringToOString(rName, RTL_TEXTENCODING_UTF8).getStr(), bVisible); Member aMember; aMember.maName = rName; aMember.mbVisible = bVisible; -- cgit From fddbd3634adb04995106aff39334c1ddf55013bc Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Tue, 25 Aug 2009 15:36:57 +0000 Subject: Reorganized accessible menu implementation so that the toplevel window is treated as menu. It's cleaner and less complicated this way. --- sc/source/ui/cctrl/dpcontrol.cxx | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index ca3d5d3d93ae..c46a83e4f8b8 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -830,6 +830,11 @@ void ScMenuFloatingWindow::getMenuItemPosSize(size_t nPos, Point& rPos, Size& rS rSize = aSize1; } +ScMenuFloatingWindow* ScMenuFloatingWindow::getParentMenuWindow() const +{ + return mpParentMenu; +} + size_t ScMenuFloatingWindow::getEnclosingMenuItem(const Point& rPos) const { size_t n = maMenuItems.size(); @@ -1212,9 +1217,7 @@ Reference ScDPFieldPopupWindow::CreateAccessible() mxAccessible.set(new ScAccessibleFilterTopWindow( GetAccessibleParentWindow()->GetAccessible(), this, getName(), getDoc())); ScAccessibleFilterTopWindow* pAccTop = static_cast(mxAccessible.get()); - Reference xAccMenu = pAccTop->getAccessibleChildMenu(); - ScAccessibleFilterMenu* pAccMenu = static_cast(xAccMenu.get()); - fillMenuItemsToAccessible(pAccMenu); + fillMenuItemsToAccessible(pAccTop); pAccTop->setAccessibleChild( maChecks.CreateAccessible(), ScAccessibleFilterTopWindow::LISTBOX); -- cgit From 4848dbac7b540e2a0d64521e19765a261f7e7305 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Wed, 26 Aug 2009 00:48:56 +0000 Subject: Fire a menu highlight event on menu item selection change, to get the accessibility to work correctly. --- sc/source/ui/cctrl/dpcontrol.cxx | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index c46a83e4f8b8..e17ff0cd1dab 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -47,9 +47,11 @@ #include "AccessibleFilterTopWindow.hxx" #include +#include using ::com::sun::star::uno::Reference; using ::com::sun::star::accessibility::XAccessible; +using ::com::sun::star::accessibility::XAccessibleContext; using ::rtl::OUString; using ::rtl::OUStringHash; using ::std::vector; @@ -706,6 +708,26 @@ void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSub else queueCloseSubMenu(); } + + if (mxAccessible.is()) + { + // Fire a menu highlight event since the accessibility framework + // needs this to track focus on menu items. + do + { + Reference xAccCxt = mxAccessible->getAccessibleContext(); + if (!xAccCxt.is()) + break; + + Reference xAccMenu = xAccCxt->getAccessibleChild(nPos); + if (!xAccMenu.is()) + break; + + VclAccessibleEvent aEvent(VCLEVENT_MENU_HIGHLIGHT, xAccMenu); + FireVclEvent(&aEvent); + } + while (false); + } } } -- cgit From 443f0efd5acca6afe87f75d9f9f75844596622ac Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Wed, 26 Aug 2009 02:47:23 +0000 Subject: clear selected menu item when the popup ends. --- sc/source/ui/cctrl/dpcontrol.cxx | 49 ++++++++++++++++++++++++---------------- 1 file changed, 29 insertions(+), 20 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index e17ff0cd1dab..8b4c1ba6812e 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -303,6 +303,7 @@ ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc, US SetFont(maLabelFont); SetText(OUString::createFromAscii("ScMenuFloatingWindow")); + SetPopupModeEndHdl( LINK(this, ScMenuFloatingWindow, PopupEndHdl) ); } ScMenuFloatingWindow::~ScMenuFloatingWindow() @@ -537,6 +538,8 @@ void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer, selectMenuItem(mnSelectedMenu, false, bSubMenuTimer); selectMenuItem(nPos, true, bSubMenuTimer); mnSelectedMenu = nPos; + + fireMenuHighlightedEvent(); } size_t ScMenuFloatingWindow::getSelectedMenuItem() const @@ -708,26 +711,6 @@ void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSub else queueCloseSubMenu(); } - - if (mxAccessible.is()) - { - // Fire a menu highlight event since the accessibility framework - // needs this to track focus on menu items. - do - { - Reference xAccCxt = mxAccessible->getAccessibleContext(); - if (!xAccCxt.is()) - break; - - Reference xAccMenu = xAccCxt->getAccessibleChild(nPos); - if (!xAccMenu.is()) - break; - - VclAccessibleEvent aEvent(VCLEVENT_MENU_HIGHLIGHT, xAccMenu); - FireVclEvent(&aEvent); - } - while (false); - } } } @@ -883,6 +866,26 @@ size_t ScMenuFloatingWindow::getSubMenuPos(ScMenuFloatingWindow* pSubMenu) return MENU_NOT_SELECTED; } +void ScMenuFloatingWindow::fireMenuHighlightedEvent() +{ + if (mnSelectedMenu == MENU_NOT_SELECTED) + return; + + if (!mxAccessible.is()) + return; + + Reference xAccCxt = mxAccessible->getAccessibleContext(); + if (!xAccCxt.is()) + return; + + Reference xAccMenu = xAccCxt->getAccessibleChild(mnSelectedMenu); + if (!xAccMenu.is()) + return; + + VclAccessibleEvent aEvent(VCLEVENT_MENU_HIGHLIGHT, xAccMenu); + FireVclEvent(&aEvent); +} + void ScMenuFloatingWindow::setSubMenuFocused(ScMenuFloatingWindow* pSubMenu) { maCloseTimer.reset(); @@ -941,6 +944,12 @@ void ScMenuFloatingWindow::terminateAllPopupMenus() mpParentMenu->terminateAllPopupMenus(); } +IMPL_LINK( ScMenuFloatingWindow, PopupEndHdl, void*, EMPTYARG ) +{ + clearSelectedMenuItem(); + return 0; +} + // ============================================================================ ScDPFieldPopupWindow::Member::Member() : -- cgit From b4049f44bf9bb5c004d238063cf8ef56951553ce Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Wed, 26 Aug 2009 03:04:42 +0000 Subject: changed endSubMenu() to not rely on the open timer data to dismiss the sub menu. --- sc/source/ui/cctrl/dpcontrol.cxx | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 8b4c1ba6812e..f4fbd02266fc 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -358,7 +358,7 @@ void ScMenuFloatingWindow::KeyInput(const KeyEvent& rKEvt) break; case KEY_LEFT: if (mpParentMenu) - mpParentMenu->endSubMenu(); + mpParentMenu->endSubMenu(this); break; case KEY_RIGHT: { @@ -636,14 +636,19 @@ void ScMenuFloatingWindow::launchSubMenu(bool bSetMenuPos) SetPopupModeFlags(nOldFlags); } -void ScMenuFloatingWindow::endSubMenu() +void ScMenuFloatingWindow::endSubMenu(ScMenuFloatingWindow* pSubMenu) { + if (!pSubMenu) + return; + + pSubMenu->EndPopupMode(); + + size_t nMenuPos = getSubMenuPos(pSubMenu); + if (nMenuPos != MENU_NOT_SELECTED) + highlightMenuItem(nMenuPos, true); + if (maOpenTimer.mpSubMenu) - { - maOpenTimer.mpSubMenu->EndPopupMode(); maOpenTimer.mpSubMenu = NULL; - highlightMenuItem(maOpenTimer.mnMenuPos, true); - } } void ScMenuFloatingWindow::fillMenuItemsToAccessible(ScAccessibleFilterMenu* pAccMenu) const -- cgit From b0838ee5af5000192b5784ca1da504be1db0b7cf Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Wed, 26 Aug 2009 03:14:06 +0000 Subject: read the highlighted menu of the parent popup when the child popup gets dismissed. --- sc/source/ui/cctrl/dpcontrol.cxx | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index f4fbd02266fc..7423ea4278fb 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -642,13 +642,15 @@ void ScMenuFloatingWindow::endSubMenu(ScMenuFloatingWindow* pSubMenu) return; pSubMenu->EndPopupMode(); + maOpenTimer.reset(); size_t nMenuPos = getSubMenuPos(pSubMenu); if (nMenuPos != MENU_NOT_SELECTED) + { highlightMenuItem(nMenuPos, true); - - if (maOpenTimer.mpSubMenu) - maOpenTimer.mpSubMenu = NULL; + mnSelectedMenu = nMenuPos; + fireMenuHighlightedEvent(); + } } void ScMenuFloatingWindow::fillMenuItemsToAccessible(ScAccessibleFilterMenu* pAccMenu) const -- cgit From 5e8d3e43d3e4689d91d2f94d826146c076f907e6 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Wed, 26 Aug 2009 19:07:14 +0000 Subject: TAB key to cycle through controls. --- sc/source/ui/cctrl/dpcontrol.cxx | 57 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 57 insertions(+) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 7423ea4278fb..4c9dee6b4af1 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -985,11 +985,21 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent, ScDocument* pDoc) : maBtnUnselectSingle(this, 0), maBtnOk(this), maBtnCancel(this), + mnCurTabStop(0), mpExtendedData(NULL), mpOKAction(NULL), maWndSize(160, 330), mePrevToggleAllState(STATE_DONTKNOW) { + maTabStopCtrls.reserve(7); + maTabStopCtrls.push_back(this); + maTabStopCtrls.push_back(&maChecks); + maTabStopCtrls.push_back(&maChkToggleAll); + maTabStopCtrls.push_back(&maBtnSelectSingle); + maTabStopCtrls.push_back(&maBtnUnselectSingle); + maTabStopCtrls.push_back(&maBtnOk); + maTabStopCtrls.push_back(&maBtnCancel); + const StyleSettings& rStyle = GetSettings().GetStyleSettings(); Point aPos; @@ -1157,6 +1167,28 @@ void ScDPFieldPopupWindow::selectCurrentMemberOnly(bool bSet) maChecks.CheckEntryPos(nSelected, bSet); } +void ScDPFieldPopupWindow::cycleFocus(bool bReverse) +{ + maTabStopCtrls[mnCurTabStop]->LoseFocus(); + if (mnCurTabStop == 0) + clearSelectedMenuItem(); + + if (bReverse) + { + if (mnCurTabStop > 0) + --mnCurTabStop; + else + mnCurTabStop = maTabStopCtrls.size() - 1; + } + else + { + ++mnCurTabStop; + if (mnCurTabStop >= maTabStopCtrls.size()) + mnCurTabStop = 0; + } + maTabStopCtrls[mnCurTabStop]->GetFocus(); +} + IMPL_LINK( ScDPFieldPopupWindow, ButtonHdl, Button*, pBtn ) { if (pBtn == &maBtnOk) @@ -1225,6 +1257,26 @@ void ScDPFieldPopupWindow::MouseMove(const MouseEvent& rMEvt) queueCloseSubMenu(); } +long ScDPFieldPopupWindow::Notify(NotifyEvent& rNEvt) +{ + switch (rNEvt.GetType()) + { + case EVENT_KEYUP: + { + const KeyEvent* pKeyEvent = rNEvt.GetKeyEvent(); + const KeyCode& rCode = pKeyEvent->GetKeyCode(); + bool bShift = rCode.IsShift(); + if (rCode.GetCode() == KEY_TAB) + { + cycleFocus(bShift); + return true; + } + } + break; + } + return ScMenuFloatingWindow::Notify(rNEvt); +} + void ScDPFieldPopupWindow::Paint(const Rectangle& rRect) { ScMenuFloatingWindow::Paint(rRect); @@ -1248,6 +1300,11 @@ void ScDPFieldPopupWindow::Paint(const Rectangle& rRect) DrawRect(Rectangle(aPos,aSize)); } +Window* ScDPFieldPopupWindow::GetPreferredKeyInputWindow() +{ + return maTabStopCtrls[mnCurTabStop]; +} + Reference ScDPFieldPopupWindow::CreateAccessible() { if (!mxAccessible.is()) -- cgit From 984236d8b16fbb1c2728a7f4f2d25146865c6dee Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Wed, 26 Aug 2009 22:59:36 +0000 Subject: Use the new "fake focus" flag of Window to simulate focus state, in order to implement tab stops inside floating windows. --- sc/source/ui/cctrl/dpcontrol.cxx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 4c9dee6b4af1..32fd88421a84 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -1169,6 +1169,7 @@ void ScDPFieldPopupWindow::selectCurrentMemberOnly(bool bSet) void ScDPFieldPopupWindow::cycleFocus(bool bReverse) { + maTabStopCtrls[mnCurTabStop]->SetFakeFocus(false); maTabStopCtrls[mnCurTabStop]->LoseFocus(); if (mnCurTabStop == 0) clearSelectedMenuItem(); @@ -1186,7 +1187,8 @@ void ScDPFieldPopupWindow::cycleFocus(bool bReverse) if (mnCurTabStop >= maTabStopCtrls.size()) mnCurTabStop = 0; } - maTabStopCtrls[mnCurTabStop]->GetFocus(); + maTabStopCtrls[mnCurTabStop]->SetFakeFocus(true); + maTabStopCtrls[mnCurTabStop]->GrabFocus(); } IMPL_LINK( ScDPFieldPopupWindow, ButtonHdl, Button*, pBtn ) -- cgit From 2d16f08b453f2b2a4a32f902caae616318a19701 Mon Sep 17 00:00:00 2001 From: Kohei Yoshida Date: Thu, 27 Aug 2009 02:36:18 +0000 Subject: Use the new PopupMenuFloatingWindow instead of FloatingWindow for popup menu specific stuff. --- sc/source/ui/cctrl/dpcontrol.cxx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index 32fd88421a84..ee58c3dca601 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -283,7 +283,7 @@ IMPL_LINK( ScMenuFloatingWindow::SubMenuItemData, TimeoutHdl, void*, EMPTYARG ) size_t ScMenuFloatingWindow::MENU_NOT_SELECTED = 999; ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent, ScDocument* pDoc, USHORT nMenuStackLevel) : - FloatingWindow(pParent, (WB_SYSTEMFLOATWIN|WB_SYSTEMWINDOW|WB_NOBORDER)), + PopupMenuFloatingWindow(pParent), maOpenTimer(this), maCloseTimer(this), maName(OUString::createFromAscii("ScMenuFloatingWindow")), -- cgit From 557814474f7c73b386fa25a189c5139ac854f616 Mon Sep 17 00:00:00 2001 From: Daniel Rentz Date: Wed, 14 Oct 2009 08:12:03 +0000 Subject: wntmsci12 warnings --- sc/source/ui/cctrl/dpcontrol.cxx | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) (limited to 'sc/source/ui/cctrl/dpcontrol.cxx') diff --git a/sc/source/ui/cctrl/dpcontrol.cxx b/sc/source/ui/cctrl/dpcontrol.cxx index ee58c3dca601..a938948e1b26 100644 --- a/sc/source/ui/cctrl/dpcontrol.cxx +++ b/sc/source/ui/cctrl/dpcontrol.cxx @@ -141,7 +141,7 @@ void ScDPFieldButton::draw() Font aTextFont( mpStyle->GetLabelFont() ); double fFontHeight = 12.0; fFontHeight *= static_cast(maZoomY.GetNumerator()) / static_cast(maZoomY.GetDenominator()); - aTextFont.SetHeight(fFontHeight); + aTextFont.SetHeight(static_cast(fFontHeight)); mpOutDev->SetFont(aTextFont); Point aTextPos = maPos; @@ -159,7 +159,7 @@ void ScDPFieldButton::draw() void ScDPFieldButton::getPopupBoundingBox(Point& rPos, Size& rSize) const { - long nW = maSize.getWidth()*0.5; + long nW = maSize.getWidth() / 2; long nH = maSize.getHeight(); if (nW > 18) nW = 18; @@ -830,7 +830,7 @@ void ScMenuFloatingWindow::getMenuItemPosSize(size_t nPos, Point& rPos, Size& rS { const sal_uInt16 nLeftMargin = 5; const sal_uInt16 nTopMargin = 5; - const sal_uInt16 nMenuItemHeight = maLabelFont.GetHeight()*1.8; + const sal_uInt16 nMenuItemHeight = static_cast< sal_uInt16 >( maLabelFont.GetHeight()*1.8 ); Size aWndSize = GetSizePixel(); @@ -1062,15 +1062,15 @@ void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionTy const sal_uInt16 nSingleItemBtnAreaHeight = 32; // height of the middle area below the list box where the single-action buttons are. const sal_uInt16 nBottomBtnAreaHeight = 50; // height of the bottom area where the OK and Cancel buttons are. const sal_uInt16 nBtnWidth = 60; - const sal_uInt16 nLabelHeight = getLabelFont().GetHeight(); + const sal_uInt16 nLabelHeight = static_cast< sal_uInt16 >( getLabelFont().GetHeight() ); const sal_uInt16 nBtnHeight = nLabelHeight*2; const sal_uInt16 nBottomMargin = 10; const sal_uInt16 nMenuListMargin = 20; // parameters calculated from constants. - const sal_uInt16 nListBoxWidth = maWndSize.Width() - nListBoxMargin*2; - const sal_uInt16 nListBoxHeight = maWndSize.Height() - nTopMargin - nMenuHeight - - nMenuListMargin - nSingleItemBtnAreaHeight - nBottomBtnAreaHeight; + const sal_uInt16 nListBoxWidth = static_cast< sal_uInt16 >( maWndSize.Width() - nListBoxMargin*2 ); + const sal_uInt16 nListBoxHeight = static_cast< sal_uInt16 >( maWndSize.Height() - nTopMargin - nMenuHeight - + nMenuListMargin - nSingleItemBtnAreaHeight - nBottomBtnAreaHeight ); const sal_uInt16 nSingleBtnAreaY = nTopMargin + nMenuHeight + nListBoxHeight + nMenuListMargin - 1; @@ -1157,7 +1157,7 @@ void ScDPFieldPopupWindow::setAllMemberState(bool bSet) { size_t n = maMembers.size(); for (size_t i = 0; i < n; ++i) - maChecks.CheckEntryPos(i, bSet); + maChecks.CheckEntryPos(static_cast< USHORT >( i ), bSet); } void ScDPFieldPopupWindow::selectCurrentMemberOnly(bool bSet) @@ -1353,7 +1353,7 @@ void ScDPFieldPopupWindow::initMembers() for (size_t i = 0; i < n; ++i) { maChecks.InsertEntry(maMembers[i].maName); - maChecks.CheckEntryPos(i, maMembers[i].mbVisible); + maChecks.CheckEntryPos(static_cast< USHORT >( i ), maMembers[i].mbVisible); if (maMembers[i].mbVisible) ++nVisMemCount; } @@ -1388,7 +1388,7 @@ void ScDPFieldPopupWindow::getResult(hash_map& rRe size_t n = maMembers.size(); for (size_t i = 0; i < n; ++i) { - bool bState = maChecks.IsChecked(i); + bool bState = maChecks.IsChecked(static_cast< USHORT >( i )); aResult.insert(ResultMap::value_type(maMembers[i].maName, bState)); } rResult.swap(aResult); -- cgit