Bug 759568 - Part 1. Parse background-clip:text; r=dholbert r=heycam

MozReview-Commit-ID: BPuQjWYvAuj
This commit is contained in:
CJKu 2016-04-14 16:28:06 +08:00
Родитель e1b5ef463a
Коммит d2552e50a5
9 изменённых файлов: 87 добавлений и 17 удалений

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

@ -146,6 +146,7 @@ using namespace mozilla::gfx;
#define DISPLAY_CONTENTS_ENABLED_PREF_NAME "layout.css.display-contents.enabled"
#define TEXT_ALIGN_UNSAFE_ENABLED_PREF_NAME "layout.css.text-align-unsafe-value.enabled"
#define FLOAT_LOGICAL_VALUES_ENABLED_PREF_NAME "layout.css.float-logical-values.enabled"
#define BG_CLIP_TEXT_ENABLED_PREF_NAME "layout.css.background-clip-text.enabled"
#ifdef DEBUG
// TODO: remove, see bug 598468.
@ -392,6 +393,39 @@ FloatLogicalValuesEnabledPrefChangeCallback(const char* aPrefName,
isFloatLogicalValuesEnabled ? eCSSKeyword_inline_end : eCSSKeyword_UNKNOWN;
}
// When the pref "layout.css.background-clip-text.enabled" changes, this
// function is invoked to let us update kBackgroundClipKTable, to selectively
// disable or restore the entries for "text" in that table.
static void
BackgroundClipTextEnabledPrefChangeCallback(const char* aPrefName,
void* aClosure)
{
NS_ASSERTION(strcmp(aPrefName, BG_CLIP_TEXT_ENABLED_PREF_NAME) == 0,
"Did you misspell " BG_CLIP_TEXT_ENABLED_PREF_NAME " ?");
static bool sIsBGClipKeywordIndexInitialized;
static int32_t sIndexOfTextInBGClipTable;
bool isBGClipTextEnabled =
Preferences::GetBool(BG_CLIP_TEXT_ENABLED_PREF_NAME, false);
if (!sIsBGClipKeywordIndexInitialized) {
// First run: find the position of "text" in kBackgroundClipKTable.
sIndexOfTextInBGClipTable =
nsCSSProps::FindIndexOfKeyword(eCSSKeyword_text,
nsCSSProps::kBackgroundClipKTable);
sIsBGClipKeywordIndexInitialized = true;
}
// OK -- now, stomp on or restore the "text" entry in kBackgroundClipKTable,
// depending on whether the pref is enabled vs. disabled.
if (sIndexOfTextInBGClipTable >= 0) {
nsCSSProps::kBackgroundClipKTable[sIndexOfTextInBGClipTable].mKeyword =
isBGClipTextEnabled ? eCSSKeyword_text : eCSSKeyword_UNKNOWN;
}
}
template<typename TestType>
static bool
HasMatchingCurrentAnimations(const nsIFrame* aFrame, TestType&& aTest)
@ -7647,6 +7681,10 @@ nsLayoutUtils::Initialize()
FLOAT_LOGICAL_VALUES_ENABLED_PREF_NAME);
FloatLogicalValuesEnabledPrefChangeCallback(FLOAT_LOGICAL_VALUES_ENABLED_PREF_NAME,
nullptr);
Preferences::RegisterCallback(BackgroundClipTextEnabledPrefChangeCallback,
BG_CLIP_TEXT_ENABLED_PREF_NAME);
BackgroundClipTextEnabledPrefChangeCallback(BG_CLIP_TEXT_ENABLED_PREF_NAME,
nullptr);
nsComputedDOMStyle::RegisterPrefChangeCallbacks();
}

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

