OpZoom Class Reference

This operation can perform zooms in and out of the current DocView, either by an immediate call to the ZoomIn/ZoomOut/ZoomInOnRect/ZoomAtPoint functions, or by a call to the DoDrag function, which starts a mouse drag to define a zoom box. More...

#include <zoomops.h>

Inheritance diagram for OpZoom:

OpCentredDragBox OpDragBox Operation MessageHandler ListItem CCObject SimpleCCObject OpZoomIn OpZoomOut OpZoomTo100 OpZoomTo200 OpZoomTo300 OpZoomTo400 List of all members.

Public Member Functions

 OpZoom ()
 Default constructor. To run a zoom drag, call the DoDrag() function.
virtual void Do (OpDescriptor *)
 Performs the zoom operation.
BOOL DoDrag (Spread *pStartSpread, const DocCoord &dcStartPos, ClickModifiers cmods)
 Starts an auto-scroll drag operation at the given mouse position. Note that this function hides the base-class DoDrag() function.
virtual BOOL SnappingDrag ()
void ZoomOut (const WorkCoord &wcZoom, BOOL fEndOp=TRUE)
 Zooms out of the current DocView by one step. By default this function will call the End() function for this operation afterwards.
void ZoomOut (Spread *pZoomSpread, const DocCoord &dcZoomPos, BOOL fEndOp=TRUE)
 Zooms out of the current DocView by one step. By default this function will call the End() function for this operation afterwards.
void ZoomIn (const WorkCoord &wcZoom, BOOL fEndOp=TRUE)
 Zooms into the current DocView by one step. By default this function will call the End() function for this operation afterwards.
void ZoomIn (Spread *pZoomSpread, const DocCoord &dcZoomPos, BOOL fEndOp=TRUE)
 Zooms in on the current DocView by one step. By default this function will call the End() function for this operation afterwards.
void ZoomTo (const WorkCoord &wcZoom, INT32 Percent, BOOL fEndOp=TRUE)
 Zooms into the current DocView by one step. By default this function will call the End() function for this operation afterwards.
void ZoomInOnRect (const WorkRect &wrZoom, BOOL fEndOp=TRUE)
 Zooms so that the given work rectangle completely fills the current DocView view extents. By default this function will call the End() function for this operation afterwards.
void ZoomInOnRect (Spread *pZoomSpread, const DocRect &dcZoomRect, BOOL fEndOp=TRUE)
 Zooms so that the given spread rectangle completely fills the current DocView view extents. By default this function will call the End() function for this operation afterwards.
void ZoomAtPoint (const WorkCoord &wcZoom, FIXED16 fxNewScaleFactor, BOOL fEndOp=TRUE)
 Sets the current DocView to show the given point at the given scale factor. By default this function will call the End() function for this operation afterwards.
void ZoomAtPoint (Spread *pZoomSpread, const DocCoord &dcZoomPos, FIXED16 fxNewScaleFactor, BOOL fEndOp=TRUE)
void MouseWheelZoomAtPoint (const WorkCoord &wcZoom, FIXED16 fxNewScalePercent, BOOL fEndOp=TRUE)
 Sets the current DocView to show the given point at the given scale factor. By default this function will call the End() function for this operation afterwards.

Static Public Member Functions

static void SpreadToWork (Spread *pspdIn, const DocCoord &dcIn, WorkCoord *pwcOut)
static void SpreadToWork (Spread *pspdIn, const DocRect &drIn, WorkRect *pwrOut)
static INT32 GetPresetZoomPercent (INT32 nPreset)
static FIXED16 GetPresetZoomScale (INT32 nPreset)
static BOOL Declare ()
 "Registers" the zoom operation's OpDescriptors, loads preferences, and makes sure the zoom-in and zoom-out cursors are valid.

Private Member Functions

BOOL OnDragStarted (Spread *, const DocCoord &, ClickModifiers)
 Called by OpZoom's base class, OpDragBox, when a drag has been started. Sets the status line text to a helpful comment.
BOOL OnPointerMoved (Spread *, const DocRect &, ClickModifiers)
 If this function is called then a drag has definitely started, so update the status bar. We don't do this on a button-down event.
BOOL OnDragEnded (Spread *pBoxSpread, const DocRect &drDragBox, ClickModifiers cmods, BOOL fDragOK)
DocRect CalcDragBox (const DocCoord &dcStartPos, const DocCoord &dcMousePos) const
 Overrides the default OpDragBox method to allow the drag box to be drawn from the centre (start of drag) to the corner (current mouse position), if the 'ZoomDragOnCentre' preference allows. If it doesn't the default method is called instead.
BOOL GetStatusLineText (String_256 *ptext, Spread *, DocCoord, ClickModifiers)
 get status line help for zoom drag op
 CC_DECLARE_DYNCREATE (OpZoom)

Private Attributes

Cursor m_csrZoomIn
Cursor m_csrZoomOut
Cursor m_csrZoomDrag
INT32 m_ncsrSaveDrag
WorkCoord m_wcStartPos
BOOL m_fStatusTextShown

Static Private Attributes

static INT32 ZoomTable [cZoomTableSize]
static BOOL m_fRadialZoomDragBox = FALSE
 Determines how the zoom drag operation invokes by the zoom tool will draw its drag box. If FALSE (the default) then the tool will draw the box from one corner to its opposite. This is similar to the selector's drag box. If TRUE then the tool will draw its centre box centred on the point where the drag started and extending to the current mouse position. The effect is to centre the zoom on the first clicked point.
