]> git.saurik.com Git - wxWidgets.git/commitdiff
overlay implementation
authorStefan Csomor <csomor@advancedconcepts.ch>
Tue, 10 Oct 2006 10:39:29 +0000 (10:39 +0000)
committerStefan Csomor <csomor@advancedconcepts.ch>
Tue, 10 Oct 2006 10:39:29 +0000 (10:39 +0000)
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@41877 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

src/common/dcbase.cpp
src/generic/caret.cpp

index 994dfcee37a437e5d23fdfdeb19e3b05181f00fa..897fa15dcc77f92e4ec542c90ad4c0afbb9f48b8 100644 (file)
@@ -1145,4 +1145,296 @@ void wxDCBase::CalculateEllipticPoints( wxList* points,
     } // not iUseAngles
 } // CalculateEllipticPoints
 
     } // not iUseAngles
 } // CalculateEllipticPoints
 
+//
+// temporary home for wxOverlay
+//
+
+#if defined(wxMAC_USE_CORE_GRAPHICS) && wxMAC_USE_CORE_GRAPHICS
+
+#include "wx/mac/private.h"
+
+class wxOverlayImpl
+{
+public:
+    wxOverlayImpl() ;
+    ~wxOverlayImpl() ;
+    
+    
+    // clears the overlay without restoring the former state
+    // to be done eg when the window content has been changed and repainted
+    void Reset();
+    
+    // returns true if it has been setup
+    bool IsOk();
+    
+    void Init( wxWindowDC* dc, int x , int y , int width , int height );
+    
+    void BeginDrawing( wxWindowDC* dc);
+    
+    void EndDrawing( wxWindowDC* dc);
+    
+    void Clear( wxWindowDC* dc);
+
+private:
+    WindowRef m_overlayWindow ;
+    CGContextRef m_overlayContext ;
+    // we store the window in case we would have to issue a Refresh()
+    wxWindow* m_window ;
+} ;
+
+wxOverlayImpl::wxOverlayImpl()
+{
+    m_window = NULL ;
+    m_overlayContext = NULL ;
+    m_overlayWindow = NULL ;
+}
+
+wxOverlayImpl::~wxOverlayImpl()
+{
+    Reset();
+}
+
+bool wxOverlayImpl::IsOk() 
+{
+    return m_overlayContext != NULL ;
+}
+
+void wxOverlayImpl::Init( wxWindowDC* dc, int x , int y , int width , int height )
+{
+    wxASSERT_MSG( !IsOk() , _("You cannot Init an overlay twice") );
+
+    m_window = dc->GetWindow(); 
+    
+    wxPoint origin(0,0);
+    origin = m_window->ClientToScreen( origin );
+    Rect bounds = { origin.y, origin.x, origin.y+y+height, origin.x+x+width } ;
+    
+    UInt32 flags = kWindowHideOnSuspendAttribute | kWindowIgnoreClicksAttribute;
+    OSStatus err = CreateNewWindow( kOverlayWindowClass, flags, &bounds, &m_overlayWindow );
+    wxASSERT_MSG(  err == noErr , _("Couldn't create the overlay window") );
+    ShowWindow(m_overlayWindow);
+    err = QDBeginCGContext(GetWindowPort(m_overlayWindow), &m_overlayContext);
+    CGContextTranslateCTM( m_overlayContext, 0, bounds.bottom - bounds.top );
+    CGContextScaleCTM( m_overlayContext, 1, -1 );
+    wxASSERT_MSG(  err == noErr , _("Couldn't init the context on the overlay window") );
+}
+
+void wxOverlayImpl::BeginDrawing( wxWindowDC* dc)
+{
+    delete dc->m_graphicContext ;
+    dc->m_graphicContext = new wxMacCGContext( m_overlayContext );
+    dc->m_macLocalOrigin.x = 0 ;
+    dc->m_macLocalOrigin.y = 0 ;
+}
+
+void wxOverlayImpl::EndDrawing( wxWindowDC* dc)
+{
+}
+
+void wxOverlayImpl::Clear(wxWindowDC* dc) 
+{
+    wxASSERT_MSG( IsOk() , _("You cannot Clear an overlay that is not inited") );
+    delete dc->m_graphicContext ;
+    dc->m_graphicContext = NULL ;
+
+    Reset();
+}
+
+void wxOverlayImpl::Reset()
+{
+    if ( m_overlayContext )
+    {
+        OSStatus err = QDEndCGContext(GetWindowPort(m_overlayWindow), &m_overlayContext);
+        wxASSERT_MSG(  err == noErr , _("Couldn't end the context on the overlay window") );
+
+        m_overlayContext = NULL ;
+    }
+    
+    // todo : don't dispose, only hide and reposition on next run
+    if (m_overlayWindow)
+    {
+        DisposeWindow(m_overlayWindow);
+        m_overlayWindow = NULL ;
+    }
+}
+
+//
+//
+//
+
+#else
+
+class wxOverlayImpl
+{
+public:
+    wxOverlayImpl() ;
+    ~wxOverlayImpl() ;
+    
+    
+    // clears the overlay without restoring the former state
+    // to be done eg when the window content has been changed and repainted
+    void Reset();
+    
+    // returns true if it has been setup
+    bool IsOk();
+    
+    void Init( wxWindowDC* dc, int x , int y , int width , int height );
+    
+    void BeginDrawing( wxWindowDC* dc);
+    
+    void EndDrawing( wxWindowDC* dc);
+    
+    void Clear( wxWindowDC* dc);
+
+private:
+    wxBitmap m_bmpSaved ;
+    int m_x ;
+    int m_y ;
+    int m_width ;
+    int m_height ;
+    wxWindow* m_window ;
+} ;
+
+wxOverlayImpl::wxOverlayImpl()
+{
+    m_window = NULL ;
+     m_x = m_y = m_width = m_height = 0 ;
+}
+
+wxOverlayImpl::~wxOverlayImpl()
+{
+}
+
+bool wxOverlayImpl::IsOk() 
+{
+    return m_bmpSaved.Ok() ;
+}
+
+void wxOverlayImpl::Init( wxWindowDC* dc, int x , int y , int width , int height )
+{
+    m_window = dc->GetWindow();
+    
+    wxMemoryDC dcMem ;
+    m_bmpSaved.Create( width, height );
+    dcMem.SelectObject( m_bmpSaved );
+    m_x = x ;
+    m_y = y ;
+    m_width = width ;
+    m_height = height ;
+#if defined(__WXGTK__) && !defined(__WX_DC_BLIT_FIXED__)
+    wxPoint pt = dcWin.GetDeviceOrigin();
+    x += pt.x;
+    y += pt.y;
+#endif // broken wxGTK wxDC::Blit
+    dcMem.Blit(0, 0, m_width, m_height,
+        dc, x, y);
+    dcMem.SelectObject( wxNullBitmap );
+}
+
+void wxOverlayImpl::Clear(wxWindowDC* dc) 
+{
+    wxMemoryDC dcMem ;
+    dcMem.SelectObject( m_bmpSaved );
+    dc->Blit( m_x, m_y, m_width, m_height , &dcMem , 0 , 0 );
+    dcMem.SelectObject( wxNullBitmap );
+}
+
+void wxOverlayImpl::Reset()
+{
+    m_bmpSaved = wxBitmap();
+}
+
+void wxOverlayImpl::BeginDrawing(wxWindowDC*  WXUNUSED(dc))
+{
+}
+
+void wxOverlayImpl::EndDrawing(wxWindowDC* WXUNUSED(dc))
+{
+}
+
+#endif
+
+// common code
+
+wxOverlay::wxOverlay()
+{
+    m_impl = new wxOverlayImpl();
+    m_inDrawing = false;
+}
+
+wxOverlay::~wxOverlay()
+{
+    wxDELETE( m_impl );
+}
+
+bool wxOverlay::IsOk()
+{
+    return m_impl->IsOk();
+}
+
+void wxOverlay::Init( wxWindowDC* dc, int x , int y , int width , int height )
+{
+    m_impl->Init(dc, x, y, width, height);
+}
+
+void wxOverlay::BeginDrawing( wxWindowDC* dc)
+{
+    m_impl->BeginDrawing(dc);
+    m_inDrawing = true ;
+}
+
+void wxOverlay::EndDrawing( wxWindowDC* dc)
+{
+    m_impl->EndDrawing(dc);
+    m_inDrawing = false ;
+}
+
+void wxOverlay::Clear( wxWindowDC* dc)
+{
+    m_impl->Clear(dc);
+}
+
+void wxOverlay::Reset()
+{
+    wxASSERT_MSG(m_inDrawing==false,wxT("cannot reset overlay during drawing"));
+    m_impl->Reset();
+}
+
+// dc connector
+
+wxDCOverlay::wxDCOverlay(wxOverlay &overlay, wxWindowDC *dc, int x , int y , int width , int height) :
+    m_overlay(overlay)
+{
+    Init(dc, x, y, width, height);
+}
+
+wxDCOverlay::wxDCOverlay(wxOverlay &overlay, wxWindowDC *dc) :
+    m_overlay(overlay)
+{
+    int width;
+    int height;
+    dc->GetSize(&width,&height);
+    Init(dc, 0, 0, width, height);
+}
+
+wxDCOverlay::~wxDCOverlay()
+{
+    m_overlay.EndDrawing(m_dc);
+}
+
+void wxDCOverlay::Init(wxWindowDC *dc, int x , int y , int width , int height )
+{
+    m_dc = dc ;
+    if ( !m_overlay.IsOk() )
+    {
+        m_overlay.Init(dc,x,y,width,height);
+    }
+    m_overlay.BeginDrawing(dc);
+}
+
+void wxDCOverlay::Clear() 
+{
+    m_overlay.Clear(m_dc);
+}
+
 #endif
 #endif
