bug 625248 - During each paint, build a list (stored as a FrameProperty of the root nsIFrame) of all the PresShells that are visible during this paint, so that we can increment their paint count correctly during an empty transaction; r=roc a=blocking-final+

--HG--
extra : rebase_source : 2524d2e258a6a6cc13a7d8df2c874752e415c1ba
This commit is contained in:
Kevin Gadd 2011-01-27 13:53:10 -08:00
Родитель 95c05a5e7e
Коммит d294ee3873
4 изменённых файлов: 92 добавлений и 7 удалений

Просмотреть файл

@ -266,6 +266,8 @@ nsDisplayListBuilder::EnterPresShell(nsIFrame* aReferenceFrame,
state->mPresShell->UpdateCanvasBackground();
if (mIsPaintingToWindow) {
mReferenceFrame->AddPaintedPresShell(state->mPresShell);
state->mPresShell->IncrementPaintCount();
}

Просмотреть файл

@ -6144,9 +6144,14 @@ PresShell::Paint(nsIView* aDisplayRoot,
if (frame) {
if (!(frame->GetStateBits() & NS_FRAME_UPDATE_LAYER_TREE)) {
if (layerManager->EndEmptyTransaction())
if (layerManager->EndEmptyTransaction()) {
frame->UpdatePaintCountForPaintedPresShells();
return NS_OK;
}
}
frame->ClearPresShellsFromLastPaint();
frame->RemoveStateBits(NS_FRAME_UPDATE_LAYER_TREE);
}

Просмотреть файл

@ -6,8 +6,11 @@
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
</head>
<body onload="doFlicker()">
<p id="display"></p>
<body onload="doBackgroundFlicker()">
<p id="display">
<embed type="application/x-test" width="100" height="100" id="p"
drawmode="solid" color="FF00FF00"></embed>
</p>
<div id="content" style="display: none">
</div>
@ -20,17 +23,36 @@ var startPaintCount = window.mozPaintCount;
ok(true, "Got to initial paint count: " + startPaintCount);
var color = 0;
function doFlicker() {
ok(true, "Iteration " + color + ", paint count: " + window.mozPaintCount);
function doPluginFlicker() {
ok(true, "Plugin color iteration " + color + ", paint count: " + window.mozPaintCount);
if (window.mozPaintCount - startPaintCount > 20) {
ok(true, "Got enough paints");
ok(true, "Got enough paints from plugin color changes");
SimpleTest.finish();
return;
}
color = (color + 1) % 256;
var str = color.toString(16);
if (str.length < 2) {
str = "0" + str;
}
str = "FF" + str + str + str;
document.getElementById("p").setColor(str);
setTimeout(doPluginFlicker, 0);
}
function doBackgroundFlicker() {
ok(true, "Background color iteration " + color + ", paint count: " + window.mozPaintCount);
if (window.mozPaintCount - startPaintCount > 20) {
ok(true, "Got enough paints from background color changes");
startPaintCount = window.mozPaintCount;
doPluginFlicker();
return;
}
color = (color + 1) % 256;
document.body.style.backgroundColor = "rgb(" + color + "," + color + "," + color + ")";
setTimeout(doFlicker, 0);
setTimeout(doBackgroundFlicker, 0);
}
</script>

Просмотреть файл

@ -2649,6 +2649,37 @@ NS_PTR_TO_INT32(frame->Properties().Get(nsIFrame::EmbeddingLevelProperty()))
*/
virtual void PullOverflowsFromPrevInFlow() {}
/**
* Clear the list of child PresShells generated during the last paint
* so that we can begin generating a new one.
*/
void ClearPresShellsFromLastPaint() {
PaintedPresShellList()->Clear();
}
/**
* Flag a child PresShell as painted so that it will get its paint count
* incremented during empty transactions.
*/
void AddPaintedPresShell(nsIPresShell* shell) {
PaintedPresShellList()->AppendElement(do_GetWeakReference(shell));
}
/**
* Increment the paint count of all child PresShells that were painted during
* the last repaint.
*/
void UpdatePaintCountForPaintedPresShells() {
nsTArray<nsWeakPtr> * list = PaintedPresShellList();
for (int i = 0, l = list->Length(); i < l; i++) {
nsCOMPtr<nsIPresShell> shell = do_QueryReferent(list->ElementAt(i));
if (shell) {
shell->IncrementPaintCount();
}
}
}
protected:
// Members
nsRect mRect;
@ -2658,6 +2689,31 @@ protected:
private:
nsIFrame* mNextSibling; // doubly-linked list of frames
nsIFrame* mPrevSibling; // Do not touch outside SetNextSibling!
static void DestroyPaintedPresShellList(void* propertyValue) {
nsTArray<nsWeakPtr>* list = static_cast<nsTArray<nsWeakPtr>*>(propertyValue);
list->Clear();
delete list;
}
// Stores weak references to all the PresShells that were painted during
// the last paint event so that we can increment their paint count during
// empty transactions
NS_DECLARE_FRAME_PROPERTY(PaintedPresShellsProperty, DestroyPaintedPresShellList)
nsTArray<nsWeakPtr>* PaintedPresShellList() {
nsTArray<nsWeakPtr>* list = static_cast<nsTArray<nsWeakPtr>*>(
Properties().Get(PaintedPresShellsProperty())
);
if (!list) {
list = new nsTArray<nsWeakPtr>();
Properties().Set(PaintedPresShellsProperty(), list);
}
return list;
}
protected:
nsFrameState mState;