static BOOL m_fFixZoomClickPoint = FALSE
 When zooming in or out with a mouse click, this determines whether to fix the clicked point in the resulting zoomed view at the same screen-relative position, or to centre the zoomed view on the clicked point. By default this is FALSE (don't fix, do centre).
static UINT32 m_nfShowZoomCursors = 0
 Determines whether to flash a "zooming-in" or "zooming-out" cursor when a zoom is being calculated, and a special drag cursor when dragging in the zoom tool.

Detailed Description

This operation can perform zooms in and out of the current DocView, either by an immediate call to the ZoomIn/ZoomOut/ZoomInOnRect/ZoomAtPoint functions, or by a call to the DoDrag function, which starts a mouse drag to define a zoom box.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95

Definition at line 166 of file zoomops.h.


Constructor & Destructor Documentation

OpZoom::OpZoom  ) 
 

Default constructor. To run a zoom drag, call the DoDrag() function.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95

Definition at line 249 of file zoomops.cpp.

00250       : m_csrZoomIn((Tool_v1*)NULL, _R(IDCSR_ZOOM_IN)),             // we only need these cursors when an OpZoom
00251         m_csrZoomOut((Tool_v1*)NULL, _R(IDCSR_ZOOM_OUT)),           
00252         m_csrZoomDrag((Tool_v1*)NULL, _R(IDCSR_ZOOM_DRAG))          // is going to be run
00253 {
00254 //  ERROR3IF(!m_csrZoomIn.IsValid() || !m_csrZoomOut.IsValid() || !m_csrZoomDrag.IsValid(),
00255 //              "Failed to load cursor(s) in OpZoom::OpZoom");
00256 }


Member Function Documentation

DocRect OpZoom::CalcDragBox const DocCoord dcStartPos,
const DocCoord dcMousePos
const [private, virtual]
 

Overrides the default OpDragBox method to allow the drag box to be drawn from the centre (start of drag) to the corner (current mouse position), if the 'ZoomDragOnCentre' preference allows. If it doesn't the default method is called instead.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
dcStartPos the position where the drag was started [INPUTS] dcMousePos the current position of the mouse
Returns:
A document (spread) rectangle the is the current bounds of the drag box.
See also:
OpDragBox::CalcDragBox

Reimplemented from OpCentredDragBox.

Definition at line 571 of file zoomops.cpp.

00572 {
00573     // Do what the preferences say.
00574     return (m_fRadialZoomDragBox) ? OpCentredDragBox::CalcDragBox(dcStartPos, dcMousePos)
00575                                   : OpDragBox::CalcDragBox(dcStartPos, dcMousePos);
00576 }

OpZoom::CC_DECLARE_DYNCREATE OpZoom   )  [private]
 

BOOL OpZoom::Declare  )  [static]
 

"Registers" the zoom operation's OpDescriptors, loads preferences, and makes sure the zoom-in and zoom-out cursors are valid.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Returns:
TRUE if everything went OK, FALSE otherwise
See also:
class OpZoomComboDescriptor; class OpZoomPrevZoomDescriptor; class OpZoomFitSpreadDescriptor; class OpZoomFitDrawingDescriptor

Definition at line 1044 of file zoomops.cpp.

01045 {
01046     // Try to create OpDescriptors for each zoom gadget.
01047     ERRORIF(!new OpZoomComboDescriptor ||
01048             !new OpZoomPrevZoomDescriptor ||
01049             !new OpZoomFitSpreadDescriptor ||
01050             !new OpZoomFitDrawingDescriptor ||
01051             !new OpZoomFitSelectedDescriptor ||
01052             !new OpZoomFitRectDescriptor ||
01053             !OpZoomTo100::Init() ||
01054             !OpZoomTo200::Init() ||
01055             !OpZoomTo300::Init() ||
01056             !OpZoomTo400::Init(),
01057             _R(IDE_NOMORE_MEMORY),
01058             FALSE);
01059 
01060 #if !defined(EXCLUDE_FROM_RALPH)
01061     // Try to load preferences.
01062     ERRORIF(!GetApplication()->DeclareSection(TEXT("Zoom Tool"), 5) ||
01063             !GetApplication()->DeclarePref(TEXT("Zoom Tool"), TEXT("FixZoomClickPoint"),
01064                                            &m_fFixZoomClickPoint, FALSE, TRUE) ||
01065             !GetApplication()->DeclarePref(TEXT("Zoom Tool"), TEXT("RadialZoomDragBox"),
01066                                            &m_fRadialZoomDragBox, FALSE, TRUE) ||
01067             !GetApplication()->DeclarePref(TEXT("Zoom Tool"), TEXT("ShowZoomCursors"),
01068                                            &m_nfShowZoomCursors, 0, 1),
01069             _R(IDE_BAD_INI_FILE),
01070             FALSE);
01071 #endif
01072 
01073     // Success.
01074     return TRUE;
01075 }

void OpZoom::Do OpDescriptor pOpDesc  )  [virtual]
 

Performs the zoom operation.

Author:
Neville_Humphrys (Xara Group Ltd) <camelotdev@xara.com>
Date:
20/9/95
Parameters:
pointer to the OpZoomDescriptor being invoked [INPUTS]
See also:
OpZoomDescriptor::FakeInvoke;

Reimplemented from Operation.

Reimplemented in OpZoomIn, OpZoomOut, OpZoomTo100, OpZoomTo200, OpZoomTo300, and OpZoomTo400.

Definition at line 270 of file zoomops.cpp.

00271 {
00272     // Do what FakeInvoke does but call the DoZoom function instead of HandleButtonMsg for
00273     // the zoom descriptor.
00274     OpZoomDescriptor* pZoomOpDesc = (OpZoomDescriptor*) pOpDesc;
00275     if (pZoomOpDesc != 0 && pZoomOpDesc->IsAvailable())
00276     {
00277         // DoZoom function must End the operation.
00278         pZoomOpDesc->DoZoom(this);
00279     }
00280 }

BOOL OpZoom::DoDrag Spread pStartSpread,
const DocCoord dcStartPos,
ClickModifiers  cmods
 