index b767a00c1ed53f1100c772adcd0d60c22a5e3945..54cab63e4b30ee252e95d97917b3851c92afd0cc 100644 (file)
@@ -88,10 +88,11 @@ void wxCaret::InitGeneric()
 {
     m_hasFocus = true;
     m_blinkedOut = true;
 {
     m_hasFocus = true;
     m_blinkedOut = true;
-
+#if wxUSE_OVERLAY == 0
     m_xOld =
     m_yOld = -1;
     m_bmpUnderCaret.Create(m_width, m_height);
     m_xOld =
     m_yOld = -1;
     m_bmpUnderCaret.Create(m_width, m_height);
+#endif
 }
 
 wxCaret::~wxCaret()
 }
 
 wxCaret::~wxCaret()
@@ -154,8 +155,10 @@ void wxCaret::DoSize()
         m_countVisible = 0;
         DoHide();
     }
         m_countVisible = 0;
         DoHide();
     }
+#if wxUSE_OVERLAY == 0
     // Change bitmap size
     m_bmpUnderCaret = wxBitmap(m_width, m_height);
     // Change bitmap size
     m_bmpUnderCaret = wxBitmap(m_width, m_height);
+#endif
     if (countVisible > 0)
     {
         m_countVisible = countVisible;
     if (countVisible > 0)
     {
         m_countVisible = countVisible;
@@ -208,6 +211,18 @@ void wxCaret::Blink()
 void wxCaret::Refresh()
 {
     wxClientDC dcWin(GetWindow());
 void wxCaret::Refresh()
 {
     wxClientDC dcWin(GetWindow());
+// this is the new code, switch to 0 if this gives problems
+#if wxUSE_OVERLAY
+    wxDCOverlay dcOverlay( m_overlay, &dcWin, m_x, m_y, m_width , m_height );
+    if ( m_blinkedOut )
+    {
+        dcOverlay.Clear();
+    }
+    else
+    {
+        DoDraw( &dcWin );
+    }
+#else
     wxMemoryDC dcMem;
     dcMem.SelectObject(m_bmpUnderCaret);
     if ( m_blinkedOut )
     wxMemoryDC dcMem;
     dcMem.SelectObject(m_bmpUnderCaret);
     if ( m_blinkedOut )
@@ -243,6 +258,7 @@ void wxCaret::Refresh()
         // and draw the caret there
         DoDraw(&dcWin);
     }
         // and draw the caret there
         DoDraw(&dcWin);
     }
+#endif
 }
 
 void wxCaret::DoDraw(wxDC *dc)
 }
 
 void wxCaret::DoDraw(wxDC *dc)