diff options
Diffstat (limited to 'layout/painting/DisplayItemClipChain.h')
-rw-r--r-- | layout/painting/DisplayItemClipChain.h | 117 |
1 files changed, 117 insertions, 0 deletions
diff --git a/layout/painting/DisplayItemClipChain.h b/layout/painting/DisplayItemClipChain.h new file mode 100644 index 0000000000..32779e09c0 --- /dev/null +++ b/layout/painting/DisplayItemClipChain.h @@ -0,0 +1,117 @@ +/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ +/* vim: set ts=8 sts=2 et sw=2 tw=80: */ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ + +#ifndef DISPLAYITEMCLIPCHAIN_H_ +#define DISPLAYITEMCLIPCHAIN_H_ + +#include "mozilla/Assertions.h" +#include "DisplayItemClip.h" +#include "nsString.h" + +class nsIScrollableFrame; + +namespace mozilla { + +struct ActiveScrolledRoot; + +/** + * A DisplayItemClipChain is a linked list of DisplayItemClips where each clip + * is associated with an active scrolled root that describes what the clip + * moves with. + * We use a chain instead of just one intersected clip due to async scrolling: + * A clip that moves along with a display item can be fused to the item's + * contents when drawing the layer contents, but all other clips in the chain + * need to be kept separate so that they can be applied at composition time, + * after any async scroll offsets have been applied. + * The clip chain is created during display list construction by the builder's + * DisplayListClipState. + * The clip chain order is determined by the active scrolled root order. + * For every DisplayItemClipChain object |clipChain|, the following holds: + * !clipChain->mParent || + * ActiveScrolledRoot::IsAncestor(clipChain->mParent->mASR, clipChain->mASR). + * The clip chain can skip over active scrolled roots. That just means that + * there is no clip that moves with the skipped ASR in this chain. + */ +struct DisplayItemClipChain { + /** + * Get the display item clip in this chain that moves with aASR, or nullptr + * if no such clip exists. aClipChain can be null. + */ + static const DisplayItemClip* ClipForASR( + const DisplayItemClipChain* aClipChain, const ActiveScrolledRoot* aASR); + + static bool Equal(const DisplayItemClipChain* aClip1, + const DisplayItemClipChain* aClip2); + /** + * Hash function that returns the same value for any two clips A and B + * where Equal(A, B) is true. + */ + static uint32_t Hash(const DisplayItemClipChain* aClip); + + static nsCString ToString(const DisplayItemClipChain* aClipChain); + + bool HasRoundedCorners() const; + + void AddRef() { mRefCount++; } + void Release() { + MOZ_ASSERT(mRefCount > 0); + mRefCount--; + } + + DisplayItemClipChain(const DisplayItemClip& aClip, + const ActiveScrolledRoot* aASR, + const DisplayItemClipChain* aParent, + DisplayItemClipChain* aNextClipChainToDestroy) + : mClip(aClip), + mASR(aASR), + mParent(aParent), + mNextClipChainToDestroy(aNextClipChainToDestroy) +#ifdef DEBUG + , + mOnStack(true) +#endif + { + } + + DisplayItemClipChain() + : mASR(nullptr), + mNextClipChainToDestroy(nullptr) +#ifdef DEBUG + , + mOnStack(true) +#endif + { + } + + DisplayItemClip mClip; + const ActiveScrolledRoot* mASR; + RefPtr<const DisplayItemClipChain> mParent; + uint32_t mRefCount = 0; + DisplayItemClipChain* mNextClipChainToDestroy; +#ifdef DEBUG + bool mOnStack; +#endif +}; + +struct DisplayItemClipChainHasher { + typedef const DisplayItemClipChain* Key; + + std::size_t operator()(const Key& aKey) const { + return DisplayItemClipChain::Hash(aKey); + } +}; + +struct DisplayItemClipChainEqualer { + typedef const DisplayItemClipChain* Key; + + bool operator()(const Key& lhs, const Key& rhs) const { + return DisplayItemClipChain::Equal(lhs, rhs); + } +}; + +} // namespace mozilla + +#endif /* DISPLAYITEMCLIPCHAIN_H_ */ |