Starts an auto-scroll drag operation at the given mouse position. Note that this function hides the base-class DoDrag() function.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
pStartSpread the spread containing the initial mouse postion [INPUTS] dcStartPos the initial mosue position, ie, where the drag started cmods the state of the mouse modifier keys
See also:
OpDragBox::DoDrag

Definition at line 391 of file zoomops.cpp.

00392 {
00393     return OpDragBox::DoDrag(DRAGTYPE_AUTOSCROLL, pStartSpread, dcStartPos, cmods);
00394 }

INT32 OpZoom::GetPresetZoomPercent INT32  nPreset  )  [static]
 

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
24/4/95
Parameters:
nPreset which preset zoom factor, with 0 the highest and [INPUTS] cZoomTableSize-1 the lowest.
Returns:
A standard preset zoom factor, as a percentage.

Definition at line 347 of file zoomops.cpp.

00348 {
00349     ERROR3IF(nPreset < 0 || nPreset >= cZoomTableSize,
00350                 "Bad preset in OpZoom::GetPresetZoomPercent");
00351     return ZoomTable[nPreset];
00352 }

FIXED16 OpZoom::GetPresetZoomScale INT32  nPreset  )  [static]
 

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
24/4/95
Parameters:
nPreset which preset zoom factor, with 0 the highest and [INPUTS] cZoomTableSize-1 the lowest.
Returns:
A standard preset zoom factor, as a scale factor.

Definition at line 367 of file zoomops.cpp.

00368 {
00369     ERROR3IF(nPreset < 0 || nPreset >= cZoomTableSize,
00370                 "Bad preset in OpZoom::GetPresetZoomScale");
00371     return ((FIXED16) ZoomTable[nPreset]) / 100;
00372 }

BOOL OpZoom::GetStatusLineText String_256 pText,
Spread ,
DocCoord  ,
ClickModifiers 
[private, virtual]
 

get status line help for zoom drag op

Author:
Ed_Cornes (Xara Group Ltd) <camelotdev@xara.com>
Date:
26/1/95
Parameters:
Spread*,DocCoord,ClickModifiers - not used [INPUTS]
pText - [OUTPUTS]
Returns:
TRUE if returning valid text

Errors: this==0

Reimplemented from Operation.

Definition at line 1023 of file zoomops.cpp.

01024 {
01025     ERROR2IF(this == 0, FALSE, "OpZoom::GetStatusLineText() - this == 0");
01026     ERROR2IF(pText == 0, FALSE, "OpZoom::GetStatusLineText() - pText == 0");
01027     return pText->Load(_R(IDS_ZOOMOP_STATUSHELP));
01028 }

void OpZoom::MouseWheelZoomAtPoint const WorkCoord wcZoom,
FIXED16  fxNewScaleFactor,
BOOL  fEndOp = TRUE
 

Sets the current DocView to show the given point at the given scale factor. By default this function will call the End() function for this operation afterwards.

Author:
Priestley (Xara Group Ltd) <camelotdev@xara.com> (BLATANTLY ripped from JustinF & Rik)
Date:
17/11/2000
Parameters:
wcZoom the point within the current view to zoom at, [INPUTS] in work coordinates. fxNewScaleFactor the required scale factor fEndOp whether to end this operation after this zoom

Definition at line 1094 of file zoomops.cpp.

01095 {
01096     // Get the current view.
01097     DocView* pDocView = DocView::GetCurrent();
01098     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::ZoomAtPoint");
01099 
01100     // Save the view's current zoom and find out current scaling factor.
01101     OpZoomPrevZoomDescriptor::SaveZoom(pDocView);
01102     FIXED16 fxOldScaleFactor = pDocView->GetViewScale();
01103 
01104     // Push the zoom-in or zoom-out cursor, depending on whether we are zooming in or
01105     // out.
01106     INT32 ncsrOldID=0;
01107     if (ZoomTool::IsSelectedTool() && m_nfShowZoomCursors)
01108     {
01109         ncsrOldID = CursorStack::GPush((fxNewScaleFactor > fxOldScaleFactor)
01110                                             ? &m_csrZoomIn
01111                                             : &m_csrZoomOut);
01112     }
01113 
01114     // Find the current view size in 64-bit work coordinates.
01115     WorkRect wrView = pDocView->GetViewRect();
01116 
01117     // Work out the ratio of the new and old scale factors.
01118     double fpLineRatio = fxOldScaleFactor.MakeDouble() / fxNewScaleFactor.MakeDouble();
01119 
01120     // We either centre the clicked point or keep it fixed, depending on the preferences.
01121     // Calculate the new position of the top-left of the view accordingly.
01122     WorkCoord wcNewTopCorner = wcZoom;
01123 
01124 //  if (!m_fFixZoomClickPoint)
01125 //  {
01126         // Find the vector from the click point to the top corner of the window, and
01127         // from this work out the new position of the top-left corner of the view.
01128         wcNewTopCorner.x += XLONG(fpLineRatio * (wrView.lo.x - wcZoom.x));
01129         wcNewTopCorner.y += XLONG(fpLineRatio * (wrView.hi.y - wcZoom.y));
01130 //  }
01131 //  else
01132 //  {
01133 //      // Find the vector from the centre of the view to the top-left corner, scaled by
01134 //      // the line-ratio.  Add this vector to the click point to work out the new position
01135 //      // of the top-left corner of the view.
01136 //      wcNewTopCorner.x -= MakeXLong(fpLineRatio * (wrView.Width().MakeDouble() / 2));
01137 //      wcNewTopCorner.y += MakeXLong(fpLineRatio * (wrView.Height().MakeDouble() / 2));
01138 //  }
01139 
01140     // Scale the value to the correct number of pixels.  We convert to doubles as the
01141     // fixed-point numbers can lose precision at high zooms.
01142     double fpPixRatio = fxNewScaleFactor.MakeDouble() / fxOldScaleFactor.MakeDouble();
01143     wcNewTopCorner.x  = XLONG(fpPixRatio * wcNewTopCorner.x);
01144     wcNewTopCorner.y  = XLONG(fpPixRatio * wcNewTopCorner.y);
01145         
01146     // Set the new scale factor in the view.
01147     pDocView->SetViewScale(fxNewScaleFactor);   
01148 
01149     // Make sure that the new scroll offset is within workspace bounds and set it.
01150     if (wcNewTopCorner.x < 0) wcNewTopCorner.x = 0;
01151     if (wcNewTopCorner.y > 0) wcNewTopCorner.y = 0;
01152     pDocView->SetScrollOffsets(wcNewTopCorner, FALSE);
01153 
01154 #ifndef RALPH
01155     // Update the combo-box containing scale factors.
01156     OpZoomComboDescriptor::Update();
01157 #endif
01158 
01159     // Finally redraw the whole window, reset the cursor, and end the operation.
01160     pDocView->ForceRedraw(TRUE);
01161     if (ZoomTool::IsSelectedTool() && m_nfShowZoomCursors) CursorStack::GPop(ncsrOldID);
01162     if (fEndOp) End();
01163 
01164     // tell people things have changed on screen
01165     TRACEUSER( "Diccon", _T("ZoomAtPoint\n"));
01166     BROADCAST_TO_ALL(ScreenChangeMsg(TRUE));
01167 }