@ -295,12 +295,16 @@ Declaration::GetImageLayerValue(
if (clip->mValue.GetIntValue() != NS_STYLE_IMAGELAYER_CLIP_BORDER ||
origin->mValue.GetIntValue() != NS_STYLE_IMAGELAYER_ORIGIN_PADDING) {
MOZ_ASSERT(nsCSSProps::kKeywordTableTable[
aTable[nsStyleImageLayers::origin]] ==
nsCSSProps::kImageLayerOriginKTable);
MOZ_ASSERT(nsCSSProps::kKeywordTableTable[
aTable[nsStyleImageLayers::clip]] ==
nsCSSProps::kImageLayerOriginKTable);
#ifdef DEBUG
for (size_t i = 0; nsCSSProps::kImageLayerOriginKTable[i].mValue != -1; i++) {
// For each keyword & value in kOriginKTable, ensure that
// kBackgroundKTable has a matching entry at the same position.
MOZ_ASSERT(nsCSSProps::kImageLayerOriginKTable[i].mKeyword ==
nsCSSProps::kBackgroundClipKTable[i].mKeyword);
MOZ_ASSERT(nsCSSProps::kImageLayerOriginKTable[i].mValue ==
nsCSSProps::kBackgroundClipKTable[i].mValue);
}
#endif
static_assert(NS_STYLE_IMAGELAYER_CLIP_BORDER ==
NS_STYLE_IMAGELAYER_ORIGIN_BORDER &&
NS_STYLE_IMAGELAYER_CLIP_PADDING ==

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

@ -12063,13 +12063,16 @@ CSSParserImpl::ParseImageLayersItem(
// The spec allows a second box value (for background-clip),
// immediately following the first one (for background-origin).
// 'background-clip' and 'background-origin' use the same keyword table
MOZ_ASSERT(nsCSSProps::kKeywordTableTable[
aTable[nsStyleImageLayers::origin]] ==
nsCSSProps::kImageLayerOriginKTable);
MOZ_ASSERT(nsCSSProps::kKeywordTableTable[
aTable[nsStyleImageLayers::clip]] ==
nsCSSProps::kImageLayerOriginKTable);
#ifdef DEBUG
for (size_t i = 0; nsCSSProps::kImageLayerOriginKTable[i].mValue != -1; i++) {
// For each keyword & value in kOriginKTable, ensure that
// kBackgroundKTable has a matching entry at the same position.
MOZ_ASSERT(nsCSSProps::kImageLayerOriginKTable[i].mKeyword ==
nsCSSProps::kBackgroundClipKTable[i].mKeyword);
MOZ_ASSERT(nsCSSProps::kImageLayerOriginKTable[i].mValue ==
nsCSSProps::kBackgroundClipKTable[i].mValue);
}
#endif
static_assert(NS_STYLE_IMAGELAYER_CLIP_BORDER ==
NS_STYLE_IMAGELAYER_ORIGIN_BORDER &&
NS_STYLE_IMAGELAYER_CLIP_PADDING ==

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

@ -522,7 +522,7 @@ CSS_PROP_BACKGROUND(
CSS_PROPERTY_VALUE_LIST_USES_COMMAS,
"",
VARIANT_KEYWORD, // used by list parsing
kImageLayerOriginKTable,
kBackgroundClipKTable,
CSS_PROP_NO_OFFSET,
eStyleAnimType_None)
CSS_PROP_BACKGROUND(

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

@ -890,7 +890,9 @@ const KTableEntry nsCSSProps::kImageLayerAttachmentKTable[] = {
static_assert(NS_STYLE_IMAGELAYER_CLIP_BORDER == NS_STYLE_IMAGELAYER_ORIGIN_BORDER &&
NS_STYLE_IMAGELAYER_CLIP_PADDING == NS_STYLE_IMAGELAYER_ORIGIN_PADDING &&
NS_STYLE_IMAGELAYER_CLIP_CONTENT == NS_STYLE_IMAGELAYER_ORIGIN_CONTENT,
"bg-clip and bg-origin style constants must agree");
"Except background-clip:text, all {background,mask}-clip and "
"{background,mask}-origin style constants must agree");
const KTableEntry nsCSSProps::kImageLayerOriginKTable[] = {
{ eCSSKeyword_border_box, NS_STYLE_IMAGELAYER_ORIGIN_BORDER },
{ eCSSKeyword_padding_box, NS_STYLE_IMAGELAYER_ORIGIN_PADDING },
@ -898,6 +900,21 @@ const KTableEntry nsCSSProps::kImageLayerOriginKTable[] = {
{ eCSSKeyword_UNKNOWN, -1 }
};
KTableEntry nsCSSProps::kBackgroundClipKTable[] = {
{ eCSSKeyword_border_box, NS_STYLE_IMAGELAYER_CLIP_BORDER },
{ eCSSKeyword_padding_box, NS_STYLE_IMAGELAYER_CLIP_PADDING },
{ eCSSKeyword_content_box, NS_STYLE_IMAGELAYER_CLIP_CONTENT },
// The next entry is controlled by the layout.css.background-clip-text.enabled
// pref.
{ eCSSKeyword_text, NS_STYLE_IMAGELAYER_CLIP_TEXT },
{ eCSSKeyword_UNKNOWN, -1 }
};
static_assert(ArrayLength(nsCSSProps::kImageLayerOriginKTable) ==
ArrayLength(nsCSSProps::kBackgroundClipKTable) - 1,
"background-clip has one extra value, which is text, compared"
"to {background,mask}-origin");
// Note: Don't change this table unless you update
// ParseImageLayerPosition!

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

@ -678,6 +678,9 @@ public:
static const KTableEntry kImageLayerSizeKTable[];
static const KTableEntry kImageLayerCompositeKTable[];
static const KTableEntry kImageLayerModeKTable[];
// Not const because we modify its entries when the pref
// "layout.css.background-clip.text" changes:
static KTableEntry kBackgroundClipKTable[];
static const KTableEntry kBlendModeKTable[];
static const KTableEntry kBorderCollapseKTable[];
static const KTableEntry kBorderColorKTable[];

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

@ -1845,7 +1845,7 @@ nsComputedDOMStyle::DoGetBackgroundClip()
return GetBackgroundList(&nsStyleImageLayers::Layer::mClip,
&nsStyleImageLayers::mClipCount,
StyleBackground()->mImage,
nsCSSProps::kImageLayerOriginKTable);
nsCSSProps::kBackgroundClipKTable);
}
already_AddRefed<CSSValue>

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

@ -267,10 +267,12 @@ enum class FillMode : uint32_t;
#define NS_STYLE_IMAGELAYER_ATTACHMENT_LOCAL 2
// See nsStyleImageLayers
// Code depends on these constants having the same values as BG_ORIGIN_*
// Code depends on these constants having the same values as IMAGELAYER_ORIGIN_*
#define NS_STYLE_IMAGELAYER_CLIP_BORDER 0
#define NS_STYLE_IMAGELAYER_CLIP_PADDING 1
#define NS_STYLE_IMAGELAYER_CLIP_CONTENT 2
// One extra constant which does not exist in IMAGELAYER_ORIGIN_*
#define NS_STYLE_IMAGELAYER_CLIP_TEXT 3
// A magic value that we use for our "pretend that background-clip is
// 'padding' when we have a solid border" optimization. This isn't

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

@ -2421,6 +2421,9 @@ pref("layout.css.scope-pseudo.enabled", true);
// Is support for background-blend-mode enabled?
pref("layout.css.background-blend-mode.enabled", true);
// Is support for background-clip:text enabled? (bug 1263516)
pref("layout.css.background-clip-text.enabled", false);
// Is support for CSS vertical text enabled?
pref("layout.css.vertical-text.enabled", true);