diff --git a/gfx/public/nsIRenderingContext.h b/gfx/public/nsIRenderingContext.h index 746d5439a61a..c9b38d714c07 100644 --- a/gfx/public/nsIRenderingContext.h +++ b/gfx/public/nsIRenderingContext.h @@ -325,6 +325,21 @@ public: */ NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) = 0; + /** + * XOR Invert a rectangle in the current foreground color + * @param aRect The rectangle to draw + */ + NS_IMETHOD InvertRect(const nsRect& aRect) = 0; + + /** + * XOR Invert a rectangle in the current foreground color + * @param aX Horizontal left Coordinate in twips + * @param aY Vertical top Coordinate in twips + * @param aWidth Width of rectangle in twips + * @param aHeight Height of rectangle in twips + */ + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) = 0; + /** * Draw a poly in the current foreground color * @param aPoints points to use for the drawing, last must equal first diff --git a/gfx/src/beos/nsRenderingContextBeOS.cpp b/gfx/src/beos/nsRenderingContextBeOS.cpp index 7807f3ff4d30..8bd9e925033b 100644 --- a/gfx/src/beos/nsRenderingContextBeOS.cpp +++ b/gfx/src/beos/nsRenderingContextBeOS.cpp @@ -823,6 +823,22 @@ NS_IMETHODIMP nsRenderingContextBeOS::FillRect(nscoord aX, nscoord aY, nscoord a return NS_OK; } +NS_IMETHODIMP +nsRenderingContextBeOS :: InvertRect(const nsRect& aRect) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextBeOS::InvertRect"); + + return NS_OK; +} + +NS_IMETHODIMP +nsRenderingContextBeOS :: InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextBeOS::InvertRect"); + + return NS_OK; +} + NS_IMETHODIMP nsRenderingContextBeOS::DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints) { // First transform nsPoint's into BPoint's; perform coordinate space diff --git a/gfx/src/beos/nsRenderingContextBeOS.h b/gfx/src/beos/nsRenderingContextBeOS.h index 569029e5d99a..a921dbb9ce41 100644 --- a/gfx/src/beos/nsRenderingContextBeOS.h +++ b/gfx/src/beos/nsRenderingContextBeOS.h @@ -96,9 +96,13 @@ public: NS_IMETHOD DrawRect(const nsRect& aRect); NS_IMETHOD DrawRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD FillRect(const nsRect& aRect); NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/gfx/src/gtk/nsRenderingContextGTK.cpp b/gfx/src/gtk/nsRenderingContextGTK.cpp index 8d716d186cb6..ebe6d0b10f92 100644 --- a/gfx/src/gtk/nsRenderingContextGTK.cpp +++ b/gfx/src/gtk/nsRenderingContextGTK.cpp @@ -745,6 +745,40 @@ NS_IMETHODIMP nsRenderingContextGTK::FillRect(nscoord aX, nscoord aY, nscoord aW return NS_OK; } +NS_IMETHODIMP nsRenderingContextGTK::InvertRect(const nsRect& aRect) +{ + return InvertRect(aRect.x, aRect.y, aRect.width, aRect.height); +} + +NS_IMETHODIMP nsRenderingContextGTK::InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + if (nsnull == mTMatrix || nsnull == mSurface) { + return NS_ERROR_FAILURE; + } + + nscoord x,y,w,h; + + x = aX; + y = aY; + w = aWidth; + h = aHeight; + + mTMatrix->TransformCoord(&x,&y,&w,&h); + + // Set XOR drawing mode + ::gdk_gc_set_function(mSurface->GetGC(),GDK_XOR); + + // Fill the rect + ::gdk_draw_rectangle(mSurface->GetDrawable(), mSurface->GetGC(), + TRUE, + x, y, w, h); + + // Back to normal copy drawing mode + ::gdk_gc_set_function(mSurface->GetGC(),GDK_COPY); + + return NS_OK; +} + NS_IMETHODIMP nsRenderingContextGTK::DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints) { g_return_val_if_fail(mTMatrix != NULL, NS_ERROR_FAILURE); diff --git a/gfx/src/gtk/nsRenderingContextGTK.h b/gfx/src/gtk/nsRenderingContextGTK.h index 34e5d47b32a0..3971b8435924 100644 --- a/gfx/src/gtk/nsRenderingContextGTK.h +++ b/gfx/src/gtk/nsRenderingContextGTK.h @@ -98,9 +98,13 @@ public: NS_IMETHOD DrawRect(const nsRect& aRect); NS_IMETHOD DrawRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD FillRect(const nsRect& aRect); NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/gfx/src/motif/nsRenderingContextMotif.cpp b/gfx/src/motif/nsRenderingContextMotif.cpp index baccb3718afb..1501ed95f19c 100644 --- a/gfx/src/motif/nsRenderingContextMotif.cpp +++ b/gfx/src/motif/nsRenderingContextMotif.cpp @@ -992,6 +992,21 @@ NS_IMETHODIMP nsRenderingContextMotif :: FillRect(nscoord aX, nscoord aY, nscoor return NS_OK; } +NS_IMETHODIMP +nsRenderingContextMotif :: InvertRect(const nsRect& aRect) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextMotif::InvertRect"); + + return NS_OK; +} + +NS_IMETHODIMP +nsRenderingContextMotif :: InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextMotif::InvertRect"); + + return NS_OK; +} NS_IMETHODIMP nsRenderingContextMotif::DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints) { diff --git a/gfx/src/motif/nsRenderingContextMotif.h b/gfx/src/motif/nsRenderingContextMotif.h index e9e3ab873f6f..fb54b3b650e1 100644 --- a/gfx/src/motif/nsRenderingContextMotif.h +++ b/gfx/src/motif/nsRenderingContextMotif.h @@ -106,9 +106,13 @@ public: NS_IMETHOD DrawRect(const nsRect& aRect); NS_IMETHOD DrawRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD FillRect(const nsRect& aRect); NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/gfx/src/os2/nsRenderingContextOS2.cpp b/gfx/src/os2/nsRenderingContextOS2.cpp index 5065c695e640..fa81c4033c9b 100644 --- a/gfx/src/os2/nsRenderingContextOS2.cpp +++ b/gfx/src/os2/nsRenderingContextOS2.cpp @@ -1003,6 +1003,22 @@ nsresult nsRenderingContextOS2::FillRect( nscoord aX, nscoord aY, nscoord aWidth return NS_OK; } +NS_IMETHODIMP +nsRenderingContextOS2 :: InvertRect(const nsRect& aRect) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextOS2::InvertRect"); + + return NS_OK; +} + +NS_IMETHODIMP +nsRenderingContextOS2 :: InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextOS2::InvertRect"); + + return NS_OK; +} + void nsRenderingContextOS2::PMDrawRect( nsRect &rect, BOOL fill) { mTMatrix.TransformCoord( &rect.x, &rect.y, &rect.width, &rect.height); diff --git a/gfx/src/os2/nsRenderingContextOS2.h b/gfx/src/os2/nsRenderingContextOS2.h index 1cc8a961f847..79530fbea2e0 100644 --- a/gfx/src/os2/nsRenderingContextOS2.h +++ b/gfx/src/os2/nsRenderingContextOS2.h @@ -112,6 +112,9 @@ class nsRenderingContextOS2 : public nsIRenderingContext, NS_IMETHOD FillRect( const nsRect& aRect); NS_IMETHOD FillRect( nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon( const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon( const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/gfx/src/photon/nsRenderingContextPh.cpp b/gfx/src/photon/nsRenderingContextPh.cpp index 92af98181b86..1813fc7ded4c 100644 --- a/gfx/src/photon/nsRenderingContextPh.cpp +++ b/gfx/src/photon/nsRenderingContextPh.cpp @@ -996,6 +996,21 @@ NS_IMETHODIMP nsRenderingContextPh :: FillRect(nscoord aX, nscoord aY, nscoord a return NS_OK; } +NS_IMETHODIMP +nsRenderingContextPh :: InvertRect(const nsRect& aRect) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextPh::InvertRect"); + + return NS_OK; +} + +NS_IMETHODIMP +nsRenderingContextPh :: InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextPh::InvertRect"); + + return NS_OK; +} NS_IMETHODIMP nsRenderingContextPh :: DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints) { diff --git a/gfx/src/photon/nsRenderingContextPh.h b/gfx/src/photon/nsRenderingContextPh.h index 6ca046cdb52d..bb2e7dd107da 100644 --- a/gfx/src/photon/nsRenderingContextPh.h +++ b/gfx/src/photon/nsRenderingContextPh.h @@ -106,9 +106,13 @@ public: NS_IMETHOD DrawRect(const nsRect& aRect); NS_IMETHOD DrawRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD FillRect(const nsRect& aRect); NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/gfx/src/ps/nsRenderingContextPS.cpp b/gfx/src/ps/nsRenderingContextPS.cpp index 41e012f6a044..958d36ee467a 100644 --- a/gfx/src/ps/nsRenderingContextPS.cpp +++ b/gfx/src/ps/nsRenderingContextPS.cpp @@ -724,6 +724,22 @@ nsRenderingContextPS :: FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord return NS_OK; } +NS_IMETHODIMP +nsRenderingContextPS :: InvertRect(const nsRect& aRect) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextPS::InvertRect"); + + return NS_OK; +} + +NS_IMETHODIMP +nsRenderingContextPS :: InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + NS_NOTYETIMPLEMENTED("nsRenderingContextPS::InvertRect"); + + return NS_OK; +} + /** --------------------------------------------------- * See documentation in nsIRenderingContext.h * @update 12/21/98 dwc diff --git a/gfx/src/ps/nsRenderingContextPS.h b/gfx/src/ps/nsRenderingContextPS.h index 68bbda0e2f2b..e8ed67d36f59 100644 --- a/gfx/src/ps/nsRenderingContextPS.h +++ b/gfx/src/ps/nsRenderingContextPS.h @@ -104,9 +104,13 @@ public: NS_IMETHOD DrawRect(const nsRect& aRect); NS_IMETHOD DrawRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD FillRect(const nsRect& aRect); NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/gfx/src/windows/nsRenderingContextWin.cpp b/gfx/src/windows/nsRenderingContextWin.cpp index 4240ff945d37..08a61a79b805 100644 --- a/gfx/src/windows/nsRenderingContextWin.cpp +++ b/gfx/src/windows/nsRenderingContextWin.cpp @@ -1202,6 +1202,35 @@ NS_IMETHODIMP nsRenderingContextWin :: FillRect(nscoord aX, nscoord aY, nscoord return NS_OK; } +NS_IMETHODIMP nsRenderingContextWin :: InvertRect(const nsRect& aRect) +{ + RECT nr; + nsRect tr; + + tr = aRect; + mTMatrix->TransformCoord(&tr.x,&tr.y,&tr.width,&tr.height); + ConditionRect(tr, nr); + ::InvertRect(mDC, &nr); + + return NS_OK; +} + +NS_IMETHODIMP nsRenderingContextWin :: InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + RECT nr; + nsRect tr; + + mTMatrix->TransformCoord(&aX,&aY,&aWidth,&aHeight); + nr.left = aX; + nr.top = aY; + nr.right = aX+aWidth; + nr.bottom = aY+aHeight; + + ::InvertRect(mDC, &nr); + + return NS_OK; +} + NS_IMETHODIMP nsRenderingContextWin :: DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints) { // First transform nsPoint's into POINT's; perform coordinate space diff --git a/gfx/src/windows/nsRenderingContextWin.h b/gfx/src/windows/nsRenderingContextWin.h index 0bc3cfd1207a..7ac4951d19b4 100644 --- a/gfx/src/windows/nsRenderingContextWin.h +++ b/gfx/src/windows/nsRenderingContextWin.h @@ -102,9 +102,13 @@ public: NS_IMETHOD DrawRect(const nsRect& aRect); NS_IMETHOD DrawRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD FillRect(const nsRect& aRect); NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/gfx/src/xlib/nsRenderingContextXlib.cpp b/gfx/src/xlib/nsRenderingContextXlib.cpp index 43d67b877c70..f7ec2fc63785 100644 --- a/gfx/src/xlib/nsRenderingContextXlib.cpp +++ b/gfx/src/xlib/nsRenderingContextXlib.cpp @@ -826,6 +826,49 @@ nsRenderingContextXlib::FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord return NS_OK; } +NS_IMETHODIMP +nsRenderingContextXlib :: InvertRect(const nsRect& aRect) +{ + return InvertRect(aRect.x, aRect.y, aRect.width, aRect.height); +} + +NS_IMETHODIMP +nsRenderingContextXlib :: InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight) +{ + if (nsnull == mTMatrix || nsnull == mRenderingSurface) + return NS_ERROR_FAILURE; + + nscoord x,y,w,h; + + x = aX; + y = aY; + w = aWidth; + h = aHeight; + + mTMatrix->TransformCoord(&x,&y,&w,&h); + + // Set XOR drawing mode + ::XSetFunction(mDisplay, + mRenderingSurface->GetGC(), + GXxor); + + ::XFillRectangle(mDisplay, + mRenderingSurface->GetDrawable(), + mRenderingSurface->GetGC(), + x, + y, + w, + h); + + // Back to normal copy drawing mode + // Set XOR drawing mode + ::XSetFunction(mDisplay, + mRenderingSurface->GetGC(), + GXcopy); + + return NS_OK; +} + NS_IMETHODIMP nsRenderingContextXlib::DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints) { diff --git a/gfx/src/xlib/nsRenderingContextXlib.h b/gfx/src/xlib/nsRenderingContextXlib.h index c670323110e3..69e9835a5034 100644 --- a/gfx/src/xlib/nsRenderingContextXlib.h +++ b/gfx/src/xlib/nsRenderingContextXlib.h @@ -101,9 +101,13 @@ class nsRenderingContextXlib : public nsIRenderingContext, NS_IMETHOD DrawRect(const nsRect& aRect); NS_IMETHOD DrawRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD FillRect(const nsRect& aRect); NS_IMETHOD FillRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD InvertRect(const nsRect& aRect); + NS_IMETHOD InvertRect(nscoord aX, nscoord aY, nscoord aWidth, nscoord aHeight); + NS_IMETHOD DrawPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); NS_IMETHOD FillPolygon(const nsPoint aPoints[], PRInt32 aNumPoints); diff --git a/layout/generic/nsTextFrame.cpp b/layout/generic/nsTextFrame.cpp index 15ea7f95f045..6c355f83e08a 100644 --- a/layout/generic/nsTextFrame.cpp +++ b/layout/generic/nsTextFrame.cpp @@ -864,8 +864,20 @@ nsTextFrame::PaintTextDecorations(nsIRenderingContext& aRenderingContext, switch (aDetails->mType) { case SELECTION_NORMAL:{ +// +// XOR InvertRect is currently implemented only in the unix and windows +// rendering contexts. When other platforms implement InvertRect(), they +// can be added here. Eventually this #ifdef should die. +// +// For platforms that dont implement InvertRect(), the selection will be +// a non-filled rectangle. +#if defined(XP_PC) || defined(XP_UNIX) + aRenderingContext.SetColor(NS_RGB(255,255,255)); + aRenderingContext.InvertRect(aX + startOffset, aY, textWidth, rect.height); +#else aRenderingContext.SetColor(NS_RGB(0,0,0)); aRenderingContext.DrawRect(aX + startOffset, aY, textWidth, rect.height); +#endif }break; case SELECTION_SPELLCHECK:{ aTextStyle.mNormalFont->GetUnderline(offset, size); diff --git a/layout/html/base/src/nsTextFrame.cpp b/layout/html/base/src/nsTextFrame.cpp index 15ea7f95f045..6c355f83e08a 100644 --- a/layout/html/base/src/nsTextFrame.cpp +++ b/layout/html/base/src/nsTextFrame.cpp @@ -864,8 +864,20 @@ nsTextFrame::PaintTextDecorations(nsIRenderingContext& aRenderingContext, switch (aDetails->mType) { case SELECTION_NORMAL:{ +// +// XOR InvertRect is currently implemented only in the unix and windows +// rendering contexts. When other platforms implement InvertRect(), they +// can be added here. Eventually this #ifdef should die. +// +// For platforms that dont implement InvertRect(), the selection will be +// a non-filled rectangle. +#if defined(XP_PC) || defined(XP_UNIX) + aRenderingContext.SetColor(NS_RGB(255,255,255)); + aRenderingContext.InvertRect(aX + startOffset, aY, textWidth, rect.height); +#else aRenderingContext.SetColor(NS_RGB(0,0,0)); aRenderingContext.DrawRect(aX + startOffset, aY, textWidth, rect.height); +#endif }break; case SELECTION_SPELLCHECK:{ aTextStyle.mNormalFont->GetUnderline(offset, size);