BOOL OpZoom::OnDragEnded Spread pBoxSpread,
const DocRect drDragBox,
ClickModifiers  cmods,
BOOL  fDragOK
[private, virtual]
 

Reimplemented from OpDragBox.

Definition at line 477 of file zoomops.cpp.

00478 {
00479     // Pop the cursor we possibly pushed in OnStartDrag.
00480     if (m_nfShowZoomCursors) CursorStack::GPop(m_ncsrSaveDrag);
00481     
00482     // If the drag didn't happen we do nothing.  We don't want FailAndExecute() called
00483     // though, so return TRUE.
00484     if (!fDragOK) return TRUE;
00485 
00486     // This could take a while . . .
00487 //  BeginSlowJob();
00488 
00489     // Get the current view.
00490     DocView* pDocView = DocView::GetCurrent();
00491     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::OnDragEnded");
00492 
00493     // Find the half of the absolute width and height of the drag box.
00494     WorkCoord wcLast = pDocView->GetClickWorkCoord();
00495     WorkRect wrZoom;
00496 
00497     if (m_fRadialZoomDragBox)
00498     {
00499         XLONG nWidth2 = m_wcStartPos.x - wcLast.x;
00500         if (nWidth2 < 0) nWidth2 = -nWidth2;
00501         XLONG nHeight2 = m_wcStartPos.y - wcLast.y;
00502         if (nHeight2 < 0) nHeight2 = -nHeight2;
00503 
00504         // Make a rectangle of this width and height, centred on the click point.
00505         wrZoom = WorkRect(m_wcStartPos.x - nWidth2, m_wcStartPos.y - nHeight2,
00506                           m_wcStartPos.x + nWidth2, m_wcStartPos.y + nHeight2);
00507     }
00508     else
00509     {
00510         #undef  MIN
00511         #undef  MAX
00512         #define MIN(a,b) (((a)<(b))?(a):(b))
00513         #define MAX(a,b) (((a)>(b))?(a):(b))
00514         
00515         wrZoom = WorkRect(MIN(m_wcStartPos.x, wcLast.x),
00516                           MIN(m_wcStartPos.y, wcLast.y),
00517                           MAX(m_wcStartPos.x, wcLast.x),
00518                           MAX(m_wcStartPos.y, wcLast.y));
00519     }
00520 
00521     // We must first check if we have a significant drag box.  If the size of the box
00522     // is less than the Camelot "click radius" we will ignore the drag and treat the
00523     // operation as a single-click "zoom in" action by the user.
00524 
00525     // Graeme (11/11/99): The comparison is now done against a constant value
00526     // (ZOOM_MIN_DRAG), which is defined in zoomops.h. dDragDistance gives an absolute
00527     // value, rather than testing against separate x and y values.
00528 
00529     // Zoom in bug fixed by Chris Snook/Graeme (14/12/99) ....
00530 
00531     double dDragDistance = sqrt ( ( (double) wrZoom.Width () * (double) wrZoom.Width () ) +
00532                                   ( (double) wrZoom.Height () * (double) wrZoom.Height () ) );
00533 
00534     if ( dDragDistance < ZOOM_MIN_DRAG || wrZoom.Width() <= 0 || wrZoom.Height() <= 0 )
00535     {
00536         // Drag is insignificant so zoom in instead.
00537         ZoomIn(m_wcStartPos, FALSE);                    // OpDragBox will end this op
00538     }
00539     else
00540     {
00541         // Do a proper mouse-drag zoom.
00542         ZoomInOnRect(wrZoom, FALSE);                    // OpDragBox will end this op
00543     }
00544     
00545     // tell people things have changed on screen
00546     TRACEUSER( "Diccon", _T("OnDragEnded\n"));
00547     BROADCAST_TO_ALL(ScreenChangeMsg(TRUE));
00548 
00549     // Remove the hour-glass and return the success code.
00550 //  EndSlowJob();
00551     return TRUE;
00552 }

BOOL OpZoom::OnDragStarted Spread ,
const DocCoord ,
ClickModifiers 
[private, virtual]
 

Called by OpZoom's base class, OpDragBox, when a drag has been started. Sets the status line text to a helpful comment.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
(not used) [INPUTS]
Returns:
TRUE (always)

