diff --git a/include/svx/svdedtv.hxx b/include/svx/svdedtv.hxx index 0b0305c..4f67dbb 100644 --- a/include/svx/svdedtv.hxx +++ b/include/svx/svdedtv.hxx @@ -100,6 +100,7 @@ protected: unsigned bShearAllowed : 1; unsigned bEdgeRadiusAllowed : 1; unsigned bTransparenceAllowed : 1; + unsigned bCropAllowed : 1; unsigned bGradientAllowed : 1; unsigned bCanConvToPath : 1; unsigned bCanConvToPoly : 1; @@ -223,6 +224,7 @@ public: void ShearMarkedObj(const Point& rRef, long nWink, bool bVShear=false, bool bCopy=false); void CrookMarkedObj(const Point& rRef, const Point& rRad, SdrCrookMode eMode, bool bVertical=false, bool bNoContortion=false, bool bCopy=false); void DistortMarkedObj(const Rectangle& rRef, const XPolygon& rDistortedRect, bool bNoContortion=false, bool bCopy=false); + void CropMarkedObj(const Point& rRef, const Fraction& xFact, const Fraction& yFact, bool bCopy=false); // Markierte Objekte kopieren und anstelle der alten markieren void CopyMarkedObj(); @@ -242,6 +244,7 @@ public: sal_Bool IsResizeAllowed(sal_Bool bProp=sal_False) const; sal_Bool IsRotateAllowed(sal_Bool b90Deg=sal_False) const; sal_Bool IsMirrorAllowed(sal_Bool b45Deg=sal_False, sal_Bool b90Deg=sal_False) const; + sal_Bool IsCropAllowed() const; sal_Bool IsTransparenceAllowed() const; sal_Bool IsGradientAllowed() const; sal_Bool IsShearAllowed() const; diff --git a/include/svx/svdobj.hxx b/include/svx/svdobj.hxx index ae32d08d..664775c 100644 --- a/include/svx/svdobj.hxx +++ b/include/svx/svdobj.hxx @@ -709,12 +709,14 @@ public: // Nbc bedeutet: 'NoBroadcast'. virtual void NbcMove (const Size& rSiz); virtual void NbcResize(const Point& rRef, const Fraction& xFact, const Fraction& yFact); + virtual void NbcCrop (const Point& rRef, const Fraction& xFact, const Fraction& yFact); virtual void NbcRotate(const Point& rRef, long nWink, double sn, double cs); virtual void NbcMirror(const Point& rRef1, const Point& rRef2); virtual void NbcShear (const Point& rRef, long nWink, double tn, bool bVShear); virtual void Move (const Size& rSiz); virtual void Resize(const Point& rRef, const Fraction& xFact, const Fraction& yFact, bool bUnsetRelative = true); + virtual void Crop (const Point& rRef, const Fraction& xFact, const Fraction& yFact); virtual void Rotate(const Point& rRef, long nWink, double sn, double cs); virtual void Mirror(const Point& rRef1, const Point& rRef2); virtual void Shear (const Point& rRef, long nWink, double tn, bool bVShear); diff --git a/include/svx/svdograf.hxx b/include/svx/svdograf.hxx index 036a83e..53d1640 100644 --- a/include/svx/svdograf.hxx +++ b/include/svx/svdograf.hxx @@ -162,6 +162,7 @@ public: virtual SdrHdl* GetHdl(sal_uInt32 nHdlNum) const; virtual void NbcResize(const Point& rRef, const Fraction& xFact, const Fraction& yFact); + virtual void NbcCrop (const Point& rRef, const Fraction& xFact, const Fraction& yFact); virtual void NbcRotate(const Point& rRef, long nWink, double sn, double cs); virtual void NbcMirror(const Point& rRef1, const Point& rRef2); virtual void NbcShear (const Point& rRef, long nWink, double tn, bool bVShear); diff --git a/svx/source/svdraw/svddrgmt.cxx b/svx/source/svdraw/svddrgmt.cxx index 2255d58..02b1763 100644 --- a/svx/source/svdraw/svddrgmt.cxx +++ b/svx/source/svdraw/svddrgmt.cxx @@ -3680,83 +3680,12 @@ bool SdrDragCrop::EndSdrDrag(bool bCopy) { Hide(); - if( DragStat().GetDX()==0 && DragStat().GetDY()==0 ) - return false; - - const SdrMarkList& rMarkList = getSdrDragView().GetMarkedObjectList(); - - if( rMarkList.GetMarkCount() != 1 ) - return false; - - SdrGrafObj* pObj = dynamic_cast( rMarkList.GetMark( 0 )->GetMarkedSdrObj() ); - - if( !pObj || (pObj->GetGraphicType() == GRAPHIC_NONE) || (pObj->GetGraphicType() == GRAPHIC_DEFAULT) ) - return false; - - const GraphicObject& rGraphicObject = pObj->GetGraphicObject(); - const MapMode aMapMode100thmm(MAP_100TH_MM); - Size aGraphicSize(rGraphicObject.GetPrefSize()); - - if( MAP_PIXEL == rGraphicObject.GetPrefMapMode().GetMapUnit() ) - aGraphicSize = Application::GetDefaultDevice()->PixelToLogic( aGraphicSize, aMapMode100thmm ); - else - aGraphicSize = Application::GetDefaultDevice()->LogicToLogic( aGraphicSize, rGraphicObject.GetPrefMapMode(), aMapMode100thmm); - - if( aGraphicSize.A() == 0 || aGraphicSize.B() == 0 ) - return false; - - const SdrGrafCropItem& rOldCrop = (const SdrGrafCropItem&)pObj->GetMergedItem(SDRATTR_GRAFCROP); - - const bool bUndo = getSdrDragView().IsUndoEnabled(); - - if( bUndo ) - { - String aUndoStr; - ImpTakeDescriptionStr(STR_DragMethCrop, aUndoStr); - - getSdrDragView().BegUndo( aUndoStr ); - getSdrDragView().AddUndo( getSdrDragView().GetModel()->GetSdrUndoFactory().CreateUndoGeoObject( *pObj ) ); - } - - Rectangle aOldRect( pObj->GetLogicRect() ); - getSdrDragView().ResizeMarkedObj(DragStat().Ref1(),aXFact,aYFact,bCopy); - Rectangle aNewRect( pObj->GetLogicRect() ); - - double fScaleX = ( aGraphicSize.Width() - rOldCrop.GetLeft() - rOldCrop.GetRight() ) / (double)aOldRect.GetWidth(); - double fScaleY = ( aGraphicSize.Height() - rOldCrop.GetTop() - rOldCrop.GetBottom() ) / (double)aOldRect.GetHeight(); - - // to correct the never working combination of cropped images and mirroring - // I have to correct the rectangles the calculation is based on here. In the current - // core geometry stuff a vertical mirror is expressed as 180 degree rotation. All - // this can be removed again when aw080 will have cleaned up the old - // (non-)transformation mess in the core. - if(18000 == pObj->GetGeoStat().nDrehWink) - { - // old notation of vertical mirror, need to correct diffs since both rects - // are rotated by 180 degrees - aOldRect = Rectangle(aOldRect.TopLeft() - (aOldRect.BottomRight() - aOldRect.TopLeft()), aOldRect.TopLeft()); - aNewRect = Rectangle(aNewRect.TopLeft() - (aNewRect.BottomRight() - aNewRect.TopLeft()), aNewRect.TopLeft()); + const bool bDoCrop(DragStat().GetDX()!=0 || DragStat().GetDY()!=0); + if(bDoCrop) { + getSdrDragView().CropMarkedObj(DragStat().Ref1(),aXFact,aYFact,bCopy); + return true; } - - sal_Int32 nDiffLeft = aNewRect.Left() - aOldRect.Left(); - sal_Int32 nDiffTop = aNewRect.Top() - aOldRect.Top(); - sal_Int32 nDiffRight = aNewRect.Right() - aOldRect.Right(); - sal_Int32 nDiffBottom = aNewRect.Bottom() - aOldRect.Bottom(); - - sal_Int32 nLeftCrop = static_cast( rOldCrop.GetLeft() + nDiffLeft * fScaleX ); - sal_Int32 nTopCrop = static_cast( rOldCrop.GetTop() + nDiffTop * fScaleY ); - sal_Int32 nRightCrop = static_cast( rOldCrop.GetRight() - nDiffRight * fScaleX ); - sal_Int32 nBottomCrop = static_cast( rOldCrop.GetBottom() - nDiffBottom * fScaleY ); - - SfxItemPool& rPool = getSdrDragView().GetModel()->GetItemPool(); - SfxItemSet aSet( rPool, SDRATTR_GRAFCROP, SDRATTR_GRAFCROP ); - aSet.Put( SdrGrafCropItem( nLeftCrop, nTopCrop, nRightCrop, nBottomCrop ) ); - getSdrDragView().SetAttributes( aSet, false ); - - if( bUndo ) - getSdrDragView().EndUndo(); - - return true; + return false; } Pointer SdrDragCrop::GetSdrDragPointer() const diff --git a/svx/source/svdraw/svddrgv.cxx b/svx/source/svdraw/svddrgv.cxx index e4cbdd4..c3e3418 100644 --- a/svx/source/svdraw/svddrgv.cxx +++ b/svx/source/svdraw/svddrgv.cxx @@ -334,7 +334,7 @@ sal_Bool SdrDragView::BegDragObj(const Point& rPnt, OutputDevice* pOut, SdrHdl* } else { - if (!IsCrookAllowed(sal_True) && !IsCrookAllowed(sal_False)) + if (!IsCropAllowed()) return sal_False; mpCurrentSdrDragMethod = new SdrDragCrop(*this); } diff --git a/svx/source/svdraw/svdedtv.cxx b/svx/source/svdraw/svdedtv.cxx index 0194e05..48285ef 100644 --- a/svx/source/svdraw/svdedtv.cxx +++ b/svx/source/svdraw/svdedtv.cxx @@ -71,6 +71,7 @@ void SdrEditView::ImpResetPossibilityFlags() bMirror45Allowed =sal_False; bMirror90Allowed =sal_False; bTransparenceAllowed =sal_False; + bCropAllowed =sal_False; bGradientAllowed =sal_False; bShearAllowed =sal_False; bEdgeRadiusAllowed =sal_False; @@ -403,6 +404,12 @@ sal_Bool SdrEditView::IsTransparenceAllowed() const return bTransparenceAllowed; } +sal_Bool SdrEditView::IsCropAllowed() const +{ + ForcePossibilities(); + return bCropAllowed; +} + sal_Bool SdrEditView::IsGradientAllowed() const { ForcePossibilities(); @@ -509,6 +516,7 @@ void SdrEditView::CheckPossibilities() // these ones are only allowed when single object is selected bTransparenceAllowed = (nMarkAnz == 1); + bCropAllowed = (nMarkAnz == 1); bGradientAllowed = (nMarkAnz == 1); if(bGradientAllowed) { @@ -577,6 +585,10 @@ void SdrEditView::CheckPossibilities() } } + // Must be resizeable to allow cropping + if (!aInfo.bResizeFreeAllowed && !aInfo.bResizePropAllowed) + bCropAllowed=sal_False; + // if one member cannot be converted, no conversion is possible if(!aInfo.bCanConvToContour) bCanConvToContour = sal_False; diff --git a/svx/source/svdraw/svdedtv1.cxx b/svx/source/svdraw/svdedtv1.cxx index 6468c91..691ad75 100644 --- a/svx/source/svdraw/svdedtv1.cxx +++ b/svx/source/svdraw/svdedtv1.cxx @@ -288,6 +288,38 @@ void SdrEditView::ResizeMultMarkedObj(const Point& rRef, EndUndo(); } +void SdrEditView::CropMarkedObj(const Point& rRef, const Fraction& xFact, const Fraction& yFact, bool /*bCopy*/) +{ + const bool bUndo = IsUndoEnabled(); + + if( bUndo ) + { + String aUndoStr; + ImpTakeDescriptionStr(STR_DragMethCrop, aUndoStr); + + BegUndo( aUndoStr ); + } + + sal_uIntPtr nMarkAnz=GetMarkedObjectCount(); + for (sal_uIntPtr nm=0; nmGetMarkedSdrObj(); + if( bUndo ) + { + std::vector< SdrUndoAction* > vConnectorUndoActions( CreateConnectorUndo( *pO ) ); + AddUndoActions( vConnectorUndoActions ); + AddUndo( GetModel()->GetSdrUndoFactory().CreateUndoGeoObject(*pO)); + } + // Sw: next call is SwVirtFlyDrawObj->Crop + // Impress: next call is SdrGrafObj->Crop with code that was previously in SdrDragCrop + pO->Crop(rRef,xFact,yFact); + } + + if( bUndo ) + EndUndo(); +} + long SdrEditView::GetMarkedObjRotate() const { long nRetval(0); diff --git a/svx/source/svdraw/svdobj.cxx b/svx/source/svdraw/svdobj.cxx index 571b729..9fcd6d4 100644 --- a/svx/source/svdraw/svdobj.cxx +++ b/svx/source/svdraw/svdobj.cxx @@ -1501,6 +1501,10 @@ void SdrObject::NbcResize(const Point& rRef, const Fraction& xFact, const Fracti SetRectsDirty(); } +void SdrObject::NbcCrop(const Point& rRef, const Fraction& xFact, const Fraction& yFact) +{ +} + void SdrObject::NbcRotate(const Point& rRef, long nWink, double sn, double cs) { SetGlueReallyAbsolute(true); @@ -1594,6 +1598,15 @@ void SdrObject::Resize(const Point& rRef, const Fraction& xFact, const Fraction& } } +void SdrObject::Crop(const Point& rRef, const Fraction& xFact, const Fraction& yFact) +{ + Rectangle aBoundRect0; if (pUserCall!=NULL) aBoundRect0=GetLastBoundRect(); + NbcCrop(rRef, xFact, yFact); + SetChanged(); + BroadcastObjectChange(); + SendUserCall(SDRUSERCALL_RESIZE,aBoundRect0); +} + void SdrObject::Rotate(const Point& rRef, long nWink, double sn, double cs) { if (nWink!=0) { diff --git a/svx/source/svdraw/svdograf.cxx b/svx/source/svdraw/svdograf.cxx index 00da762..fdd446a 100644 --- a/svx/source/svdraw/svdograf.cxx +++ b/svx/source/svdraw/svdograf.cxx @@ -900,6 +900,79 @@ void SdrGrafObj::NbcResize(const Point& rRef, const Fraction& xFact, const Fract bMirrored = !bMirrored; } +void SdrGrafObj::NbcCrop(const Point& rRef, const Fraction& xFact, const Fraction& yFact) +{ + + if( (GetGraphicType() == GRAPHIC_NONE) || (GetGraphicType() == GRAPHIC_DEFAULT) ) + return; + + const GraphicObject& rGraphicObject = GetGraphicObject(); + const MapMode aMapMode100thmm(MAP_100TH_MM); + Size aGraphicSize(rGraphicObject.GetPrefSize()); + + if( MAP_PIXEL == rGraphicObject.GetPrefMapMode().GetMapUnit() ) + aGraphicSize = Application::GetDefaultDevice()->PixelToLogic( aGraphicSize, aMapMode100thmm ); + else + aGraphicSize = Application::GetDefaultDevice()->LogicToLogic( aGraphicSize, rGraphicObject.GetPrefMapMode(), aMapMode100thmm); + + if( aGraphicSize.A() == 0 || aGraphicSize.B() == 0 ) + return ; + + const SdrGrafCropItem& rOldCrop = (const SdrGrafCropItem&)GetMergedItem(SDRATTR_GRAFCROP); + +// const bool bUndo = getSdrDragView().IsUndoEnabled(); + +// if( bUndo ) +// { +// String aUndoStr; +// ImpTakeDescriptionStr(STR_DragMethCrop, aUndoStr); + +// getSdrDragView().BegUndo( aUndoStr ); +// getSdrDragView().AddUndo( getSdrDragView().GetModel()->GetSdrUndoFactory().CreateUndoGeoObject( *this ) ); +// } + + Rectangle aOldRect( GetLogicRect() ); + SdrRectObj::NbcResize( rRef, xFact, yFact ); + Rectangle aNewRect( GetLogicRect() ); + + double fScaleX = ( aGraphicSize.Width() - rOldCrop.GetLeft() - rOldCrop.GetRight() ) / (double)aOldRect.GetWidth(); + double fScaleY = ( aGraphicSize.Height() - rOldCrop.GetTop() - rOldCrop.GetBottom() ) / (double)aOldRect.GetHeight(); + + // to correct the never working combination of cropped images and mirroring + // I have to correct the rectangles the calculation is based on here. In the current + // core geometry stuff a vertical mirror is expressed as 180 degree rotation. All + // this can be removed again when aw080 will have cleaned up the old + // (non-)transformation mess in the core. + if(18000 == GetGeoStat().nDrehWink) + { + // old notation of vertical mirror, need to correct diffs since both rects + // are rotated by 180 degrees + aOldRect = Rectangle(aOldRect.TopLeft() - (aOldRect.BottomRight() - aOldRect.TopLeft()), aOldRect.TopLeft()); + aNewRect = Rectangle(aNewRect.TopLeft() - (aNewRect.BottomRight() - aNewRect.TopLeft()), aNewRect.TopLeft()); + } + + sal_Int32 nDiffLeft = aNewRect.Left() - aOldRect.Left(); + sal_Int32 nDiffTop = aNewRect.Top() - aOldRect.Top(); + sal_Int32 nDiffRight = aNewRect.Right() - aOldRect.Right(); + sal_Int32 nDiffBottom = aNewRect.Bottom() - aOldRect.Bottom(); + + sal_Int32 nLeftCrop = static_cast( rOldCrop.GetLeft() + nDiffLeft * fScaleX ); + sal_Int32 nTopCrop = static_cast( rOldCrop.GetTop() + nDiffTop * fScaleY ); + sal_Int32 nRightCrop = static_cast( rOldCrop.GetRight() - nDiffRight * fScaleX ); + sal_Int32 nBottomCrop = static_cast( rOldCrop.GetBottom() - nDiffBottom * fScaleY ); + + SfxItemPool& rPool = GetModel()->GetItemPool(); + SfxItemSet aSet( rPool, SDRATTR_GRAFCROP, SDRATTR_GRAFCROP ); + aSet.Put( SdrGrafCropItem( nLeftCrop, nTopCrop, nRightCrop, nBottomCrop ) ); + SetMergedItemSet( aSet ); +// SetAttributes( aSet, false ); + +// if( bUndo ) +// getSdrDragView().EndUndo(); + +// return true; +} + void SdrGrafObj::NbcRotate(const Point& rRef, long nWink, double sn, double cs) { SdrRectObj::NbcRotate(rRef,nWink,sn,cs); diff --git a/sw/inc/cmdid.h b/sw/inc/cmdid.h index dee921d..1d1df6f 100644 --- a/sw/inc/cmdid.h +++ b/sw/inc/cmdid.h @@ -891,6 +891,7 @@ included in c-context files, so c++ style stuff will cause problems. #define FN_HORI_ORIENT (FN_FRAME + 5) #define FN_SET_FRM_NAME (FN_FRAME + 6) #define FN_KEEP_ASPECT_RATIO (FN_FRAME + 7) +#define SID_OBJECT_CROP (FN_FRAME + 8) /* Crop image */ #define FN_SET_FRM_ALT_NAME (FN_FRAME + 18) #define FN_UNO_TITLE (FN_FRAME + 19) diff --git a/sw/inc/fesh.hxx b/sw/inc/fesh.hxx index c68a6c0..4d2e56a 100644 --- a/sw/inc/fesh.hxx +++ b/sw/inc/fesh.hxx @@ -240,6 +240,11 @@ public: sal_Bool SelectObj( const Point& rSelPt, sal_uInt8 nFlag = 0, SdrObject *pObj = 0 ); void DelSelectedObj(); + // Overrides SdrEditView method because selected object in sw + // is a virtual fly draw obj whereas default behaviour expects + // the selected object to be a SdrGrafObj + virtual SdrObject* GetMarkedObjToCrop(); + /** Move selection upwards or downwards (Z-Order). TRUE = to top or bottom. FALSE = run past one other. */ @@ -458,6 +463,12 @@ public: /// Set DragMode (e.g. Rotae), but do nothing when frame is selected. void SetDragMode( sal_uInt16 eSdrDragMode ); + // Get the current drag mode + SdrDragMode GetDragMode() const; + + // Start cropping the selected image + void StartCropImage(); + sal_uInt16 IsObjSelected() const; ///< @return object count, but doesn't count the objects in groups. sal_Bool IsObjSelected( const SdrObject& rObj ) const; diff --git a/sw/sdi/_grfsh.sdi b/sw/sdi/_grfsh.sdi index 15c00cc..fe5d4ee 100644 --- a/sw/sdi/_grfsh.sdi +++ b/sw/sdi/_grfsh.sdi @@ -21,6 +21,13 @@ interface BaseTextGraphic Automation = FALSE; ] { + SID_OBJECT_CROP // ole : no, status : play rec + [ + ExecMethod = Execute ; + StateMethod = GetState ; + DisableFlags="SW_DISABLE_ON_PROTECTED_CURSOR"; + ] + SID_FLIP_VERTICAL [ ExecMethod = ExecAttr ; diff --git a/sw/sdi/swriter.sdi b/sw/sdi/swriter.sdi index c5b7326..23782d7 100644 --- a/sw/sdi/swriter.sdi +++ b/sw/sdi/swriter.sdi @@ -1033,6 +1033,34 @@ SfxVoidItem CreateAbstract FN_ABSTRACT_NEWDOC GroupId = GID_DOCUMENT; ] +SfxVoidItem Crop SID_OBJECT_CROP +() +[ + /* flags: */ + AutoUpdate = TRUE, + Cachable = Cachable, + FastCall = FALSE, + HasCoreId = FALSE, + HasDialog = FALSE, + ReadOnlyDoc = TRUE, + Toggle = FALSE, + Container = FALSE, + RecordAbsolute = FALSE, + RecordPerSet; + Synchron; + + /* status: */ + SlotType = SfxBoolItem + + /* config: */ + AccelConfig = TRUE, + MenuConfig = TRUE, + StatusBarConfig = FALSE, + ToolBoxConfig = TRUE, + GroupId = GID_FORMAT ; +] + + //-------------------------------------------------------------------------- SfxVoidItem DecrementIndentValue FN_DEC_INDENT_OFFSET () diff --git a/sw/source/core/draw/dflyobj.cxx b/sw/source/core/draw/dflyobj.cxx index ab9c5bc..5ddd372 100644 --- a/sw/source/core/draw/dflyobj.cxx +++ b/sw/source/core/draw/dflyobj.cxx @@ -56,6 +56,10 @@ #include #include +#include +#include "wrtsh.hxx" +#include + using namespace ::com::sun::star; static bool bInResize = false; @@ -727,6 +731,82 @@ void SwVirtFlyDrawObj::NbcMove(const Size& rSiz) pFmt->SetFmtAttr( aSet ); } +void SwVirtFlyDrawObj::NbcCrop(const Point& rRef, + const Fraction& xFact, const Fraction& yFact) +{ + // Get Wrt Shell + SwWrtShell *pSh = dynamic_cast( GetFlyFrm()->getRootFrm()->GetCurrShell() ); + if (!pSh || !pSh->ISA(SwWrtShell)) + return; + + // Compute old and new rect. This will give us the deformation to apply to + // the object to crop + Rectangle aOldRect( aOutRect ); + + Rectangle aNewRect( aOutRect ); + ResizeRect( aNewRect, rRef, xFact, yFact ); + + // Get graphic object size in 100th of mm + GraphicObject *pGraphicObject = (GraphicObject *) pSh->GetGraphicObj(); + if (!pGraphicObject) + return; + const MapMode aMapMode100thmm(MAP_100TH_MM); + Size aGraphicSize(pGraphicObject->GetPrefSize()); + if( MAP_PIXEL == pGraphicObject->GetPrefMapMode().GetMapUnit() ) + aGraphicSize = Application::GetDefaultDevice()->PixelToLogic( aGraphicSize, aMapMode100thmm ); + else + aGraphicSize = Application::GetDefaultDevice()->LogicToLogic( aGraphicSize, pGraphicObject->GetPrefMapMode(), aMapMode100thmm); + if( aGraphicSize.A() == 0 || aGraphicSize.B() == 0 ) + return ; + + // Get old values for crop in 10th of mm + SfxItemSet aSet( pSh->GetAttrPool(), RES_GRFATR_CROPGRF, RES_GRFATR_CROPGRF ); + pSh->GetCurAttr( aSet ); + SwCropGrf aCrop( (const SwCropGrf&) aSet.Get(RES_GRFATR_CROPGRF) ); + Rectangle aCropRectangle( + TWIP_TO_MM100(aCrop.GetLeft()), + TWIP_TO_MM100(aCrop.GetTop()), + TWIP_TO_MM100(aCrop.GetRight()), + TWIP_TO_MM100(aCrop.GetBottom()) ); + + // Compute delta to apply + double fScaleX = ( aGraphicSize.Width() - aCropRectangle.Left() - aCropRectangle.Right() ) / (double)aOldRect.GetWidth(); + double fScaleY = ( aGraphicSize.Height() - aCropRectangle.Top() - aCropRectangle.Bottom() ) / (double)aOldRect.GetHeight(); + + sal_Int32 nDiffLeft = aNewRect.Left() - aOldRect.Left(); + sal_Int32 nDiffTop = aNewRect.Top() - aOldRect.Top(); + sal_Int32 nDiffRight = aNewRect.Right() - aOldRect.Right(); + sal_Int32 nDiffBottom = aNewRect.Bottom() - aOldRect.Bottom(); + + // Compute new values in 10th of mm + sal_Int32 nLeftCrop = static_cast( aCropRectangle.Left() + nDiffLeft * fScaleX ); + sal_Int32 nTopCrop = static_cast( aCropRectangle.Top() + nDiffTop * fScaleY ); + sal_Int32 nRightCrop = static_cast( aCropRectangle.Right() - nDiffRight * fScaleX ); + sal_Int32 nBottomCrop = static_cast( aCropRectangle.Bottom() - nDiffBottom * fScaleY ); + + // Apply values + pSh->StartAllAction(); +// pSh->StartUndo(UNDO_START); + + // Set new crop values in twips + aCrop.SetLeft(MM100_TO_TWIP(nLeftCrop)); + aCrop.SetTop(MM100_TO_TWIP(nTopCrop)); + aCrop.SetRight(MM100_TO_TWIP(nRightCrop)); + aCrop.SetBottom(MM100_TO_TWIP(nBottomCrop )); + pSh->SetAttr(aCrop); + + // Set new frame size + SwFrmFmt *pFmt = GetFmt(); + SwFmtFrmSize aSz( pFmt->GetFrmSize() ); + aSz.SetWidth(aNewRect.GetWidth()); + aSz.SetHeight(aNewRect.GetHeight()); + pFmt->GetDoc()->SetAttr( aSz, *pFmt ); + +// pSh->EndUndo(UNDO_END); + pSh->EndAllAction(); +} + + void SwVirtFlyDrawObj::NbcResize(const Point& rRef, const Fraction& xFact, const Fraction& yFact) { @@ -849,6 +929,14 @@ void SwVirtFlyDrawObj::Resize(const Point& rRef, GetFmt()->GetDoc()->GetIDocumentUndoRedo().DoDrawUndo(false); } +void SwVirtFlyDrawObj::Crop(const Point& rRef, + const Fraction& xFact, const Fraction& yFact) +{ + NbcCrop( rRef, xFact, yFact ); + SetChanged(); + GetFmt()->GetDoc()->GetIDocumentUndoRedo().DoDrawUndo(false); +} + // Macro Pointer SwVirtFlyDrawObj::GetMacroPointer( diff --git a/sw/source/core/frmedt/feshview.cxx b/sw/source/core/frmedt/feshview.cxx index 535c67e..65179af 100644 --- a/sw/source/core/frmedt/feshview.cxx +++ b/sw/source/core/frmedt/feshview.cxx @@ -247,6 +247,22 @@ sal_Bool SwFEShell::SelectObj( const Point& rPt, sal_uInt8 nFlag, SdrObject *pOb return bRet; } +// Overrides SdrEditView method because selected object in sw +// is a virtual fly draw obj whereas default behaviour expects +// the selected object to be a SdrGrafObj +SdrObject* SwFEShell::GetMarkedObjToCrop() +{ + SwFlyFrm* pFrm = GetFlyFromMarked(NULL, this); + if (!pFrm) + { + return NULL; + } + + SdrObject* pSdrObj = pFrm->GetVirtDrawObj(); + + return pSdrObj; +} + /************************************************************************* |* |* sal_Bool SwFEShell::MoveAnchor( sal_uInt16 nDir ) @@ -611,6 +627,65 @@ void SwFEShell::SetDragMode( sal_uInt16 eDragMode ) /************************************************************************* |* +|* SwFEShell::GetDragMode() +|* +*************************************************************************/ + +SdrDragMode SwFEShell::GetDragMode() const +{ + SdrDragMode nRet = (SdrDragMode)0; + if ( Imp()->HasDrawView() ) + { + nRet = Imp()->GetDrawView()->GetDragMode(); + } + return nRet; +} + +/************************************************************************* +|* +|* SwFEShell::StartCropImage() +|* +*************************************************************************/ + +void SwFEShell::StartCropImage() +{ + if ( !Imp()->HasDrawView() ) + { + return; + } + SdrView *pView = Imp()->GetDrawView(); + if (!pView) return; + + const SdrMarkList &rMarkList = pView->GetMarkedObjectList(); + if( 0 == rMarkList.GetMarkCount() ) { + // No object selected + return; + } + + // If more than a single SwVirtFlyDrawObj is selected, select only the first SwVirtFlyDrawObj + if ( rMarkList.GetMarkCount() > 1 ) + { + for ( sal_uInt16 i = 0; i < rMarkList.GetMarkCount(); ++i ) + { + SdrObject *pTmpObj = rMarkList.GetMark( i )->GetMarkedSdrObj(); + sal_Bool bForget = pTmpObj->ISA(SwVirtFlyDrawObj); + if( bForget ) + { + pView->UnmarkAll(); + pView->MarkObj( pTmpObj, Imp()->GetPageView(), sal_False, sal_False ); + break; + } + } + } + + // Activate CROP mode + pView->SetEditMode( SDREDITMODE_EDIT ); + SetDragMode( SDRDRAG_CROP ); +} + + +/************************************************************************* +|* |* SwFEShell::BeginDrag() |* *************************************************************************/ @@ -693,6 +768,11 @@ long SwFEShell::EndDrag( const Point *, sal_Bool ) GetDoc()->SetModified(); ::FrameNotify( this, FLY_DRAG ); + // Cancel crop mode + if ( SDRDRAG_CROP == GetDragMode() ) + { + SetDragMode( SDRDRAG_MOVE ); + } return 1; } return 0; diff --git a/sw/source/core/inc/dflyobj.hxx b/sw/source/core/inc/dflyobj.hxx index 5dd9133..3e3796f 100644 --- a/sw/source/core/inc/dflyobj.hxx +++ b/sw/source/core/inc/dflyobj.hxx @@ -99,9 +99,13 @@ public: virtual void NbcMove (const Size& rSiz); virtual void NbcResize(const Point& rRef, const Fraction& xFact, const Fraction& yFact); + virtual void NbcCrop(const Point& rRef, const Fraction& xFact, + const Fraction& yFact); virtual void Move (const Size& rSiz); virtual void Resize(const Point& rRef, const Fraction& xFact, const Fraction& yFact, bool bUnsetRelative = true); + virtual void Crop(const Point& rRef, const Fraction& xFact, + const Fraction& yFact); const SwFrmFmt *GetFmt() const; SwFrmFmt *GetFmt(); diff --git a/sw/source/ui/shells/grfsh.cxx b/sw/source/ui/shells/grfsh.cxx index 33108c0..f271585 100644 --- a/sw/source/ui/shells/grfsh.cxx +++ b/sw/source/ui/shells/grfsh.cxx @@ -105,6 +105,15 @@ void SwGrfShell::Execute(SfxRequest &rReq) sal_uInt16 nSlot = rReq.GetSlot(); switch(nSlot) { + case SID_OBJECT_CROP: + { + GraphicObject *pGraphicObject = (GraphicObject *) rSh.GetGraphicObj(); + if (0 != pGraphicObject && SDRDRAG_CROP != rSh.GetDragMode()) { + rSh.StartCropImage(); + } + break; + } + case SID_TWAIN_TRANSFER: { GetView().ExecuteScan( rReq ); @@ -631,6 +640,11 @@ void SwGrfShell::GetAttrState(SfxItemSet &rSet) } break; +// case SID_ATTR_GRAF_CROP: +// if( !bParentCntProt ) { +// rSet.Put(SfxBoolItem( nWhich, true)); +// } +// break; case SID_ATTR_GRAF_LUMINANCE: if( !bParentCntProt ) diff --git a/sw/uiconfig/swriter/toolbar/graphicobjectbar.xml b/sw/uiconfig/swriter/toolbar/graphicobjectbar.xml index 6e7201c..babc2f9 100644 --- a/sw/uiconfig/swriter/toolbar/graphicobjectbar.xml +++ b/sw/uiconfig/swriter/toolbar/graphicobjectbar.xml @@ -31,5 +31,7 @@ + +