Closed Bug 6551 Opened 26 years ago Closed 26 years ago

Need nsIViewManager methods that batch UpdateView requests.

Categories

(Core :: Web Painting, defect, P3)

defect

Tracking

()

VERIFIED FIXED

People

(Reporter: kinmoz, Assigned: kinmoz)

Details

The nsIViewManager needs some sort of mechanism that allows the editor to tell it that it wants damage rects and update counts to be accumulated, but doesn't want any screen updates. The editor is currently using a call to nsIViewManager::DisableRefresh() to stop screen updates. Calling nsIViewManager::EnableRefresh() does not update the damaged areas on the screen, so we are forced to redraw the entire screen to see our modifications by doing something like: viewmgr->UpdateView(view,nsnull,NS_VMREFRESH_IMMEDIATE); I looked into why we have to redraw the entire screen, and it seems that DisableRefresh() sets an internal member variable that forces calls to nsIViewManager::UpdateView(), from layout, to return immediately without doing anything. This means that the nsViewManager's internal update count stays at zero, and the damage rects stop being remembered. When EnableRefresh() is called, it makes a call to nsIViewManager::Composite(), which should trigger repainting, but it doesn't, because the view manager's internal update count is zero.
Status: NEW → ASSIGNED
Target Milestone: M8
Assignee: beard → kin
Status: ASSIGNED → NEW
Target Milestone: M8 → M7
Status: NEW → ASSIGNED
Accepting bug.
Here's the fix. I'll check it in after I get feedback from others in the editor group, and when I get approval from beard@netscape.com. --== Kin ==-- Index: editor/base/nsEditor.cpp =================================================================== RCS file: /cvsroot/mozilla/editor/base/nsEditor.cpp,v retrieving revision 1.91 diff -c -r1.91 nsEditor.cpp *** nsEditor.cpp 1999/05/20 01:48:12 1.91 --- nsEditor.cpp 1999/05/21 16:57:11 *************** *** 67,73 **** #include "JoinElementTxn.h" #include "nsIStringStream.h" ! #define HACK_FORCE_REDRAW 1 #ifdef HACK_FORCE_REDRAW --- 67,73 ---- #include "JoinElementTxn.h" #include "nsIStringStream.h" ! // #define HACK_FORCE_REDRAW 1 #ifdef HACK_FORCE_REDRAW *************** *** 759,765 **** --- 759,771 ---- if (nsnull!=mViewManager) { if (0==mUpdateCount) + { + #ifdef HACK_FORCE_REDRAW mViewManager->DisableRefresh(); + #else + mViewManager->BeginUpdateViewBatch(); + #endif + } mUpdateCount++; } *************** *** 786,793 **** --- 792,803 ---- mUpdateCount--; if (0==mUpdateCount) { + #ifdef HACK_FORCE_REDRAW mViewManager->EnableRefresh(); HACKForceRedraw(); + #else + mViewManager->EndUpdateViewBatch(); + #endif } } Index: view/public/nsIViewManager.h =================================================================== RCS file: /cvsroot/mozilla/view/public/nsIViewManager.h,v retrieving revision 3.26 diff -c -r3.26 nsIViewManager.h *** nsIViewManager.h 1999/02/16 19:57:43 3.26 --- nsIViewManager.h 1999/05/21 16:57:44 *************** *** 358,363 **** --- 358,379 ---- NS_IMETHOD EnableRefresh(void) = 0; /** + * prevents the view manager from refreshing. allows UpdateView() + * to notify widgets of damaged regions that should be repainted + * when the batch is ended. + * @return error status + */ + NS_IMETHOD BeginUpdateViewBatch(void) = 0; + + /** + * allow the view manager to refresh any damaged areas accumulated + * after the BeginUpdateViewBatch() call. this may cause a + * synchronous paint to occur inside the call. + * @return error status + */ + NS_IMETHOD EndUpdateViewBatch(void) = 0; + + /** * set the view that is is considered to be the root scrollable * view for the document. * @param aScrollable root scrollable view Index: view/src/nsViewManager.cpp =================================================================== RCS file: /cvsroot/mozilla/view/src/nsViewManager.cpp,v retrieving revision 3.95 diff -c -r3.95 nsViewManager.cpp *** nsViewManager.cpp 1999/05/19 23:23:47 3.95 --- nsViewManager.cpp 1999/05/21 16:58:14 *************** *** 1478,1484 **** NS_IMETHODIMP nsViewManager :: UpdateView(nsIView *aView, const nsRect &aRect, PRUint32 aUpdateFlags) { NS_PRECONDITION(nsnull != aView, "null view"); ! if (!mRefreshEnabled) { return NS_OK; } --- 1478,1484 ---- NS_IMETHODIMP nsViewManager :: UpdateView(nsIView *aView, const nsRect &aRect, PRUint32 aUpdateFlags) { NS_PRECONDITION(nsnull != aView, "null view"); ! if (!mRefreshEnabled && 0 == mUpdateBatchCnt) { return NS_OK; } *************** *** 1519,1525 **** if (nsnull != widgetView) { ! if (0 == mUpdateCnt) RestartTimer(); mUpdateCnt++; --- 1519,1525 ---- if (nsnull != widgetView) { ! if (0 == mUpdateCnt && 0 == mUpdateBatchCnt) RestartTimer(); mUpdateCnt++; *************** *** 1548,1566 **** // See if we should do an immediate refresh or wait ! if (aUpdateFlags & NS_VMREFRESH_IMMEDIATE) { ! Composite(); ! } ! else if ((mTrueFrameRate > 0) && !(aUpdateFlags & NS_VMREFRESH_NO_SYNC)) ! { ! // or if a sync paint is allowed and it's time for the compositor to ! // do a refresh ! PRInt32 deltams = PR_IntervalToMilliseconds(PR_IntervalNow() - mLastRefresh); ! if (deltams > (1000 / (PRInt32)mTrueFrameRate)) ! Composite(); } } --- 1548,1569 ---- // See if we should do an immediate refresh or wait ! if (0 == mUpdateBatchCnt) { ! if (aUpdateFlags & NS_VMREFRESH_IMMEDIATE) ! { ! Composite(); ! } ! else if ((mTrueFrameRate > 0) && !(aUpdateFlags & NS_VMREFRESH_NO_SYNC)) ! { ! // or if a sync paint is allowed and it's time for the compositor to ! // do a refresh ! PRInt32 deltams = PR_IntervalToMilliseconds(PR_IntervalNow() - mLastRefresh); ! if (deltams > (1000 / (PRInt32)mTrueFrameRate)) ! Composite(); ! } } } *************** *** 2365,2370 **** --- 2368,2406 ---- } return NS_OK; + } + + NS_IMETHODIMP nsViewManager :: BeginUpdateViewBatch(void) + { + nsresult result = NS_OK; + + if (mUpdateBatchCnt == 0) + result = DisableRefresh(); + + if (NS_SUCCEEDED(result)) + ++mUpdateBatchCnt; + + return result; + } + + NS_IMETHODIMP nsViewManager :: EndUpdateViewBatch(void) + { + nsresult result = NS_OK; + + --mUpdateBatchCnt; + + NS_ASSERTION(mUpdateBatchCnt >= 0, "Invalid batch count!"); + + if (mUpdateBatchCnt < 0) + { + mUpdateBatchCnt = 0; + return NS_ERROR_FAILURE; + } + + if (mUpdateBatchCnt == 0) + result = EnableRefresh(); + + return result; } NS_IMETHODIMP nsViewManager :: SetRootScrollableView(nsIScrollableView *aScrollable) Index: view/src/nsViewManager.h =================================================================== RCS file: /cvsroot/mozilla/view/src/nsViewManager.h,v retrieving revision 3.32 diff -c -r3.32 nsViewManager.h *** nsViewManager.h 1999/03/09 22:10:31 3.32 --- nsViewManager.h 1999/05/21 16:58:20 *************** *** 108,113 **** --- 108,116 ---- NS_IMETHOD DisableRefresh(void); NS_IMETHOD EnableRefresh(void); + NS_IMETHOD BeginUpdateViewBatch(void); + NS_IMETHOD EndUpdateViewBatch(void); + NS_IMETHOD SetRootScrollableView(nsIScrollableView *aScrollable); NS_IMETHOD GetRootScrollableView(nsIScrollableView **aScrollable); *************** *** 155,160 **** --- 158,164 ---- nsIView *mMouseGrabber; nsIView *mKeyGrabber; PRInt32 mUpdateCnt; + PRInt32 mUpdateBatchCnt; nsVoidArray *mDisplayList; nsIScrollableView *mRootScrollable;
Status: ASSIGNED → RESOLVED
Closed: 26 years ago
Resolution: --- → FIXED
I checked this in yesterday. mozilla/view/public/nsIViewManager.h mozilla/view/public/nsViewManager.cpp mozilla/view/public/nsViewManager.h mozilla/editor/base/nsEditor.cpp
Status: RESOLVED → VERIFIED
code level fix, marking verified per developer input
Component: Layout: View Rendering → Layout: Web Painting
You need to log in before you can comment on or make changes to this bug.