Reimplemented from OpDragBox.

Definition at line 409 of file zoomops.cpp.

00410 {
00411     // Remember where the drag started.  We have to "bodge" this as it is apparently too
00412     // difficult to translate document coordinates to work coordinates during a drag, so
00413     // we can't use the mouse position info passed to us by the OpDragBox base-class.
00414     DocView* pDocView = DocView::GetCurrent();
00415     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::OnDragStarted");
00416     m_wcStartPos = pDocView->GetClickWorkCoord();
00417 
00418     // Reset this flag.
00419     m_fStatusTextShown = FALSE;
00420 
00421     // Possibly set the zoom-cursor, saving the old one, and return success.
00422     if (m_nfShowZoomCursors) m_ncsrSaveDrag = CursorStack::GPush(&m_csrZoomDrag);
00423     return TRUE;
00424 }

BOOL OpZoom::OnPointerMoved Spread ,
const DocRect ,
ClickModifiers 
[private, virtual]
 

If this function is called then a drag has definitely started, so update the status bar. We don't do this on a button-down event.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
24/6/95
Parameters:
(not used) [INPUTS]
Returns:
TRUE, meaning continue dragging.

Reimplemented from OpDragBox.

Definition at line 439 of file zoomops.cpp.

00440 {
00441 #if !defined(EXCLUDE_FROM_RALPH)
00442     // The first time through this function set the status-line text.  We don't really
00443     // want to do this on a button-down event as not all such events lead to drags.
00444     if (!m_fStatusTextShown)
00445     {
00446         // Set the status line text.  If we manage to do it then don't bother doing it
00447         // again until another drag really begins.
00448         String_256 str(_R(IDS_ZOOMOP_STATUSHELP));
00449         m_fStatusTextShown = GetApplication()->UpdateStatusBarText(&str);   
00450     }
00451 #endif
00452     
00453     // All fine, continue dragging.
00454     return TRUE;
00455 }

virtual BOOL OpZoom::SnappingDrag  )  [inline, virtual]
 

Reimplemented from Operation.

Definition at line 187 of file zoomops.h.

00187 { return FALSE; }

void OpZoom::SpreadToWork Spread pspdIn,
const DocRect drIn,
WorkRect pwrOut
[static]
 

Definition at line 327 of file zoomops.cpp.

00328 {
00329     // Convert low and high corners of the rectangle.
00330     SpreadToWork(pspdIn, drIn.lo, &pwrOut->lo);
00331     SpreadToWork(pspdIn, drIn.hi, &pwrOut->hi);
00332 }

void OpZoom::SpreadToWork Spread pspdIn,
const DocCoord dcIn,
WorkCoord pwcOut
[static]
 

Definition at line 297 of file zoomops.cpp.

00298 {
00299     // Caller must provide a location to store the converted coordinate.
00300     ERROR3IF(pwcOut == 0, "No output in OpZoom::SpreadToWork");
00301 
00302     // Find the current DocView.
00303     DocView* pDocView = DocView::GetCurrent();
00304     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::SpreadToWork");
00305 
00306     // Convert.
00307     if (pDocView && pwcOut)
00308         *pwcOut = ((DocCoord&) dcIn).ToWork(pspdIn, pDocView);
00309 }

void OpZoom::ZoomAtPoint Spread pZoomSpread,
const DocCoord dcZoomPos,
FIXED16  fxNewScaleFactor,
BOOL  fEndOp = TRUE
 

Definition at line 1000 of file zoomops.cpp.

01002 {
01003     // Now we can just pass to the WorkCoord version of this function.
01004     WorkCoord wcZoom;
01005     SpreadToWork(pZoomSpread, dcZoomPos, &wcZoom);
01006     ZoomAtPoint(wcZoom, fxNewScaleFactor, fEndOp);
01007 }

void OpZoom::ZoomAtPoint const WorkCoord wcZoom,
FIXED16  fxNewScaleFactor,
BOOL  fEndOp = TRUE
 

Sets the current DocView to show the given point at the given scale factor. By default this function will call the End() function for this operation afterwards.

Technical notes: What the zoom does. This routine finds out the current scroll offsets and makes a vector from the clicked point to the top corner of the window (ie the scroll offsets). It knows the ratio of the old scale factor and the new scale factor and uses this to calculate a new point from the click point along the vector.

For example, if the ratio of the old and new zooms is one half then the new top corner of the window will be a point on the vector, half way between the click point and the old top corner of the window.

Since the document will be changing size and since the scroll offsets are measured in pixels, these will be changing after the zoom has happened, so we have to compensate for that as well. All that remains to do after that is check that the offsets are valid and then set them.

Definition at line 908 of file zoomops.cpp.

