1 diff --git sc/inc/sc.hrc sc/inc/sc.hrc
2 index 3ecd9ba..32f883a 100644
6 // Language chooser for text import filters.
7 #define RID_SCDLG_LANG_CHOOSER (SC_OOO_BUILD_START + 12)
10 +#define RID_SC_DPCONTROL (SC_OOO_BUILD_START + 13)
15 diff --git sc/source/ui/cctrl/dpcontrol.cxx sc/source/ui/cctrl/dpcontrol.cxx
16 index e188ab3..02fb0b9 100644
17 --- sc/source/ui/cctrl/dpcontrol.cxx
18 +++ sc/source/ui/cctrl/dpcontrol.cxx
20 #include "vcl/outdev.hxx"
21 #include "vcl/settings.hxx"
22 #include "vcl/wintypes.hxx"
23 +#include "vcl/decoview.hxx"
25 +#define MENU_NOT_SELECTED 999
27 using ::rtl::OUString;
28 using ::rtl::OUStringHash;
29 @@ -182,6 +185,525 @@ void ScDPFieldButton::drawPopupButton()
31 // ============================================================================
33 +ScMenuFloatingWindow::MenuItem::MenuItem() :
35 + mpAction(static_cast<ScDPFieldPopupWindow::Action*>(NULL)),
36 + mpSubMenuWin(static_cast<ScMenuFloatingWindow*>(NULL))
40 +// ----------------------------------------------------------------------------
42 +ScMenuFloatingWindow::SubMenuItem::SubMenuItem(ScMenuFloatingWindow* pParent) :
44 + mnMenuPos(MENU_NOT_SELECTED),
47 + maTimer.SetTimeoutHdl( LINK(this, ScMenuFloatingWindow::SubMenuItem, TimeoutHdl) );
48 + maTimer.SetTimeout(mpParent->GetSettings().GetMouseSettings().GetMenuDelay());
51 +void ScMenuFloatingWindow::SubMenuItem::reset()
54 + mnMenuPos = MENU_NOT_SELECTED;
58 +IMPL_LINK( ScMenuFloatingWindow::SubMenuItem, TimeoutHdl, void*, EMPTYARG )
60 + mpParent->handleMenuTimeout(this);
64 +// ----------------------------------------------------------------------------
66 +ScMenuFloatingWindow::ScMenuFloatingWindow(Window* pParent) :
67 + FloatingWindow(pParent, (WB_SYSTEMFLOATWIN|WB_SYSTEMWINDOW|WB_NOBORDER)),
70 + mnSelectedMenu(MENU_NOT_SELECTED),
71 + mnClickedMenu(MENU_NOT_SELECTED),
72 + mpParentMenu(dynamic_cast<ScMenuFloatingWindow*>(pParent)),
73 + mpActiveSubMenu(NULL),
74 + mbActionFired(false)
76 + // TODO: How do we get the right font to use here ?
77 + const sal_uInt16 nPopupFontHeight = 12;
78 + const StyleSettings& rStyle = GetSettings().GetStyleSettings();
79 + maLabelFont = rStyle.GetLabelFont();
80 + maLabelFont.SetHeight(nPopupFontHeight);
81 + SetFont(maLabelFont);
83 + SetPopupModeEndHdl( LINK(this, ScMenuFloatingWindow, EndPopupHdl) );
86 +ScMenuFloatingWindow::~ScMenuFloatingWindow()
91 +void ScMenuFloatingWindow::MouseMove(const MouseEvent& rMEvt)
93 + const Point& rPos = rMEvt.GetPosPixel();
94 + size_t nSelectedMenu = getEnclosingMenuItem(rPos);
95 + setSelectedMenuItem(nSelectedMenu);
97 + Window::MouseMove(rMEvt);
100 +void ScMenuFloatingWindow::MouseButtonDown(const MouseEvent& rMEvt)
102 + const Point& rPos = rMEvt.GetPosPixel();
103 + mnClickedMenu = getEnclosingMenuItem(rPos);
104 + Window::MouseButtonDown(rMEvt);
107 +void ScMenuFloatingWindow::MouseButtonUp(const MouseEvent& rMEvt)
109 + executeMenu(mnClickedMenu);
110 + mnClickedMenu = MENU_NOT_SELECTED;
111 + Window::MouseButtonUp(rMEvt);
114 +void ScMenuFloatingWindow::KeyInput(const KeyEvent& rKEvt)
116 + const KeyCode& rKeyCode = rKEvt.GetKeyCode();
117 + bool bHandled = true;
118 + size_t nSelectedMenu = mnSelectedMenu;
119 + size_t nLastMenuPos = maMenuItems.size() - 1;
120 + switch (rKeyCode.GetCode())
123 + if (nSelectedMenu == MENU_NOT_SELECTED || nSelectedMenu == 0)
124 + nSelectedMenu = nLastMenuPos;
127 + setSelectedMenuItem(nSelectedMenu, false);
130 + if (nSelectedMenu == MENU_NOT_SELECTED || nSelectedMenu == nLastMenuPos)
134 + setSelectedMenuItem(nSelectedMenu, false);
138 + mpParentMenu->endSubMenu();
142 + if (mnSelectedMenu >= maMenuItems.size() || mnSelectedMenu == MENU_NOT_SELECTED)
145 + const MenuItem& rMenu = maMenuItems[mnSelectedMenu];
146 + if (!rMenu.mbEnabled || !rMenu.mpSubMenuWin)
149 + maOpenTimer.mnMenuPos = mnSelectedMenu;
150 + maOpenTimer.mpSubMenu = rMenu.mpSubMenuWin.get();
151 + launchSubMenu(true);
155 + if (nSelectedMenu != MENU_NOT_SELECTED)
156 + executeMenu(nSelectedMenu);
163 + Window::KeyInput(rKEvt);
166 +void ScMenuFloatingWindow::Paint(const Rectangle& /*rRect*/)
168 + const StyleSettings& rStyle = GetSettings().GetStyleSettings();
169 + Color aBackColor = rStyle.GetMenuColor();
170 + Color aBorderColor = rStyle.GetShadowColor();
172 + Rectangle aCtrlRect(Point(0, 0), GetOutputSizePixel());
174 + // Window background
175 + bool bNativeDrawn = true;
176 + if (IsNativeControlSupported(CTRL_MENU_POPUP, PART_ENTIRE_CONTROL))
179 + bNativeDrawn = DrawNativeControl(
180 + CTRL_MENU_POPUP, PART_ENTIRE_CONTROL, Region(aCtrlRect), CTRL_STATE_ENABLED,
181 + ImplControlValue(), OUString());
184 + bNativeDrawn = false;
188 + SetFillColor(aBackColor);
189 + SetLineColor(aBorderColor);
190 + DrawRect(aCtrlRect);
194 + SetTextColor(rStyle.GetMenuTextColor());
195 + drawAllMenuItems();
198 +void ScMenuFloatingWindow::addMenuItem(const OUString& rText, bool bEnabled, Action* pAction)
201 + aItem.maText = rText;
202 + aItem.mbEnabled = bEnabled;
203 + aItem.mpAction.reset(pAction);
204 + maMenuItems.push_back(aItem);
207 +ScMenuFloatingWindow* ScMenuFloatingWindow::addSubMenuItem(const OUString& rText, bool bEnabled)
210 + aItem.maText = rText;
211 + aItem.mbEnabled = bEnabled;
212 + aItem.mpSubMenuWin.reset(new ScMenuFloatingWindow(this));
213 + maMenuItems.push_back(aItem);
214 + return aItem.mpSubMenuWin.get();
217 +void ScMenuFloatingWindow::drawMenuItem(size_t nPos)
219 + if (nPos >= maMenuItems.size())
224 + getMenuItemPosSize(aPos, aSize, nPos);
226 + DecorationView aDecoView(this);
228 + long nYOffset = (aSize.Height() - maLabelFont.GetHeight())/2;
229 + DrawCtrlText(Point(aPos.X()+nXOffset, aPos.Y() + nYOffset), maMenuItems[nPos].maText, 0, STRING_LEN,
230 + maMenuItems[nPos].mbEnabled ? TEXT_DRAW_MNEMONIC : TEXT_DRAW_DISABLE);
232 + if (maMenuItems[nPos].mpSubMenuWin)
234 + long nFontHeight = maLabelFont.GetHeight();
235 + Point aMarkerPos = aPos;
236 + aMarkerPos.Y() += aSize.Height()/2 - nFontHeight/4 + 1;
237 + aMarkerPos.X() += aSize.Width() - nFontHeight + nFontHeight/4;
238 + Size aMarkerSize(nFontHeight/2, nFontHeight/2);
239 + aDecoView.DrawSymbol(Rectangle(aMarkerPos, aMarkerSize),
240 + SYMBOL_SPIN_RIGHT, GetTextColor(), 0);
244 +void ScMenuFloatingWindow::drawAllMenuItems()
246 + size_t n = maMenuItems.size();
247 + for (size_t i = 0; i < n; ++i)
248 + highlightMenuItem(i, i == mnSelectedMenu);
251 +const Font& ScMenuFloatingWindow::getLabelFont() const
253 + return maLabelFont;
256 +void ScMenuFloatingWindow::executeMenu(size_t nPos)
258 + if (nPos >= maMenuItems.size())
261 + if (!maMenuItems[nPos].mpAction)
262 + // no action is defined.
265 + maMenuItems[nPos].mpAction->execute();
266 + mbActionFired = true;
270 +void ScMenuFloatingWindow::setSelectedMenuItem(size_t nPos, bool bSubMenuTimer)
272 + if (mnSelectedMenu != nPos)
274 + selectMenuItem(mnSelectedMenu, false, bSubMenuTimer);
275 + selectMenuItem(nPos, true, bSubMenuTimer);
276 + mnSelectedMenu = nPos;
280 +size_t ScMenuFloatingWindow::getSelectedMenuItem() const
282 + return mnSelectedMenu;
285 +void ScMenuFloatingWindow::handleMenuTimeout(SubMenuItem* pTimer)
287 + if (pTimer == &maOpenTimer)
289 + // Close any open submenu immediately.
290 + if (maCloseTimer.mpSubMenu)
292 + maCloseTimer.mpSubMenu->EndPopupMode();
293 + maCloseTimer.mpSubMenu = NULL;
294 + maCloseTimer.maTimer.Stop();
297 + launchSubMenu(false);
299 + else if (pTimer == &maCloseTimer)
302 + if (maCloseTimer.mpSubMenu)
304 + maOpenTimer.mpSubMenu = NULL;
306 + maCloseTimer.mpSubMenu->EndPopupMode();
307 + maCloseTimer.mpSubMenu = NULL;
309 + highlightMenuItem(maOpenTimer.mnMenuPos, false);
310 + maOpenTimer.mnMenuPos = MENU_NOT_SELECTED;
315 +void ScMenuFloatingWindow::queueLaunchSubMenu(size_t nPos, ScMenuFloatingWindow* pMenu)
320 + // Set the submenu on launch queue.
321 + if (maOpenTimer.mpSubMenu)
323 + if (maOpenTimer.mpSubMenu == pMenu)
325 + if (pMenu == maCloseTimer.mpSubMenu)
326 + maCloseTimer.reset();
330 + // new submenu is being requested.
331 + queueCloseSubMenu();
334 + maOpenTimer.mpSubMenu = pMenu;
335 + maOpenTimer.mnMenuPos = nPos;
336 + maOpenTimer.maTimer.Start();
339 +void ScMenuFloatingWindow::queueCloseSubMenu()
341 + if (!maOpenTimer.mpSubMenu)
342 + // There is no submenu to close.
345 + // Stop any submenu on queue for opening.
346 + maOpenTimer.maTimer.Stop();
348 + maCloseTimer.mpSubMenu = maOpenTimer.mpSubMenu;
349 + maCloseTimer.mnMenuPos = maOpenTimer.mnMenuPos;
350 + maCloseTimer.maTimer.Start();
353 +void ScMenuFloatingWindow::launchSubMenu(bool bSetMenuPos)
357 + getMenuItemPosSize(aPos, aSize, maOpenTimer.mnMenuPos);
358 + ScMenuFloatingWindow* pSubMenu = maOpenTimer.mpSubMenu;
363 + sal_uInt32 nOldFlags = GetPopupModeFlags();
364 + SetPopupModeFlags(nOldFlags | FLOATWIN_POPUPMODE_NOAPPFOCUSCLOSE);
365 + pSubMenu->resetMenu(bSetMenuPos);
366 + pSubMenu->StartPopupMode(
367 + Rectangle(aPos,aSize), (FLOATWIN_POPUPMODE_RIGHT | FLOATWIN_POPUPMODE_GRABFOCUS));
368 + pSubMenu->AddPopupModeWindow(this);
369 + SetPopupModeFlags(nOldFlags);
372 +void ScMenuFloatingWindow::endSubMenu()
374 + if (maOpenTimer.mpSubMenu)
376 + maOpenTimer.mpSubMenu->EndPopupMode();
377 + maOpenTimer.mpSubMenu = NULL;
378 + highlightMenuItem(maOpenTimer.mnMenuPos, true);
382 +void ScMenuFloatingWindow::notify(NotificationType eType)
386 + case SUBMENU_FOCUSED:
387 + // Cancel any request for ending submenu.
388 + maCloseTimer.reset();
389 + if (mnSelectedMenu != maOpenTimer.mnMenuPos)
391 + highlightMenuItem(maOpenTimer.mnMenuPos, true);
392 + mnSelectedMenu = maOpenTimer.mnMenuPos;
400 +void ScMenuFloatingWindow::resetMenu(bool bSetMenuPos)
402 + mnSelectedMenu = bSetMenuPos ? 0 : MENU_NOT_SELECTED;
403 + resizeToFitMenuItems();
406 +void ScMenuFloatingWindow::resizeToFitMenuItems()
408 + if (maMenuItems.empty())
411 + vector<MenuItem>::const_iterator itr = maMenuItems.begin(), itrEnd = maMenuItems.end();
412 + long nTextWidth = 0;
413 + for (; itr != itrEnd; ++itr)
414 + nTextWidth = ::std::max(GetTextWidth(itr->maText), nTextWidth);
416 + size_t nLastPos = maMenuItems.size()-1;
419 + getMenuItemPosSize(aPos, aSize, nLastPos);
420 + aPos.X() += nTextWidth + 15;
421 + aPos.Y() += aSize.Height() + 5;
422 + SetOutputSizePixel(Size(aPos.X(), aPos.Y()));
425 +void ScMenuFloatingWindow::selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer)
427 + if (nPos >= maMenuItems.size() || nPos == MENU_NOT_SELECTED)
429 + queueCloseSubMenu();
433 + if (!maMenuItems[nPos].mbEnabled)
435 + queueCloseSubMenu();
439 + highlightMenuItem(nPos, bSelected);
444 + mpParentMenu->notify(SUBMENU_FOCUSED);
448 + if (maMenuItems[nPos].mpSubMenuWin)
450 + ScMenuFloatingWindow* pSubMenu = maMenuItems[nPos].mpSubMenuWin.get();
451 + queueLaunchSubMenu(nPos, pSubMenu);
454 + queueCloseSubMenu();
459 +void ScMenuFloatingWindow::highlightMenuItem(size_t nPos, bool bSelected)
461 + const StyleSettings& rStyle = GetSettings().GetStyleSettings();
462 + Color aBackColor = rStyle.GetMenuColor();
463 + SetFillColor(aBackColor);
464 + SetLineColor(aBackColor);
468 + getMenuItemPosSize(aPos, aSize, nPos);
469 + Region aRegion(Rectangle(aPos,aSize));
471 + if (IsNativeControlSupported(CTRL_MENU_POPUP, PART_ENTIRE_CONTROL))
473 + Push(PUSH_CLIPREGION);
474 + IntersectClipRegion(Rectangle(aPos, aSize));
475 + Rectangle aCtrlRect(Point(0,0), GetOutputSizePixel());
477 + CTRL_MENU_POPUP, PART_ENTIRE_CONTROL, Region(aCtrlRect), CTRL_STATE_ENABLED,
478 + ImplControlValue(), OUString());
483 + bool bNativeDrawn = true;
484 + if (IsNativeControlSupported(CTRL_MENU_POPUP, PART_MENU_ITEM))
486 + ControlState nState = bSelected ? CTRL_STATE_SELECTED : 0;
487 + if (maMenuItems[nPos].mbEnabled)
488 + nState |= CTRL_STATE_ENABLED;
489 + bNativeDrawn = DrawNativeControl(
490 + CTRL_MENU_POPUP, PART_MENU_ITEM, aRegion, nState, ImplControlValue(), OUString());
493 + bNativeDrawn = false;
499 + aBackColor = rStyle.GetMenuHighlightColor();
500 + SetFillColor(aBackColor);
501 + SetLineColor(aBackColor);
503 + DrawRect(Rectangle(aPos,aSize));
506 + Color aTextColor = bSelected ? rStyle.GetMenuHighlightTextColor() : rStyle.GetMenuTextColor();
507 + SetTextColor(aTextColor);
508 + drawMenuItem(nPos);
511 +void ScMenuFloatingWindow::getMenuItemPosSize(Point& rPos, Size& rSize, size_t nPos) const
513 + const sal_uInt16 nLeftMargin = 5;
514 + const sal_uInt16 nTopMargin = 5;
515 + const sal_uInt16 nMenuItemHeight = maLabelFont.GetHeight()*1.8;
517 + Size aWndSize = GetSizePixel();
519 + Point aPos1(nLeftMargin, nTopMargin);
520 + Size aSize1(aWndSize.Width() - nLeftMargin*2, nMenuItemHeight);
523 + rPos.Y() += aSize1.Height()*nPos;
527 +size_t ScMenuFloatingWindow::getEnclosingMenuItem(const Point& rPos) const
529 + size_t n = maMenuItems.size();
530 + for (size_t i = 0; i < n; ++i)
534 + getMenuItemPosSize(aPos, aSize, i);
535 + Rectangle aRect(aPos, aSize);
536 + if (aRect.IsInside(rPos))
539 + return MENU_NOT_SELECTED;
542 +IMPL_LINK( ScMenuFloatingWindow, EndPopupHdl, void*, EMPTYARG )
544 + if (mbActionFired && mpParentMenu)
545 + mpParentMenu->EndPopupMode();
550 +// ============================================================================
552 ScDPFieldPopupWindow::Member::Member() :
555 @@ -189,8 +711,19 @@ ScDPFieldPopupWindow::Member::Member() :
557 // ----------------------------------------------------------------------------
559 +ScDPFieldPopupWindow::CancelButton::CancelButton(ScDPFieldPopupWindow* pParent) :
560 + ::CancelButton(pParent), mpParent(pParent) {}
562 +void ScDPFieldPopupWindow::CancelButton::Click()
564 + mpParent->EndPopupMode();
565 + ::CancelButton::Click();
568 +// ----------------------------------------------------------------------------
570 ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) :
571 - FloatingWindow(pParent, (WB_SYSTEMFLOATWIN|WB_SYSTEMWINDOW|WB_NOBORDER)),
572 + ScMenuFloatingWindow(pParent),
576 @@ -201,8 +734,6 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) :
580 - maCheck10(this, 0),
581 - maCheck11(this, 0),
582 maScrollBar(this, WB_VERT),
585 @@ -210,12 +741,13 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) :
589 - SetOutputSizePixel(Size(150, 280));
592 + getSectionPosSize(aPos, aSize, WHOLE);
593 + SetOutputSizePixel(aSize);
594 Size aOutSize = GetOutputSizePixel();
596 - const StyleSettings& rStyle = GetSettings().GetStyleSettings();
598 - mpCheckPtr.reserve(12);
599 + mpCheckPtr.reserve(10);
600 mpCheckPtr.push_back(&maCheck0);
601 mpCheckPtr.push_back(&maCheck1);
602 mpCheckPtr.push_back(&maCheck2);
603 @@ -226,33 +758,27 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) :
604 mpCheckPtr.push_back(&maCheck7);
605 mpCheckPtr.push_back(&maCheck8);
606 mpCheckPtr.push_back(&maCheck9);
607 - mpCheckPtr.push_back(&maCheck10);
608 - mpCheckPtr.push_back(&maCheck11);
612 getSectionPosSize(aPos, aSize, FIRST_LISTITEM);
613 - Font aMemFont(rStyle.GetLabelFont());
614 - aMemFont.SetHeight(11);
615 for (vector<CheckBox*>::iterator itr = mpCheckPtr.begin(), itrEnd = mpCheckPtr.end();
616 itr != itrEnd; ++itr)
619 p->SetPosSizePixel(aPos, aSize);
620 - p->SetFont(aMemFont);
621 + p->SetFont(getLabelFont());
622 p->SetClickHdl( LINK(this, ScDPFieldPopupWindow, CheckBoxHdl) );
624 + aPos.Y() += aSize.Height() + 1;
627 getSectionPosSize(aPos, aSize, BTN_OK);
628 maBtnOk.SetPosSizePixel(aPos, aSize);
629 - maBtnOk.SetFont(aMemFont);
630 + maBtnOk.SetFont(getLabelFont());
631 maBtnOk.SetClickHdl( LINK(this, ScDPFieldPopupWindow, OKButtonHdl) );
634 getSectionPosSize(aPos, aSize, BTN_CANCEL);
635 maBtnCancel.SetPosSizePixel(aPos, aSize);
636 - maBtnCancel.SetFont(aMemFont);
637 + maBtnCancel.SetFont(getLabelFont());
640 getSectionPosSize(aPos, aSize, SCROLL_BAR_V);
641 @@ -264,6 +790,10 @@ ScDPFieldPopupWindow::ScDPFieldPopupWindow(Window* pParent) :
642 maScrollBar.EnableDrag(true);
645 +ScDPFieldPopupWindow::~ScDPFieldPopupWindow()
649 vector<ScDPFieldPopupWindow::Member>& ScDPFieldPopupWindow::getMembers()
652 @@ -271,61 +801,66 @@ vector<ScDPFieldPopupWindow::Member>& ScDPFieldPopupWindow::getMembers()
654 void ScDPFieldPopupWindow::getSectionPosSize(Point& rPos, Size& rSize, SectionType eType) const
656 - static const long nListBoxMargin = 5;
657 - static const long nBottomBtnAreaHeight = 50;
658 - static const long nInnerItemMargin = 5;
659 - static const long nScrollBarWidth = 17;
660 - static const long nBtnWidth = 60;
661 - static const long nBtnHeight = 22;
662 - static const long nBottomMargin = 10;
664 - const Size& rWndSize = GetSizePixel();
665 + const sal_uInt16 nListBoxMargin = 5;
666 + const sal_uInt16 nTopMargin = 5;
667 + const sal_uInt16 nMenuHeight = 60;
668 + const sal_uInt16 nBottomBtnAreaHeight = 50;
669 + const sal_uInt16 nInnerItemMargin = 5;
670 + const sal_uInt16 nScrollBarWidth = 17;
671 + const sal_uInt16 nBtnWidth = 60;
672 + const sal_uInt16 nBtnHeight = getLabelFont().GetHeight()*2;
673 + const sal_uInt16 nBottomMargin = 10;
674 + const sal_uInt16 nMenuListMargin = 20;
676 + Size aWndSize = Size(160, 330);
689 - rPos = Point(nListBoxMargin, nListBoxMargin);
690 + rPos = Point(nListBoxMargin, nTopMargin + nMenuHeight + nMenuListMargin);
692 - rWndSize.Width() - nListBoxMargin*2,
693 - rWndSize.Height() - nListBoxMargin - nBottomBtnAreaHeight);
694 + aWndSize.Width() - nListBoxMargin*2,
695 + aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight);
700 rPos = Point(nListBoxMargin + nInnerItemMargin,
701 - nListBoxMargin + nInnerItemMargin);
702 + nTopMargin + nMenuHeight + nMenuListMargin + nInnerItemMargin);
704 - rWndSize.Width() - nListBoxMargin*2 - nInnerItemMargin - nScrollBarWidth - 10,
705 + aWndSize.Width() - nListBoxMargin*2 - nInnerItemMargin - nScrollBarWidth - 10,
711 - long x = (rWndSize.Width() - nBtnWidth*2)/3;
712 - long y = rWndSize.Height() - nBottomMargin - nBtnHeight;
713 + long x = (aWndSize.Width() - nBtnWidth*2)/3;
714 + long y = aWndSize.Height() - nBottomMargin - nBtnHeight;
716 rSize = Size(nBtnWidth, nBtnHeight);
721 - long x = (rWndSize.Width() - nBtnWidth*2)/3*2 + nBtnWidth;
722 - long y = rWndSize.Height() - nBottomMargin - nBtnHeight;
723 + long x = (aWndSize.Width() - nBtnWidth*2)/3*2 + nBtnWidth;
724 + long y = aWndSize.Height() - nBottomMargin - nBtnHeight;
726 rSize = Size(nBtnWidth, nBtnHeight);
731 - long x = rWndSize.Width() - nListBoxMargin - nInnerItemMargin - nScrollBarWidth;
732 - long y = nListBoxMargin + nInnerItemMargin;
733 + long x = aWndSize.Width() - nListBoxMargin - nInnerItemMargin - nScrollBarWidth;
734 + long y = nTopMargin + nMenuHeight + nMenuListMargin + nInnerItemMargin;
736 - long h = rWndSize.Height() - nListBoxMargin - nBottomBtnAreaHeight - nInnerItemMargin*2;
737 + long h = aWndSize.Height() - nTopMargin - nMenuHeight - nMenuListMargin - nBottomBtnAreaHeight - nInnerItemMargin*2;
738 rSize = Size(nScrollBarWidth, h);
741 @@ -377,31 +912,26 @@ IMPL_LINK( ScDPFieldPopupWindow, ScrollHdl, ScrollBar*, EMPTYARG )
745 -ScDPFieldPopupWindow::~ScDPFieldPopupWindow()
746 +void ScDPFieldPopupWindow::MouseMove(const MouseEvent& rMEvt)
749 + ScMenuFloatingWindow::MouseMove(rMEvt);
751 + size_t nSelectedMenu = getSelectedMenuItem();
752 + if (nSelectedMenu == MENU_NOT_SELECTED)
753 + queueCloseSubMenu();
756 void ScDPFieldPopupWindow::Paint(const Rectangle& rRect)
758 - Window::Paint(rRect);
759 + ScMenuFloatingWindow::Paint(rRect);
761 const StyleSettings& rStyle = GetSettings().GetStyleSettings();
762 - Color aBackColor = rStyle.GetMenuColor();
763 - Color aBorderColor = rStyle.GetShadowColor();
764 Color aMemberBackColor = rStyle.GetFieldColor();
769 - // Window background
770 - SetFillColor(aBackColor);
771 - SetLineColor(aBorderColor);
772 - getSectionPosSize(aPos, aSize, WHOLE);
773 - DrawRect(Rectangle(aPos,aSize));
775 // Member list box background
776 SetFillColor(aMemberBackColor);
779 getSectionPosSize(aPos, aSize, LISTBOX_AREA);
780 DrawRect(Rectangle(aPos,aSize));
782 @@ -472,7 +1002,7 @@ ScDPFieldPopupWindow::ExtendedData* ScDPFieldPopupWindow::getExtendedData()
783 return mpExtendedData.get();
786 -void ScDPFieldPopupWindow::setOKAction(OKAction* p)
787 +void ScDPFieldPopupWindow::setOKAction(Action* p)
791 diff --git sc/source/ui/cctrl/dpcontrol.src sc/source/ui/cctrl/dpcontrol.src
793 index 0000000..6c5fffe
795 +++ sc/source/ui/cctrl/dpcontrol.src
797 +/*************************************************************************
799 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
801 + * Copyright 2008 by Sun Microsystems, Inc.
803 + * OpenOffice.org - a multi-platform office productivity suite
805 + * $RCSfile: globstr.src,v $
806 + * $Revision: 1.74.96.1 $
808 + * This file is part of OpenOffice.org.
810 + * OpenOffice.org is free software: you can redistribute it and/or modify
811 + * it under the terms of the GNU Lesser General Public License version 3
812 + * only, as published by the Free Software Foundation.
814 + * OpenOffice.org is distributed in the hope that it will be useful,
815 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
816 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
817 + * GNU Lesser General Public License version 3 for more details
818 + * (a copy is included in the LICENSE file that accompanied this code).
820 + * You should have received a copy of the GNU Lesser General Public License
821 + * version 3 along with OpenOffice.org. If not, see
822 + * <http://www.openoffice.org/license.html>
823 + * for a copy of the LGPLv3 License.
825 + ************************************************************************/
827 +#include "dpcontrol.hrc"
829 +Resource RID_SC_DPCONTROL
831 + String STR_MENU_SORT_ASC
833 + Text [ en-US ] = "Sort Ascending" ;
836 + String STR_MENU_SORT_DESC
838 + Text [ en-US ] = "Sort Descending" ;
841 + String STR_MENU_SORT_CUSTOM
843 + Text [ en-US ] = "Custom Sort" ;
846 diff --git sc/source/ui/cctrl/makefile.mk sc/source/ui/cctrl/makefile.mk
847 index 8e8add3..70095d8 100644
848 --- sc/source/ui/cctrl/makefile.mk
849 +++ sc/source/ui/cctrl/makefile.mk
850 @@ -45,7 +45,8 @@ LIBTARGET=NO
851 # --- Files --------------------------------------------------------
854 - $(SLO)$/tbzoomsliderctrl.obj
855 + $(SLO)$/tbzoomsliderctrl.obj \
856 + $(SLO)$/dpcontrol.obj
859 $(SLO)$/popmenu.obj \
860 @@ -55,6 +56,10 @@ SLOFILES = \
861 $(SLO)$/editfield.obj \
868 LIB1TARGET=$(SLB)$/$(TARGET).lib
870 $(SLO)$/popmenu.obj \
871 @@ -63,6 +68,7 @@ LIB1OBJFILES= \
872 $(SLO)$/dpcontrol.obj \
873 $(SLO)$/tbzoomsliderctrl.obj
876 # --- Tagets -------------------------------------------------------
879 diff --git sc/source/ui/inc/dbfunc.hxx sc/source/ui/inc/dbfunc.hxx
880 index d894e48..b494ae6 100644
881 --- sc/source/ui/inc/dbfunc.hxx
882 +++ sc/source/ui/inc/dbfunc.hxx
883 @@ -101,6 +101,7 @@ public:
884 void UngroupDataPilot();
885 void DataPilotInput( const ScAddress& rPos, const String& rString );
887 + bool DataPilotSort( const ScAddress& rPos, bool bAscending, sal_uInt16* pUserListId = NULL );
888 BOOL DataPilotMove( const ScRange& rSource, const ScAddress& rDest );
890 BOOL HasSelectionForDrillDown( USHORT& rOrientation );
891 diff --git sc/source/ui/inc/dpcontrol.hrc sc/source/ui/inc/dpcontrol.hrc
893 index 0000000..2ca698d
895 +++ sc/source/ui/inc/dpcontrol.hrc
897 +/*************************************************************************
899 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
901 + * Copyright 2008 by Sun Microsystems, Inc.
903 + * OpenOffice.org - a multi-platform office productivity suite
905 + * $RCSfile: protectiondlg.hrc,v $
906 + * $Revision: 1.1.2.1 $
908 + * This file is part of OpenOffice.org.
910 + * OpenOffice.org is free software: you can redistribute it and/or modify
911 + * it under the terms of the GNU Lesser General Public License version 3
912 + * only, as published by the Free Software Foundation.
914 + * OpenOffice.org is distributed in the hope that it will be useful,
915 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
916 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
917 + * GNU Lesser General Public License version 3 for more details
918 + * (a copy is included in the LICENSE file that accompanied this code).
920 + * You should have received a copy of the GNU Lesser General Public License
921 + * version 3 along with OpenOffice.org. If not, see
922 + * <http://www.openoffice.org/license.html>
923 + * for a copy of the LGPLv3 License.
925 + ************************************************************************/
927 +#ifndef __DPCONTROL_HRC__
928 +#define __DPCONTROL_HRC__
932 +#define STR_MENU_SORT_ASC 1
933 +#define STR_MENU_SORT_DESC 2
934 +#define STR_MENU_SORT_CUSTOM 3
937 diff --git sc/source/ui/inc/dpcontrol.hxx sc/source/ui/inc/dpcontrol.hxx
938 index 6a28354..64d56d3 100644
939 --- sc/source/ui/inc/dpcontrol.hxx
940 +++ sc/source/ui/inc/dpcontrol.hxx
942 #include "vcl/floatwin.hxx"
943 #include "vcl/button.hxx"
944 #include "vcl/scrbar.hxx"
945 +#include "vcl/timer.hxx"
947 +#include <boost/shared_ptr.hpp>
951 @@ -80,43 +82,128 @@ private:
953 // ============================================================================
956 - * This class implements a popup window for field button, for quick access
957 - * of hide-item list, and possibly more stuff related to field options.
959 -class ScDPFieldPopupWindow : public FloatingWindow
960 +class ScMenuFloatingWindow : public FloatingWindow
965 + * Action to perform when an event takes place. Create a sub-class of
966 + * this to implement the desired action.
971 virtual void execute() = 0;
974 + explicit ScMenuFloatingWindow(Window* pParent);
975 + virtual ~ScMenuFloatingWindow();
977 + virtual void MouseMove(const MouseEvent& rMEvt);
978 + virtual void MouseButtonDown(const MouseEvent& rMEvt);
979 + virtual void MouseButtonUp(const MouseEvent& rMEvt);
980 + virtual void KeyInput(const KeyEvent& rKEvt);
981 + virtual void Paint(const Rectangle& rRect);
983 + void addMenuItem(const ::rtl::OUString& rText, bool bEnabled, Action* pAction);
984 + ScMenuFloatingWindow* addSubMenuItem(const ::rtl::OUString& rText, bool bEnabled);
987 + void drawMenuItem(size_t nPos);
988 + void drawAllMenuItems();
989 + const Font& getLabelFont() const;
991 + void executeMenu(size_t nPos);
992 + void setSelectedMenuItem(size_t nPos, bool bSubMenuTimer = true);
993 + size_t getSelectedMenuItem() const;
994 + void queueLaunchSubMenu(size_t nPos, ScMenuFloatingWindow* pMenu);
995 + void queueCloseSubMenu();
996 + void launchSubMenu(bool bSetMenuPos);
1000 + struct SubMenuItem;
1001 + void handleMenuTimeout(SubMenuItem* pTimer);
1003 + enum NotificationType { SUBMENU_FOCUSED };
1004 + void notify(NotificationType eType);
1006 + void resetMenu(bool bSetMenuPos);
1007 + void resizeToFitMenuItems();
1008 + void selectMenuItem(size_t nPos, bool bSelected, bool bSubMenuTimer);
1009 + void highlightMenuItem(size_t nPos, bool bSelected);
1011 + void getMenuItemPosSize(Point& rPos, Size& rSize, size_t nPos) const;
1012 + size_t getEnclosingMenuItem(const Point& rPos) const;
1014 + DECL_LINK( EndPopupHdl, void* );
1019 + ::rtl::OUString maText;
1022 + ::boost::shared_ptr<Action> mpAction;
1023 + ::boost::shared_ptr<ScMenuFloatingWindow> mpSubMenuWin;
1028 + ::std::vector<MenuItem> maMenuItems;
1030 + struct SubMenuItem
1033 + ScMenuFloatingWindow* mpSubMenu;
1036 + DECL_LINK( TimeoutHdl, void* );
1038 + SubMenuItem(ScMenuFloatingWindow* pParent);
1042 + ScMenuFloatingWindow* mpParent;
1044 + SubMenuItem maOpenTimer;
1045 + SubMenuItem maCloseTimer;
1049 + size_t mnSelectedMenu;
1050 + size_t mnClickedMenu;
1052 + ScMenuFloatingWindow* mpParentMenu;
1053 + ScMenuFloatingWindow* mpActiveSubMenu;
1055 + bool mbActionFired;
1058 +// ============================================================================
1061 + * This class implements a popup window for field button, for quick access
1062 + * of hide-item list, and possibly more stuff related to field options.
1064 +class ScDPFieldPopupWindow : public ScMenuFloatingWindow
1068 * Extended data that the client code may need to store. Create a
1069 * sub-class of this and store data there.
1071 struct ExtendedData {};
1074 - * Action to perform when the OK button is pressed. Create a sub-class of
1075 - * this to implement the desired action.
1080 - virtual void execute() = 0;
1083 explicit ScDPFieldPopupWindow(Window* pParent);
1084 virtual ~ScDPFieldPopupWindow();
1086 + virtual void MouseMove(const MouseEvent& rMEvt);
1087 virtual void Paint(const Rectangle& rRect);
1089 void setMemberSize(size_t n);
1090 void addMember(const ::rtl::OUString& rName, bool bVisible);
1093 void getResult(::std::hash_map< ::rtl::OUString, bool, ::rtl::OUStringHash>& rResult);
1094 void close(bool bOK);
1096 @@ -132,7 +219,7 @@ public:
1098 ExtendedData* getExtendedData();
1100 - void setOKAction(OKAction* p);
1101 + void setOKAction(Action* p);
1105 @@ -143,6 +230,17 @@ private:
1109 + class CancelButton : public ::CancelButton
1112 + CancelButton(ScDPFieldPopupWindow* pParent);
1114 + virtual void Click();
1117 + ScDPFieldPopupWindow* mpParent;
1120 ::std::vector<Member>& getMembers();
1123 @@ -173,8 +271,6 @@ private:
1127 - CheckBox maCheck10;
1128 - CheckBox maCheck11;
1130 ScrollBar maScrollBar;
1132 @@ -185,9 +281,9 @@ private:
1134 ::std::vector<Member> maMembers;
1135 ::std::auto_ptr<ExtendedData> mpExtendedData;
1136 - ::std::auto_ptr<OKAction> mpOKAction;
1137 + ::std::auto_ptr<Action> mpOKAction;
1139 - size_t mnScrollPos;
1140 + size_t mnScrollPos;
1144 diff --git sc/source/ui/view/dbfunc3.cxx sc/source/ui/view/dbfunc3.cxx
1145 index d83add1..f58d9b5 100644
1146 --- sc/source/ui/view/dbfunc3.cxx
1147 +++ sc/source/ui/view/dbfunc3.cxx
1149 #include "patattr.hxx"
1150 #include "unonames.hxx"
1152 +#include "userlist.hxx"
1155 +#include <hash_map>
1160 using namespace com::sun::star;
1161 using ::com::sun::star::uno::Any;
1162 @@ -94,8 +98,13 @@ using ::com::sun::star::beans::XPropertySet;
1163 using ::com::sun::star::container::XNameAccess;
1164 using ::com::sun::star::sheet::XDimensionsSupplier;
1165 using ::rtl::OUString;
1166 +using ::rtl::OUStringHash;
1167 using ::rtl::OUStringBuffer;
1168 using ::std::auto_ptr;
1170 +using ::std::vector;
1171 +using ::std::hash_map;
1172 +using ::std::hash_set;
1174 // STATIC DATA -----------------------------------------------------------
1176 @@ -1695,6 +1704,134 @@ void lcl_MoveToEnd( ScDPSaveDimension& rDim, const String& rItemName )
1177 // puts it to the end of the list even if it was in the list before.
1180 +bool ScDBFunc::DataPilotSort( const ScAddress& rPos, bool bAscending, sal_uInt16* pUserListId )
1182 + ScDocument* pDoc = GetViewData()->GetDocument();
1183 + ScDPObject* pDPObj = pDoc->GetDPAtCursor(rPos.Col(), rPos.Row(), rPos.Tab());
1187 + // We need to run this to get all members later.
1188 + pDPObj->BuildAllDimensionMembers();
1190 + USHORT nOrientation;
1191 + long nDimIndex = pDPObj->GetHeaderDim(rPos, nOrientation);
1192 + if (nDimIndex < 0)
1193 + // Invalid dimension index. Bail out.
1197 + ScDPSaveData* pSaveData = pDPObj->GetSaveData();
1201 + ScDPSaveData aNewSaveData(*pSaveData);
1202 + String aDimName = pDPObj->GetDimName(nDimIndex, bDataLayout);
1203 + ScDPSaveDimension* pSaveDim = aNewSaveData.GetDimensionByName(aDimName);
1207 + typedef ScDPSaveDimension::MemberList MemList;
1208 + const MemList& rDimMembers = pSaveDim->GetMembers();
1209 + list<OUString> aMembers;
1210 + hash_set<OUString, ::rtl::OUStringHash> aMemberSet;
1211 + size_t nMemberCount = 0;
1212 + for (MemList::const_iterator itr = rDimMembers.begin(), itrEnd = rDimMembers.end();
1213 + itr != itrEnd; ++itr)
1215 + ScDPSaveMember* pMem = *itr;
1216 + aMembers.push_back(pMem->GetName());
1217 + aMemberSet.insert(pMem->GetName());
1221 + // Sort the member list in ascending order.
1224 + // Collect and rank those custom sort strings that also exist in the member name list.
1226 + typedef hash_map<OUString, sal_uInt16, OUStringHash> UserSortMap;
1227 + UserSortMap aSubStrs;
1228 + sal_uInt16 nSubCount = 0;
1231 + ScUserList* pUserList = ScGlobal::GetUserList();
1236 + sal_uInt16 n = pUserList->GetCount();
1237 + if (!n || *pUserListId >= n)
1241 + ScUserListData* pData = static_cast<ScUserListData*>((*pUserList)[*pUserListId]);
1244 + sal_uInt16 n = pData->GetSubCount();
1245 + for (sal_uInt16 i = 0; i < n; ++i)
1247 + OUString aSub = pData->GetSubStr(i);
1248 + if (!aMemberSet.count(aSub))
1249 + // This string doesn't exist in the member name set. Don't add this.
1252 + aSubStrs.insert(UserSortMap::value_type(aSub, nSubCount++));
1257 + // Rank all members.
1259 + vector<OUString> aRankedNames(nMemberCount);
1260 + sal_uInt16 nCurStrId = 0;
1261 + for (list<OUString>::const_iterator itr = aMembers.begin(), itrEnd = aMembers.end();
1262 + itr != itrEnd; ++itr)
1264 + OUString aName = *itr;
1265 + sal_uInt16 nRank = 0;
1266 + UserSortMap::const_iterator itrSub = aSubStrs.find(aName);
1267 + if (itrSub == aSubStrs.end())
1268 + nRank = nSubCount + nCurStrId++;
1270 + nRank = itrSub->second;
1273 + nRank = nMemberCount - nRank - 1;
1275 + aRankedNames[nRank] = aName;
1278 + // Re-order ScDPSaveMember instances with the new ranks.
1280 + for (vector<OUString>::const_iterator itr = aRankedNames.begin(), itrEnd = aRankedNames.end();
1281 + itr != itrEnd; ++itr)
1283 + const ScDPSaveMember* pOldMem = pSaveDim->GetExistingMemberByName(*itr);
1285 + // All members are supposed to be present.
1288 + ScDPSaveMember* pNewMem = new ScDPSaveMember(*pOldMem);
1289 + pSaveDim->AddMember(pNewMem);
1292 + // Set the sorting mode to manual for now. We may introduce a new sorting
1295 + sheet::DataPilotFieldSortInfo aSortInfo;
1296 + aSortInfo.Mode = sheet::DataPilotFieldSortMode::MANUAL;
1297 + pSaveDim->SetSortInfo(&aSortInfo);
1299 + // Update the datapilot with the newly sorted field members.
1301 + auto_ptr<ScDPObject> pNewObj(new ScDPObject(*pDPObj));
1302 + pNewObj->SetSaveData(aNewSaveData);
1303 + ScDBDocFunc aFunc(*GetViewData()->GetDocShell());
1305 + return aFunc.DataPilotUpdate(pDPObj, pNewObj.get(), true, false);
1308 BOOL ScDBFunc::DataPilotMove( const ScRange& rSource, const ScAddress& rDest )
1311 diff --git sc/source/ui/view/gridwin2.cxx sc/source/ui/view/gridwin2.cxx
1312 index 63ce024..72a6606 100644
1313 --- sc/source/ui/view/gridwin2.cxx
1314 +++ sc/source/ui/view/gridwin2.cxx
1316 #include "dpshttab.hxx"
1317 #include "dbdocfun.hxx"
1318 #include "dpcontrol.hxx"
1319 +#include "dpcontrol.hrc"
1320 +#include "strload.hxx"
1321 +#include "userlist.hxx"
1323 #include <com/sun/star/sheet/DataPilotFieldOrientation.hpp>
1324 #include "scabstdlg.hxx" //CHINA001
1325 @@ -778,7 +781,7 @@ struct DPFieldPopupData : public ScDPFieldPopupWindow::ExtendedData
1329 -class DPFieldPopupOKAction : public ScDPFieldPopupWindow::OKAction
1330 +class DPFieldPopupOKAction : public ScMenuFloatingWindow::Action
1333 explicit DPFieldPopupOKAction(ScGridWindow* p) :
1334 @@ -792,6 +795,39 @@ private:
1335 ScGridWindow* mpGridWindow;
1338 +class PopupSortAction : public ScMenuFloatingWindow::Action
1341 + enum SortType { ASCENDING, DESCENDING, CUSTOM };
1343 + explicit PopupSortAction(const ScAddress& rPos, SortType eType, sal_uInt16 nUserListIndex, ScTabViewShell* pViewShell) :
1344 + maPos(rPos), meType(eType), mnUserListIndex(nUserListIndex), mpViewShell(pViewShell) {}
1346 + virtual void execute()
1351 + mpViewShell->DataPilotSort(maPos, true);
1354 + mpViewShell->DataPilotSort(maPos, false);
1357 + mpViewShell->DataPilotSort(maPos, true, &mnUserListIndex);
1367 + sal_uInt16 mnUserListIndex;
1368 + ScTabViewShell* mpViewShell;
1373 void ScGridWindow::DPLaunchFieldPopupMenu(
1374 @@ -814,11 +850,48 @@ void ScGridWindow::DPLaunchFieldPopupMenu(
1375 mpDPFieldPopup.reset(new ScDPFieldPopupWindow(this));
1376 mpDPFieldPopup->setExtendedData(pDPData.release());
1377 mpDPFieldPopup->setOKAction(new DPFieldPopupOKAction(this));
1378 - sal_Int32 n = rLabelData.maMembers.getLength();
1379 - mpDPFieldPopup->setMemberSize(n);
1380 - for (sal_Int32 i = 0; i < n; ++i)
1381 - mpDPFieldPopup->addMember(rLabelData.maMembers[i], rLabelData.maVisible[i]);
1382 - mpDPFieldPopup->initMembers();
1384 + sal_Int32 n = rLabelData.maMembers.getLength();
1385 + mpDPFieldPopup->setMemberSize(n);
1386 + for (sal_Int32 i = 0; i < n; ++i)
1387 + mpDPFieldPopup->addMember(rLabelData.maMembers[i], rLabelData.maVisible[i]);
1388 + mpDPFieldPopup->initMembers();
1391 + vector<OUString> aUserSortNames;
1392 + ScUserList* pUserList = ScGlobal::GetUserList();
1395 + sal_uInt16 n = pUserList->GetCount();
1396 + aUserSortNames.reserve(n);
1397 + for (sal_uInt16 i = 0; i < n; ++i)
1399 + ScUserListData* pData = static_cast<ScUserListData*>((*pUserList)[i]);
1400 + aUserSortNames.push_back(pData->GetString());
1404 + // Populate the menus.
1405 + ScTabViewShell* pViewShell = pViewData->GetViewShell();
1406 + mpDPFieldPopup->addMenuItem(
1407 + ScRscStrLoader(RID_SC_DPCONTROL, STR_MENU_SORT_ASC).GetString(), true,
1408 + new PopupSortAction(rPos, PopupSortAction::ASCENDING, 0, pViewShell));
1409 + mpDPFieldPopup->addMenuItem(
1410 + ScRscStrLoader(RID_SC_DPCONTROL, STR_MENU_SORT_DESC).GetString(), true,
1411 + new PopupSortAction(rPos, PopupSortAction::DESCENDING, 0, pViewShell));
1412 + ScMenuFloatingWindow* pSubMenu = mpDPFieldPopup->addSubMenuItem(
1413 + ScRscStrLoader(RID_SC_DPCONTROL, STR_MENU_SORT_CUSTOM).GetString(), !aUserSortNames.empty());
1415 + if (pSubMenu && !aUserSortNames.empty())
1417 + size_t n = aUserSortNames.size();
1418 + for (size_t i = 0; i < n; ++i)
1420 + pSubMenu->addMenuItem(
1421 + aUserSortNames[i], true,
1422 + new PopupSortAction(rPos, PopupSortAction::CUSTOM, i, pViewShell));
1426 mpDPFieldPopup->SetPopupModeEndHdl( LINK(this, ScGridWindow, PopupModeEndHdl) );
1427 Rectangle aCellRect(rSrcPos, rSrcSize);
1428 diff --git sc/util/makefile.mk sc/util/makefile.mk
1429 index 88e0594..bdf4954 100644
1430 --- sc/util/makefile.mk
1431 +++ sc/util/makefile.mk
1432 @@ -58,6 +58,7 @@ RESLIB1LIST=\
1433 $(SRS)$/formdlgs.srs \
1434 $(SRS)$/pagedlg.srs \
1435 $(SRS)$/navipi.srs \
1436 + $(SRS)$/cctrl.srs \
1437 $(SOLARCOMMONRESDIR)$/sfx.srs