LibreOffice Module sw (master)  1
SidebarTxtControl.cxx
Go to the documentation of this file.
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
5  * This Source Code Form is subject to the terms of the Mozilla Public
6  * License, v. 2.0. If a copy of the MPL was not distributed with this
7  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
11  * Licensed to the Apache Software Foundation (ASF) under one or more
12  * contributor license agreements. See the NOTICE file distributed
13  * with this work for additional information regarding copyright
14  * ownership. The ASF licenses this file to you under the Apache
15  * License, Version 2.0 (the "License"); you may not use this file
16  * except in compliance with the License. You may obtain a copy of
17  * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18  */
19 
20 #include "SidebarTxtControl.hxx"
21 
22 #include "SidebarTxtControlAcc.hxx"
23 #include <docsh.hxx>
24 #include <doc.hxx>
25 
26 #include <PostItMgr.hxx>
27 #include <edtwin.hxx>
28 
29 #include <cmdid.h>
30 #include <strings.hrc>
31 
33 
34 #include <sfx2/viewfrm.hxx>
35 #include <sfx2/bindings.hxx>
36 #include <sfx2/dispatch.hxx>
37 #include <sfx2/sfxhelp.hxx>
38 
39 #include <vcl/commandevent.hxx>
40 #include <vcl/svapp.hxx>
41 #include <vcl/help.hxx>
42 #include <vcl/weld.hxx>
43 #include <vcl/gradient.hxx>
44 #include <vcl/settings.hxx>
45 
46 #include <editeng/outliner.hxx>
47 #include <editeng/editeng.hxx>
48 #include <editeng/editview.hxx>
49 #include <editeng/flditem.hxx>
50 #include <comphelper/lok.hxx>
51 #include <sfx2/lokhelper.hxx>
52 
53 #include <uitool.hxx>
54 #include <view.hxx>
55 #include <wrtsh.hxx>
56 #include <AnnotationWin.hxx>
57 #include <redline.hxx>
58 #include <memory>
59 
60 namespace sw { namespace sidebarwindows {
61 
63  WinBits nBits,
64  SwView& rDocView,
65  SwPostItMgr& rPostItMgr )
66  : Control( &rSidebarWin, nBits )
67  , mrSidebarWin( rSidebarWin )
68  , mrDocView( rDocView )
69  , mrPostItMgr( rPostItMgr )
70 {
72 }
73 
75 {
76  disposeOnce();
77 }
78 
80 {
83 }
84 
86 {
88 }
89 
91 {
92  Window::GetFocus();
93  if ( !mrSidebarWin.IsMouseOver() )
94  {
95  Invalidate();
96  }
97 }
98 
100 {
101  // write the visible text back into the SwField
103 
104  Window::LoseFocus();
105  if ( !mrSidebarWin.IsMouseOver() )
106  {
107  Invalidate();
108  }
109 }
110 
112 {
113  const char* pResId = nullptr;
114  switch( mrSidebarWin.GetLayoutStatus() )
115  {
116  case SwPostItHelper::INSERTED: pResId = STR_REDLINE_INSERT; break;
117  case SwPostItHelper::DELETED: pResId = STR_REDLINE_DELETE; break;
118  default: pResId = nullptr;
119  }
120 
121  SwContentAtPos aContentAtPos( IsAttrAtPos::Redline );
122  if ( pResId &&
124  {
125  OUString sText = SwResId(pResId) + ": " +
126  aContentAtPos.aFnd.pRedl->GetAuthorString() + " - " +
127  GetAppLangDateTimeString( aContentAtPos.aFnd.pRedl->GetTimeStamp() );
129  }
130 }
131 
132 void SidebarTextControl::Draw(OutputDevice* pDev, const Point& rPt, const Size& rSz, DrawFlags)
133 {
134  //Take the control's height, but overwrite the scrollbar area if there was one
135  Size aSize(PixelToLogic(GetSizePixel()));
136  aSize.setWidth( rSz.Width() );
137 
138  if ( GetTextView() )
139  {
140  GetTextView()->GetOutliner()->Draw(pDev, tools::Rectangle(rPt, aSize));
141  }
142 
144  {
146  pDev->DrawLine( PixelToLogic( GetPosPixel(), pDev->GetMapMode() ),
148  Point( GetSizePixel().Width(),
149  GetSizePixel().Height() ), pDev->GetMapMode() ) );
150  pDev->DrawLine( PixelToLogic( GetPosPixel() +
151  Point( GetSizePixel().Width(),0), pDev->GetMapMode() ),
153  Point( 0, GetSizePixel().Height() ), pDev->GetMapMode() ) );
154  }
155 }
156 
158 {
159  if (!rRenderContext.GetSettings().GetStyleSettings().GetHighContrastMode())
160  {
162  {
163  rRenderContext.DrawGradient(tools::Rectangle(Point(0,0), rRenderContext.PixelToLogic(GetSizePixel())),
164  Gradient(GradientStyle::Linear, mrSidebarWin.ColorDark(), mrSidebarWin.ColorDark()));
165  }
166  else
167  {
168  rRenderContext.DrawGradient(tools::Rectangle(Point(0,0), rRenderContext.PixelToLogic(GetSizePixel())),
169  Gradient(GradientStyle::Linear, mrSidebarWin.ColorLight(), mrSidebarWin.ColorDark()));
170  }
171  }
172 
173  if (GetTextView())
174  {
175  GetTextView()->Paint(rRect, &rRenderContext);
176  }
177 
179  {
180  rRenderContext.SetLineColor(mrSidebarWin.GetChangeColor());
181  rRenderContext.DrawLine(rRenderContext.PixelToLogic(GetPosPixel()),
182  rRenderContext.PixelToLogic(GetPosPixel() + Point(GetSizePixel().Width(),
183  GetSizePixel().Height())));
184  rRenderContext.DrawLine(rRenderContext.PixelToLogic(GetPosPixel() + Point(GetSizePixel().Width(),
185  0)),
186  rRenderContext.PixelToLogic(GetPosPixel() + Point(0,
187  GetSizePixel().Height())));
188  }
189 }
190 
192 {
193  tools::Rectangle aRectangle;
194 
195  if (!pRectangle)
196  {
197  Push(PushFlags::MAPMODE);
198  EnableMapMode();
199  aRectangle = tools::Rectangle(Point(0, 0), PixelToLogic(GetSizePixel()));
200  Pop();
201  }
202  else
203  aRectangle = *pRectangle;
204 
205  // Convert from relative twips to absolute ones.
206  vcl::Window& rParent = mrSidebarWin.EditWin();
207  Point aOffset(GetOutOffXPixel() - rParent.GetOutOffXPixel(), GetOutOffYPixel() - rParent.GetOutOffYPixel());
208  rParent.Push(PushFlags::MAPMODE);
209  rParent.EnableMapMode();
210  aOffset = rParent.PixelToLogic(aOffset);
211  rParent.Pop();
212  aRectangle.Move(aOffset.getX(), aOffset.getY());
213 
214  OString sRectangle = aRectangle.toString();
215  SwWrtShell& rWrtShell = mrDocView.GetWrtShell();
216  SfxLokHelper::notifyInvalidation(rWrtShell.GetSfxViewShell(), sRectangle);
217 }
218 
220 {
221  if (getenv("SW_DEBUG") && rKeyEvt.GetKeyCode().GetCode() == KEY_F12)
222  {
223  if (rKeyEvt.GetKeyCode().IsShift())
224  {
226  return;
227  }
228  }
229 
230  const vcl::KeyCode& rKeyCode = rKeyEvt.GetKeyCode();
231  sal_uInt16 nKey = rKeyCode.GetCode();
232  if ( ( rKeyCode.IsMod1() && rKeyCode.IsMod2() ) &&
233  ( (nKey == KEY_PAGEUP) || (nKey == KEY_PAGEDOWN) ) )
234  {
236  }
237  else if ( nKey == KEY_ESCAPE ||
238  ( rKeyCode.IsMod1() &&
239  ( nKey == KEY_PAGEUP ||
240  nKey == KEY_PAGEDOWN ) ) )
241  {
243  }
244  else if ( rKeyCode.GetFullCode() == KEY_INSERT )
245  {
247  }
248  else
249  {
250  // MakeVisible can lose our MapMode, save it.
251  auto oldMapMode = GetMapMode();
252  //let's make sure we see our note
255  SetMapMode(oldMapMode);
256 
257  long aOldHeight = mrSidebarWin.GetPostItTextHeight();
258  bool bDone = false;
259 
261  if ( !( (nKey == KEY_Z || nKey == KEY_Y) && rKeyCode.IsMod1()) )
262  {
263  bool bIsProtected = mrSidebarWin.IsProtected();
264  if ( !bIsProtected || !EditEngine::DoesKeyChangeText(rKeyEvt) )
265  {
266  bDone = GetTextView() && GetTextView()->PostKeyEvent( rKeyEvt );
267  }
268  else
269  {
270  std::unique_ptr<weld::Builder> xBuilder(Application::CreateBuilder(GetFrameWeld(), "modules/swriter/ui/inforeadonlydialog.ui"));
271  std::unique_ptr<weld::MessageDialog> xQuery(xBuilder->weld_message_dialog("InfoReadonlyDialog"));
272  xQuery->run();
273  }
274  }
275  if (bDone)
277  else
278  {
279  // write back data first when showing navigator
280  if ( nKey==KEY_F5 )
282  if (!mrDocView.KeyInput(rKeyEvt))
283  Window::KeyInput(rKeyEvt);
284  }
285  }
286 
288 }
289 
291 {
292  if ( GetTextView() )
293  {
294  OutlinerView* pOutlinerView( GetTextView() );
295  pOutlinerView->MouseMove( rMEvt );
296  // mba: why does OutlinerView not handle the modifier setting?!
297  // this forces the postit to handle *all* pointer types
298  SetPointer( pOutlinerView->GetPointer( rMEvt.GetPosPixel() ) );
299 
300  const EditView& aEV = pOutlinerView->GetEditView();
301  const SvxFieldItem* pItem = aEV.GetFieldUnderMousePointer();
302  if ( pItem )
303  {
304  const SvxFieldData* pField = pItem->GetField();
305  const SvxURLField* pURL = dynamic_cast<const SvxURLField*>( pField );
306  if ( pURL )
307  {
308  OUString sText(SfxHelp::GetURLHelpText(pURL->GetURL()));
310  this, PixelToLogic(tools::Rectangle(GetPosPixel(), Size(50, 10))), sText);
311  }
312  }
313  }
314 }
315 
317 {
318  if ( GetTextView() )
319  {
320  SvtSecurityOptions aSecOpts;
321  bool bExecuteMod = aSecOpts.IsOptionSet( SvtSecurityOptions::EOption::CtrlClickHyperlink);
322 
323  if ( !bExecuteMod || (rMEvt.GetModifier() == KEY_MOD1))
324  {
325  const EditView& aEV = GetTextView()->GetEditView();
326  const SvxFieldItem* pItem = aEV.GetFieldUnderMousePointer();
327  if ( pItem )
328  {
329  const SvxFieldData* pField = pItem->GetField();
330  const SvxURLField* pURL = dynamic_cast<const SvxURLField*>( pField );
331  if ( pURL )
332  {
333  GetTextView()->MouseButtonDown( rMEvt );
335  const OUString& sURL( pURL->GetURL() );
336  const OUString& sTarget( pURL->GetTargetFrame() );
337  ::LoadURL(rSh, sURL, LoadUrlFlags::NONE, sTarget);
338  return;
339  }
340  }
341  }
342  }
343 
344  GrabFocus();
345  if ( GetTextView() )
346  {
347  GetTextView()->MouseButtonDown( rMEvt );
348  }
350 }
351 
353 {
354  if ( GetTextView() )
355  GetTextView()->MouseButtonUp( rMEvt );
356 }
357 
358 IMPL_LINK( SidebarTextControl, OnlineSpellCallback, SpellCallbackInfo&, rInfo, void )
359 {
360  if ( rInfo.nCommand == SpellCallbackCommand::STARTSPELLDLG )
361  {
362  mrDocView.GetViewFrame()->GetDispatcher()->Execute( FN_SPELL_GRAMMAR_DIALOG, SfxCallMode::ASYNCHRON);
363  }
364 }
365 
367 {
368  if ( rCEvt.GetCommand() == CommandEventId::ContextMenu )
369  {
370  if ( !mrSidebarWin.IsProtected() &&
371  GetTextView() &&
373  {
374  Link<SpellCallbackInfo&,void> aLink = LINK(this, SidebarTextControl, OnlineSpellCallback);
376  }
377  else
378  {
379  Point aPos;
380  if (rCEvt.IsMouseEvent())
381  aPos = rCEvt.GetMousePosPixel();
382  else
383  {
384  const Size aSize = GetSizePixel();
385  aPos = Point( aSize.getWidth()/2, aSize.getHeight()/2 );
386  }
387  SfxDispatcher::ExecutePopup(this, &aPos);
388  }
389  }
390  else
391  if (rCEvt.GetCommand() == CommandEventId::Wheel)
392  {
394  {
395  const CommandWheelData* pData = rCEvt.GetWheelData();
396  if (pData->IsShift() || pData->IsMod1() || pData->IsMod2())
397  {
399  }
400  else
401  {
402  HandleScrollCommand( rCEvt, nullptr , mrSidebarWin.Scrollbar());
403  }
404  }
405  else
406  {
408  }
409  }
410  else
411  {
412  if ( GetTextView() )
413  GetTextView()->Command( rCEvt );
414  else
415  Window::Command(rCEvt);
416  }
417 }
418 
420 {
421  if (GetTextView())
422  return GetTextView()->GetSurroundingText();
423  return OUString();
424 }
425 
427 {
428  if( GetTextView() )
430  else
431  return Selection( 0, 0 );
432 }
433 
434 css::uno::Reference< css::accessibility::XAccessible > SidebarTextControl::CreateAccessible()
435 {
436 
438  css::uno::Reference< css::awt::XWindowPeer > xWinPeer( pAcc );
439  SetWindowPeer( xWinPeer, pAcc );
440 
441  css::uno::Reference< css::accessibility::XAccessible > xAcc( xWinPeer, css::uno::UNO_QUERY );
442  return xAcc;
443 }
444 
445 } } // end of namespace sw::sidebarwindows
446 
447 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
bool IsOptionSet(EOption eOption) const
virtual Point GetPosPixel() const
bool MouseButtonDown(const MouseEvent &)
SfxViewFrame * GetViewFrame() const
long Width() const
virtual void Command(const CommandEvent &rCEvt) override
bool IsMod1() const
const SvxFieldItem * GetFieldUnderMousePointer() const
void ExecuteSpellPopup(const Point &rPosPixel, Link< SpellCallbackInfo &, void > const *pCallBack)
OUString const & GetAuthorString(sal_uInt16 nPos=0) const
Definition: docredln.cxx:1718
SwPostItHelper::SwLayoutStatus GetLayoutStatus() const
#define KEY_PAGEDOWN
std::unique_ptr< ContentProperties > pData
virtual css::uno::Reference< css::accessibility::XAccessible > CreateAccessible() override
#define KEY_PAGEUP
virtual void MouseMove(const MouseEvent &rMEvt) override
long GetOutOffXPixel() const
const StyleSettings & GetStyleSettings() const
bool MouseButtonUp(const MouseEvent &)
IMPL_LINK(SidebarTextControl, OnlineSpellCallback, SpellCallbackInfo &, rInfo, void)
virtual Size GetSizePixel() const
#define KEY_MOD1
void Draw(OutputDevice *pOutDev, const tools::Rectangle &rOutRect)
void ResizeIfNecessary(long aOldHeight, long aNewHeight)
bool IsShift() const
const MapMode & GetMapMode() const
sal_uInt16 GetCode() const
Dialog to specify the properties of date form field.
void EnableMapMode(bool bEnable=true)
const CommandWheelData * GetWheelData() const
SfxViewShell * GetSfxViewShell() const
Definition: viewsh.hxx:444
virtual Selection GetSurroundingTextSelection() const override
OUString GetAppLangDateTimeString(const DateTime &)
Definition: uitool.cxx:818
bool HandleScrollCommand(const CommandEvent &rCmd, ScrollBar *pHScrl, ScrollBar *pVScrl)
const OUString & GetTargetFrame() const
void SetMapMode()
void ExecutePopup(const OUString &rResName, vcl::Window *pWin=nullptr, const Point *pPos=nullptr)
#define KEY_Y
#define KEY_F5
SwWrtShell & GetWrtShell() const
Definition: view.hxx:400
void Move(long nHorzMoveDelta, long nVertMoveDelta)
Used by the UI to modify the document model.
Definition: wrtsh.hxx:90
weld::Window * GetFrameWeld() const
sal_Int64 WinBits
void LoadURL(SwViewShell &rVSh, const OUString &rURL, LoadUrlFlags nFilter, const OUString &rTargetFrameName)
Definition: wrtsh2.cxx:495
OUString GetSurroundingText() const
static void notifyInvalidation(SfxViewShell const *pThisView, const OString &rPayload)
virtual void Draw(OutputDevice *pDev, const Point &, const Size &, DrawFlags) override
virtual void MouseButtonDown(const MouseEvent &rMouseEvent) override
bool IsMouseEvent() const
const DateTime & GetTimeStamp(sal_uInt16 nPos=0) const
Definition: docredln.cxx:1723
bool GetHighContrastMode() const
union SwContentAtPos::@24 aFnd
SidebarTextControl(sw::annotation::SwAnnotationWin &rSidebarWin, WinBits nBits, SwView &rDocView, SwPostItMgr &rPostItMgr)
void DrawLine(const Point &rStartPt, const Point &rEndPt)
PointerStyle GetPointer(const Point &rPosPixel)
virtual void Paint(vcl::RenderContext &rRenderContext, const tools::Rectangle &rRect) override
void LogicInvalidate(const tools::Rectangle *pRectangle) override
EditView & GetEditView() const
const Point & GetMousePosPixel() const
SwDoc * GetDoc()
returns Doc. But be careful!
Definition: docsh.hxx:203
static bool DoesKeyChangeText(const KeyEvent &rKeyEvent)
void SetLineColor()
void SetWindowPeer(css::uno::Reference< css::awt::XWindowPeer > const &xPeer, VCLXWindow *pVCLXWindow)
DrawFlags
virtual void RequestHelp(const HelpEvent &rEvt) override
void dumpAsXml(xmlTextWriterPtr=nullptr) const
Dumps the entire nodes structure to the given destination (file nodes.xml in the current directory by...
Definition: docfmt.cxx:1918
bool IsMod2() const
SfxBindings & GetBindings()
#define KEY_ESCAPE
const Color & GetChangeColor() const
virtual void Invalidate(InvalidateFlags nFlags=InvalidateFlags::NONE)
void MakeVisible(const sw::annotation::SwAnnotationWin *pPostIt)
Definition: PostItMgr.cxx:1071
CommandEventId GetCommand() const
Outliner * GetOutliner() const
void SwitchToPostIt(sal_uInt16 aDirection)
virtual void dispose() override
const AllSettings & GetSettings() const
OUString SwResId(const char *pId)
Definition: swmodule.cxx:178
bool MouseMove(const MouseEvent &)
sal_uInt16 GetModifier() const
#define KEY_Z
void GrabFocus()
static void ShowQuickHelp(vcl::Window *pParent, const tools::Rectangle &rScreenRect, const OUString &rHelpText, QuickHelpFlags nStyle=QuickHelpFlags::NONE)
SwDocShell * GetDocShell()
Definition: view.cxx:1128
#define KEY_F12
const OUString & GetURL() const
const Point & GetMousePosPixel() const
Point PixelToLogic(const Point &rDevicePt) const
void AddEventListener(const Link< VclWindowEvent &, void > &rEventListener)
void SetPointer(PointerStyle)
const vcl::KeyCode & GetKeyCode() const
bool IsShift() const
bool IsMouseOver() const
#define FN_SPELL_GRAMMAR_DIALOG
Definition: cmdid.h:593
void Command(const CommandEvent &rCEvt)
virtual void KeyInput(const KeyEvent &rKeyEvt) override
bool PostKeyEvent(const KeyEvent &rKEvt, vcl::Window const *pFrameWin=nullptr)
bool IsMod1() const
long GetOutOffYPixel() const
const Point & GetPosPixel() const
sal_uInt16 GetFullCode() const
const SwRangeRedline * pRedl
Definition: crsrsh.hxx:101
virtual bool KeyInput(const KeyEvent &rKeyEvent)
static weld::Builder * CreateBuilder(weld::Widget *pParent, const OUString &rUIFile)
void InvalidateAll(bool bWithMsg)
#define KEY_INSERT
void RemoveEventListener(const Link< VclWindowEvent &, void > &rEventListener)
bool HandleWheelCommands(const CommandEvent &)
Definition: viewport.cxx:1209
bool GetContentAtPos(const Point &rPt, SwContentAtPos &rContentAtPos, bool bSetCursor=false, SwRect *pFieldRect=nullptr)
Definition: crstrvl.cxx:1268
long getHeight() const
virtual OUString GetSurroundingText() const override
rtl::OString toString() const
bool HasFocus() const
void Push(PushFlags nFlags=PushFlags::ALL)
long getWidth() const
void DrawGradient(const tools::Rectangle &rRect, const Gradient &rGradient)
void setWidth(long nWidth)
static OUString GetURLHelpText(const OUString &)
Selection GetSurroundingTextSelection() const
sw::annotation::SwAnnotationWin & mrSidebarWin
Definition: view.hxx:146
virtual void MouseButtonUp(const MouseEvent &rMEvt) override
const SvxFieldData * GetField() const
bool IsMod2() const
bool IsWrongSpelledWordAtPos(const Point &rPosPixel, bool bMarkIfWrong=false)
void Paint(const tools::Rectangle &rRect, OutputDevice *pTargetDevice=nullptr)