00909 {
00910     // Get the current view.
00911     DocView* pDocView = DocView::GetCurrent();
00912     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::ZoomAtPoint");
00913 
00914     // Save the view's current zoom and find out current scaling factor.
00915     OpZoomPrevZoomDescriptor::SaveZoom(pDocView);
00916     FIXED16 fxOldScaleFactor = pDocView->GetViewScale();
00917 
00918     // Push the zoom-in or zoom-out cursor, depending on whether we are zooming in or
00919     // out.
00920     INT32 ncsrOldID=0;
00921     if (ZoomTool::IsSelectedTool() && m_nfShowZoomCursors)
00922     {
00923         ncsrOldID = CursorStack::GPush((fxNewScaleFactor > fxOldScaleFactor)
00924                                             ? &m_csrZoomIn
00925                                             : &m_csrZoomOut);
00926     }
00927 
00928     // Find the current view size in 64-bit work coordinates.
00929     WorkRect wrView = pDocView->GetViewRect();
00930 
00931     // Work out the ratio of the new and old scale factors.
00932     double fpLineRatio = fxOldScaleFactor.MakeDouble() / fxNewScaleFactor.MakeDouble();
00933 
00934     // We either centre the clicked point or keep it fixed, depending on the preferences.
00935     // Calculate the new position of the top-left of the view accordingly.
00936     WorkCoord wcNewTopCorner = wcZoom;
00937     if (m_fFixZoomClickPoint)
00938     {
00939         // Find the vector from the click point to the top corner of the window, and
00940         // from this work out the new position of the top-left corner of the view.
00941         wcNewTopCorner.x += XLONG(fpLineRatio * (wrView.lo.x - wcZoom.x));
00942         wcNewTopCorner.y += XLONG(fpLineRatio * (wrView.hi.y - wcZoom.y));
00943     }
00944     else
00945     {
00946         // Find the vector from the centre of the view to the top-left corner, scaled by
00947         // the line-ratio.  Add this vector to the click point to work out the new position
00948         // of the top-left corner of the view.
00949         wcNewTopCorner.x -= XLONG(fpLineRatio * wrView.Width ()/2);
00950         wcNewTopCorner.y += XLONG(fpLineRatio * wrView.Height()/2);
00951     }
00952 
00953     // Scale the value to the correct number of pixels.  We convert to doubles as the
00954     // fixed-point numbers can lose precision at high zooms.
00955     double fpPixRatio = fxNewScaleFactor.MakeDouble() / fxOldScaleFactor.MakeDouble();
00956     wcNewTopCorner.x  = XLONG(fpPixRatio * wcNewTopCorner.x);
00957     wcNewTopCorner.y  = XLONG(fpPixRatio * wcNewTopCorner.y);
00958         
00959     // Set the new scale factor in the view.
00960     pDocView->SetViewScale(fxNewScaleFactor);   
00961 
00962     // Make sure that the new scroll offset is within workspace bounds and set it.
00963     if (wcNewTopCorner.x < 0) wcNewTopCorner.x = 0;
00964     if (wcNewTopCorner.y > 0) wcNewTopCorner.y = 0;
00965     pDocView->SetScrollOffsets(wcNewTopCorner, FALSE);
00966 
00967 #ifndef RALPH
00968     // Update the combo-box containing scale factors.
00969     OpZoomComboDescriptor::Update();
00970 #endif
00971 
00972     // Finally redraw the whole window, reset the cursor, and end the operation.
00973     pDocView->ForceRedraw(TRUE);
00974     if (ZoomTool::IsSelectedTool() && m_nfShowZoomCursors) CursorStack::GPop(ncsrOldID);
00975     if (fEndOp) End();
00976 
00977     // tell people things have changed on screen
00978     TRACEUSER( "Diccon", _T("ZoomAtPoint\n"));
00979     BROADCAST_TO_ALL(ScreenChangeMsg(TRUE));
00980 }

void OpZoom::ZoomIn Spread pZoomSpread,
const DocCoord dcZoomPos,
BOOL  fEndOp = TRUE
 

Zooms in on the current DocView by one step. By default this function will call the End() function for this operation afterwards.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
pZoomSpread the spread containing the point to zoom in at [INPUTS] dcZoomPos the point to zoom in at fEndOp whether to end this operation after this zoom

Definition at line 733 of file zoomops.cpp.

00734 {
00735     WorkCoord wcZoom;
00736     SpreadToWork(pZoomSpread, dcZoomPos, &wcZoom);
00737     ZoomIn(wcZoom, fEndOp);
00738 }

void OpZoom::ZoomIn const WorkCoord wcZoom,
BOOL  fEndOp = TRUE
 

Zooms into the current DocView by one step. By default this function will call the End() function for this operation afterwards.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
wcZoom the point to zoom in at [INPUTS] fEndOp whether to end this operation after this zoom

Definition at line 688 of file zoomops.cpp.

00689 {
00690     // Find out the current view.
00691     DocView* pDocView = DocView::GetCurrent();
00692     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::ZoomIn");
00693     
00694     if (pDocView)
00695     {
00696         // Find the current view's scaling factor.  By converting this to a percentage
00697         // and rounding we improve the accuracy of the comparison below.
00698         INT32 nOldScalePercent = ((pDocView->GetViewScale() * 100) + FIXED16_DBL(0.5)).MakeInt();
00699 
00700         // Search backwards until we find a higher zoom, or the end of the table (meaning that
00701         // there is no higher zoom).
00702         for (INT32 i = cZoomTableSize - 1; i >= 0; i--)
00703         {
00704             // Found a higher zoom?  If so, set it, remember it's position and return.
00705             if (nOldScalePercent < GetPresetZoomPercent(i))
00706             {
00707                 // Do the zoom.  We will (optionally) end the operation.
00708                 pDocView->SetZoomTableIndex(i);
00709                 ZoomAtPoint(wcZoom, GetPresetZoomScale(i), FALSE);
00710                 break;
00711             }
00712         }
00713     }
00714 
00715     // End the operation if the caller wants us to.
00716     if (fEndOp) End();
00717 }

void OpZoom::ZoomInOnRect Spread pZoomSpread,
const DocRect drZoomRect,
BOOL  fEndOp = TRUE
 

Zooms so that the given spread rectangle completely fills the current DocView view extents. By default this function will call the End() function for this operation afterwards.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
pZoomSpread the spread containing the rectangle to zoom in on [INPUTS] drZoomRect the rectangle to zoom in on. fEndOp whether to end this operation after this zoom

Definition at line 867 of file zoomops.cpp.

00868 {
00869     // Call the WorkRect version of this function to do the zoom.
00870     WorkRect wrZoom;
00871     SpreadToWork(pZoomSpread, drZoomRect, &wrZoom);
00872     ZoomInOnRect(wrZoom, fEndOp);
00873 }

void OpZoom::ZoomInOnRect const WorkRect wrZoom,
BOOL  fEndOp = TRUE
 

Zooms so that the given work rectangle completely fills the current DocView view extents. By default this function will call the End() function for this operation afterwards.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
wrZoom the rectangle to zoom in on. [INPUTS] fEndOp whether to end this operation after this zoom

Definition at line 754 of file zoomops.cpp.

00755 {
00756     // Make sure the zoom rectangle isn't empty, or we'll divide by zero later on.
00757     if (wrZoom.IsEmpty())
00758     {
00759         ERROR3("Empty zoom rectangle passed to OpZoom::ZoomInOnRect");
00760         return;
00761     }
00762 
00763     // Find out the current view and save its scale factor and scroll offsets.
00764     DocView* pDocView = DocView::GetCurrent();
00765     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::ZoomInOnRect");
00766     // Get out now if view 0 otherwise we will access violate later on
00767     if (pDocView == 0)
00768         return;
00769     
00770     OpZoomPrevZoomDescriptor::SaveZoom(pDocView);
00771 
00772     // Find out the size of the window and the given zoom rectangle in work coordinates.
00773     WorkRect wrView = pDocView->GetViewRect();
00774 
00775     // Get the current scale factor.
00776     double fpOldScaleFactor = pDocView->GetViewScale().MakeDouble();
00777 
00778     // Find out the ratios of the width and height (zoom rect to view rect).  We know
00779     // that the divisors are not zero, or we would not have entered this function.
00780     double fpWidthFactor  = (double)wrView.Width ()/wrZoom.Width ();
00781     double fpHeightFactor = (double)wrView.Height()/wrZoom.Height();
00782     double fpMinFactor = (fpWidthFactor < fpHeightFactor) ? fpWidthFactor : fpHeightFactor;
00783 
00784     // The new zoom factor is proportional to the above
00785     double fpNewScaleFactor = fpOldScaleFactor * fpMinFactor;
00786 
00787     // Push the zoom-in or zoom-out cursor, depending on whether we are zooming in or
00788     // out and the state of the preference.
00789     INT32 ncsrOldID=0;
00790     if (ZoomTool::IsSelectedTool() && m_nfShowZoomCursors)
00791     {
00792         ncsrOldID = CursorStack::GPush((fpNewScaleFactor > fpOldScaleFactor)
00793                                             ? &m_csrZoomIn
00794                                             : &m_csrZoomOut);
00795     }
00796     
00797     // Convert the new scale factor to a percentage and check that it's in bounds.  If it
00798     // isn't adjust it to the lowest/highest zoom factors.
00799     INT32 nZoomPercent = (INT32) (fpNewScaleFactor * 100);
00800     if (nZoomPercent < GetPresetZoomPercent(cZoomTableSize - 1))
00801     {
00802         fpNewScaleFactor = GetPresetZoomScale(cZoomTableSize - 1).MakeDouble();
00803     }
00804     else if (nZoomPercent > GetPresetZoomPercent(0))
00805     {
00806         fpNewScaleFactor = GetPresetZoomScale(0).MakeDouble();
00807     }
00808 
00809     // Set the scroll offsets to the middle of the box.
00810     WorkCoord wcScrollOffset;
00811     wcScrollOffset.x = (wrZoom.lo.x + wrZoom.hi.x) / 2;
00812     wcScrollOffset.y = (wrZoom.lo.y + wrZoom.hi.y) / 2;
00813 
00814     // Scale the value to the correct number of pixels. 
00815     double fpRatio = fpNewScaleFactor / fpOldScaleFactor;
00816     wcScrollOffset.x = XLONG(wcScrollOffset.x*fpRatio);
00817     wcScrollOffset.y = XLONG(wcScrollOffset.y*fpRatio);
00818 
00819     // Offset it by half the size of the window.  WHY?  AND WHY THE MakeLong() CALL?
00820     wcScrollOffset.x = wcScrollOffset.x - (wrView.Width() / 2);
00821     wcScrollOffset.y += wrView.Height() / 2;
00822 
00823     // Check the scroll offsets bounds as we can't have scroll offsets anywhere.
00824     if (wcScrollOffset.x < 0) wcScrollOffset.x = 0;
00825     if (wcScrollOffset.y > 0) wcScrollOffset.y = 0;
00826 
00827     // Set the scale. This must be done before the scroll offset is set or
00828     // strangeness will follow . . .
00829     pDocView->SetViewScale((FIXED16) fpNewScaleFactor);
00830     pDocView->SetScrollOffsets(wcScrollOffset, FALSE);
00831 
00832     // Update the combo-box containing scale factors.
00833     pDocView->SetZoomTableIndex(cFractionalZoomIndex);
00834 #ifndef RALPH
00835     OpZoomComboDescriptor::Update();
00836 #endif
00837 
00838     // We have to force a redraw as the zoom has changed, reset the cursor, and end the
00839     // operation.
00840     pDocView->ForceRedraw(TRUE);
00841     if (ZoomTool::IsSelectedTool() && m_nfShowZoomCursors) CursorStack::GPop(ncsrOldID);
00842     if (fEndOp) End();
00843 
00844 
00845     // tell people things have changed on screen
00846     TRACEUSER( "Diccon", _T("ZoomInOnRect\n"));
00847     BROADCAST_TO_ALL(ScreenChangeMsg(TRUE));
00848 }

void OpZoom::ZoomOut Spread pZoomSpread,
const DocCoord dcZoomPos,
BOOL  fEndOp = TRUE
 

Zooms out of the current DocView by one step. By default this function will call the End() function for this operation afterwards.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
pZoomSpread the spread containing the point to zoom out at [INPUTS] dcZoomPos the point to zoom out at fEndOp whether to end this operation after this zoom

Definition at line 640 of file zoomops.cpp.

00641 {
00642     WorkCoord wcZoom;
00643     SpreadToWork(pZoomSpread, dcZoomPos, &wcZoom);
00644     ZoomOut(wcZoom, fEndOp);
00645 }

void OpZoom::ZoomOut const WorkCoord wcZoom,
BOOL  fEndOp = TRUE
 

Zooms out of the current DocView by one step. By default this function will call the End() function for this operation afterwards.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
wcZoom the point to zoom out at [INPUTS] fEndOp whether to end this operation after this zoom

Definition at line 591 of file zoomops.cpp.

00592 {
00593     // Find out the current view.
00594     DocView* pDocView = DocView::GetCurrent();
00595     ERROR3IF(pDocView == 0, "No selected DocView in OpZoom::ZoomOut");
00596 
00597     if (pDocView)
00598     {
00599         // Get the current view's scaling factor as a rounded precentage.
00600         INT32 nOldScalePercent = ((pDocView->GetViewScale() * 100) + FIXED16_DBL(0.5)).MakeInt();
00601 
00602         // Search forwards through the zoom table until we find a lower zoom factor, or
00603         // until we hit the end of the table, meaning no lower zoom factor exists.
00604         for (INT32 i = 0; i < cZoomTableSize; i++)
00605         {
00606             // Found a lower zoom?  If so, set it, remember it's position in the zoom table
00607             // and return.
00608             if (nOldScalePercent > GetPresetZoomPercent(i))
00609             {
00610                 // Do the zoom.  We will (optionally) end the operation.
00611                 pDocView->SetZoomTableIndex(i);
00612                 ZoomAtPoint(wcZoom, GetPresetZoomScale(i), FALSE);
00613                 break;
00614             }
00615         }
00616     }
00617 
00618     // We must correctly end the operation.
00619     if (fEndOp) End();
00620 
00621     // tell people things have changed on screen
00622     TRACEUSER( "Diccon", _T("ZoomOut\n"));
00623     BROADCAST_TO_ALL(ScreenChangeMsg(TRUE));
00624 }

void OpZoom::ZoomTo const WorkCoord wcZoom,
INT32  nPercent,
BOOL  fEndOp = TRUE
 

Zooms into the current DocView by one step. By default this function will call the End() function for this operation afterwards.

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com>
Date:
23/4/95
Parameters:
wcZoom the point to zoom in at [INPUTS] fEndOp whether to end this operation after this zoom

Definition at line 659 of file zoomops.cpp.

00660 {
00661     // Find out the current view.
00662     DocView* pDocView = DocView::GetCurrent();
00663     ERROR3IF(pDocView == 0, "No current DocView in OpZoom::ZoomIn");
00664     
00665     if (pDocView)
00666     {
00667         // Do the zoom.  We will (optionally) end the operation.
00668         FIXED16     f16Scale = FIXED16(nPercent) / 100;
00669         ZoomAtPoint(wcZoom, f16Scale, FALSE);
00670     }
00671 
00672     // End the operation if the caller wants us to.
00673     if (fEndOp) End();
00674 }


Member Data Documentation

Cursor OpZoom::m_csrZoomDrag [private]
 

Definition at line 232 of file zoomops.h.

Cursor OpZoom::m_csrZoomIn [private]
 

Definition at line 230 of file zoomops.h.

Cursor OpZoom::m_csrZoomOut [private]
 

Definition at line 231 of file zoomops.h.

BOOL OpZoom::m_fFixZoomClickPoint = FALSE [static, private]
 

When zooming in or out with a mouse click, this determines whether to fix the clicked point in the resulting zoomed view at the same screen-relative position, or to centre the zoomed view on the clicked point. By default this is FALSE (don't fix, do centre).

Preference: FixZoomClickPoint Section: Zoom Tool

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> Range: FALSE or TRUE

Definition at line 242 of file zoomops.h.

BOOL OpZoom::m_fRadialZoomDragBox = FALSE [static, private]
 

Determines how the zoom drag operation invokes by the zoom tool will draw its drag box. If FALSE (the default) then the tool will draw the box from one corner to its opposite. This is similar to the selector's drag box. If TRUE then the tool will draw its centre box centred on the point where the drag started and extending to the current mouse position. The effect is to centre the zoom on the first clicked point.

Preference: RadialZoomDragBox Section: Zoom Tool

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> Range: FALSE or TRUE

Definition at line 241 of file zoomops.h.

BOOL OpZoom::m_fStatusTextShown [private]
 

Definition at line 235 of file zoomops.h.

INT32 OpZoom::m_ncsrSaveDrag [private]
 

Definition at line 233 of file zoomops.h.

UINT32 OpZoom::m_nfShowZoomCursors = 0 [static, private]
 

Determines whether to flash a "zooming-in" or "zooming-out" cursor when a zoom is being calculated, and a special drag cursor when dragging in the zoom tool.

Preference: ShowZoomInOutCursors Section: Zoom Tool

Author:
Justin_Flude (Xara Group Ltd) <camelotdev@xara.com> Range: 0 ... 1
Some people think this adds a groovy, polished feel to the program. Others don't, which is why this preference is 0 by default (ie. no special zoom cursors).

Definition at line 243 of file zoomops.h.

WorkCoord OpZoom::m_wcStartPos [private]
 

Definition at line 234 of file zoomops.h.

INT32 OpZoom::ZoomTable [static, private]
 

Initial value:

{
    25601,                  
    16000,
    8000,
    4000,                   
    2000,
    1000,
    500,
    200,
    100,                    
    75,
    50,
    25,
    10,
}

Definition at line 238 of file zoomops.h.


The documentation for this class was generated from the following files:
Generated on Sat Nov 10 03:59:12 2007 for Camelot by  doxygen 1.4.4