Bug 1408308: Integrate Servo SourceSizeList in ResponsiveImageSelector. r=Manishearth
This needs to dumb down the parsing in order to match what we do in Gecko and pass more tests. The remaining tests are just because of calc() in media queries and "or" media expressions. MozReview-Commit-ID: CXGdYVbojBL
This commit is contained in:
@@ -5,6 +5,7 @@
|
|||||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||||
|
|
||||||
#include "mozilla/dom/ResponsiveImageSelector.h"
|
#include "mozilla/dom/ResponsiveImageSelector.h"
|
||||||
|
#include "mozilla/ServoStyleSet.h"
|
||||||
#include "nsIURI.h"
|
#include "nsIURI.h"
|
||||||
#include "nsIDocument.h"
|
#include "nsIDocument.h"
|
||||||
#include "nsContentUtils.h"
|
#include "nsContentUtils.h"
|
||||||
@@ -241,11 +242,18 @@ bool
|
|||||||
ResponsiveImageSelector::SetSizesFromDescriptor(const nsAString & aSizes)
|
ResponsiveImageSelector::SetSizesFromDescriptor(const nsAString & aSizes)
|
||||||
{
|
{
|
||||||
ClearSelectedCandidate();
|
ClearSelectedCandidate();
|
||||||
mSizeQueries.Clear();
|
|
||||||
mSizeValues.Clear();
|
if (Document()->IsStyledByServo()) {
|
||||||
|
NS_ConvertUTF16toUTF8 sizes(aSizes);
|
||||||
|
mServoSourceSizeList.reset(Servo_SourceSizeList_Parse(&sizes));
|
||||||
|
return !!mServoSourceSizeList;
|
||||||
|
}
|
||||||
|
|
||||||
nsCSSParser cssParser;
|
nsCSSParser cssParser;
|
||||||
|
|
||||||
|
mSizeQueries.Clear();
|
||||||
|
mSizeValues.Clear();
|
||||||
|
|
||||||
return cssParser.ParseSourceSizeList(aSizes, nullptr, 0,
|
return cssParser.ParseSourceSizeList(aSizes, nullptr, 0,
|
||||||
mSizeQueries, mSizeValues);
|
mSizeQueries, mSizeValues);
|
||||||
}
|
}
|
||||||
@@ -364,11 +372,11 @@ ResponsiveImageSelector::SelectImage(bool aReselect)
|
|||||||
}
|
}
|
||||||
|
|
||||||
nsIDocument* doc = Document();
|
nsIDocument* doc = Document();
|
||||||
nsIPresShell *shell = doc ? doc->GetShell() : nullptr;
|
nsIPresShell* shell = doc->GetShell();
|
||||||
nsPresContext* pctx = shell ? shell->GetPresContext() : nullptr;
|
nsPresContext* pctx = shell ? shell->GetPresContext() : nullptr;
|
||||||
nsCOMPtr<nsIURI> baseURI = mOwnerNode ? mOwnerNode->GetBaseURI() : nullptr;
|
nsCOMPtr<nsIURI> baseURI = mOwnerNode->GetBaseURI();
|
||||||
|
|
||||||
if (!pctx || !doc || !baseURI) {
|
if (!pctx || !baseURI) {
|
||||||
return oldBest != -1;
|
return oldBest != -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -388,7 +396,7 @@ ResponsiveImageSelector::SelectImage(bool aReselect)
|
|||||||
double computedWidth = -1;
|
double computedWidth = -1;
|
||||||
for (int i = 0; i < numCandidates; i++) {
|
for (int i = 0; i < numCandidates; i++) {
|
||||||
if (mCandidates[i].IsComputedFromWidth()) {
|
if (mCandidates[i].IsComputedFromWidth()) {
|
||||||
DebugOnly<bool> computeResult = \
|
DebugOnly<bool> computeResult =
|
||||||
ComputeFinalWidthForCurrentViewport(&computedWidth);
|
ComputeFinalWidthForCurrentViewport(&computedWidth);
|
||||||
MOZ_ASSERT(computeResult,
|
MOZ_ASSERT(computeResult,
|
||||||
"Computed candidates not allowed without sizes data");
|
"Computed candidates not allowed without sizes data");
|
||||||
@@ -439,15 +447,19 @@ ResponsiveImageSelector::GetSelectedCandidateIndex()
|
|||||||
bool
|
bool
|
||||||
ResponsiveImageSelector::ComputeFinalWidthForCurrentViewport(double *aWidth)
|
ResponsiveImageSelector::ComputeFinalWidthForCurrentViewport(double *aWidth)
|
||||||
{
|
{
|
||||||
unsigned int numSizes = mSizeQueries.Length();
|
|
||||||
nsIDocument* doc = Document();
|
nsIDocument* doc = Document();
|
||||||
nsIPresShell *presShell = doc ? doc->GetShell() : nullptr;
|
nsIPresShell* presShell = doc->GetShell();
|
||||||
nsPresContext* pctx = presShell ? presShell->GetPresContext() : nullptr;
|
nsPresContext* pctx = presShell ? presShell->GetPresContext() : nullptr;
|
||||||
|
|
||||||
if (!pctx) {
|
if (!pctx) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
nscoord effectiveWidth;
|
||||||
|
if (doc->IsStyledByServo()) {
|
||||||
|
effectiveWidth = presShell->StyleSet()->AsServo()->EvaluateSourceSizeList(
|
||||||
|
mServoSourceSizeList.get());
|
||||||
|
} else {
|
||||||
|
unsigned int numSizes = mSizeQueries.Length();
|
||||||
MOZ_ASSERT(numSizes == mSizeValues.Length(),
|
MOZ_ASSERT(numSizes == mSizeValues.Length(),
|
||||||
"mSizeValues length differs from mSizeQueries");
|
"mSizeValues length differs from mSizeQueries");
|
||||||
|
|
||||||
@@ -458,7 +470,6 @@ ResponsiveImageSelector::ComputeFinalWidthForCurrentViewport(double *aWidth)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
nscoord effectiveWidth;
|
|
||||||
if (i == numSizes) {
|
if (i == numSizes) {
|
||||||
// No match defaults to 100% viewport
|
// No match defaults to 100% viewport
|
||||||
nsCSSValue defaultWidth(100.0f, eCSSUnit_ViewportWidth);
|
nsCSSValue defaultWidth(100.0f, eCSSUnit_ViewportWidth);
|
||||||
@@ -468,6 +479,7 @@ ResponsiveImageSelector::ComputeFinalWidthForCurrentViewport(double *aWidth)
|
|||||||
effectiveWidth = nsRuleNode::CalcLengthWithInitialFont(pctx,
|
effectiveWidth = nsRuleNode::CalcLengthWithInitialFont(pctx,
|
||||||
mSizeValues[i]);
|
mSizeValues[i]);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
*aWidth = nsPresContext::AppUnitsToDoubleCSSPixels(std::max(effectiveWidth, 0));
|
*aWidth = nsPresContext::AppUnitsToDoubleCSSPixels(std::max(effectiveWidth, 0));
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -120,6 +120,10 @@ private:
|
|||||||
// resolve the absolute URL at selection time
|
// resolve the absolute URL at selection time
|
||||||
nsCOMPtr<nsIURI> mSelectedCandidateURL;
|
nsCOMPtr<nsIURI> mSelectedCandidateURL;
|
||||||
|
|
||||||
|
// Servo bits.
|
||||||
|
UniquePtr<RawServoSourceSizeList> mServoSourceSizeList;
|
||||||
|
|
||||||
|
// Gecko bits.
|
||||||
nsTArray< nsAutoPtr<nsMediaQuery> > mSizeQueries;
|
nsTArray< nsAutoPtr<nsMediaQuery> > mSizeQueries;
|
||||||
nsTArray<nsCSSValue> mSizeValues;
|
nsTArray<nsCSSValue> mSizeValues;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -134,6 +134,13 @@ SERVO_BINDING_FUNC(Servo_SelectorList_Drop, void,
|
|||||||
SERVO_BINDING_FUNC(Servo_SelectorList_Parse,
|
SERVO_BINDING_FUNC(Servo_SelectorList_Parse,
|
||||||
RawServoSelectorList*,
|
RawServoSelectorList*,
|
||||||
const nsACString* selector_list)
|
const nsACString* selector_list)
|
||||||
|
SERVO_BINDING_FUNC(Servo_SourceSizeList_Parse,
|
||||||
|
RawServoSourceSizeList*,
|
||||||
|
const nsACString* value)
|
||||||
|
SERVO_BINDING_FUNC(Servo_SourceSizeList_Evaluate,
|
||||||
|
int32_t,
|
||||||
|
RawServoStyleSetBorrowed set,
|
||||||
|
RawServoSourceSizeListBorrowedOrNull)
|
||||||
SERVO_BINDING_FUNC(Servo_SelectorList_Matches, bool,
|
SERVO_BINDING_FUNC(Servo_SelectorList_Matches, bool,
|
||||||
RawGeckoElementBorrowed, RawServoSelectorListBorrowed)
|
RawGeckoElementBorrowed, RawServoSelectorListBorrowed)
|
||||||
SERVO_BINDING_FUNC(Servo_SelectorList_Closest, const RawGeckoElement*,
|
SERVO_BINDING_FUNC(Servo_SelectorList_Closest, const RawGeckoElement*,
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
|
|
||||||
struct RawServoStyleSet;
|
struct RawServoStyleSet;
|
||||||
struct RawServoSelectorList;
|
struct RawServoSelectorList;
|
||||||
|
struct RawServoSourceSizeList;
|
||||||
struct RawServoAnimationValueMap;
|
struct RawServoAnimationValueMap;
|
||||||
struct RustString;
|
struct RustString;
|
||||||
|
|
||||||
@@ -182,6 +183,9 @@ DECL_BORROWED_REF_TYPE_FOR(nsXBLBinding)
|
|||||||
DECL_BORROWED_MUT_REF_TYPE_FOR(RawGeckoStyleChildrenIterator)
|
DECL_BORROWED_MUT_REF_TYPE_FOR(RawGeckoStyleChildrenIterator)
|
||||||
DECL_OWNED_REF_TYPE_FOR(RawServoSelectorList)
|
DECL_OWNED_REF_TYPE_FOR(RawServoSelectorList)
|
||||||
DECL_BORROWED_REF_TYPE_FOR(RawServoSelectorList)
|
DECL_BORROWED_REF_TYPE_FOR(RawServoSelectorList)
|
||||||
|
DECL_OWNED_REF_TYPE_FOR(RawServoSourceSizeList)
|
||||||
|
DECL_BORROWED_REF_TYPE_FOR(RawServoSourceSizeList)
|
||||||
|
DECL_NULLABLE_BORROWED_REF_TYPE_FOR(RawServoSourceSizeList)
|
||||||
|
|
||||||
#undef DECL_ARC_REF_TYPE_FOR
|
#undef DECL_ARC_REF_TYPE_FOR
|
||||||
#undef DECL_OWNED_REF_TYPE_FOR
|
#undef DECL_OWNED_REF_TYPE_FOR
|
||||||
@@ -225,6 +229,7 @@ DECL_BORROWED_REF_TYPE_FOR(RawServoSelectorList)
|
|||||||
|
|
||||||
DEFINE_BOXED_TYPE(StyleSet, RawServoStyleSet);
|
DEFINE_BOXED_TYPE(StyleSet, RawServoStyleSet);
|
||||||
DEFINE_BOXED_TYPE(SelectorList, RawServoSelectorList);
|
DEFINE_BOXED_TYPE(SelectorList, RawServoSelectorList);
|
||||||
|
DEFINE_BOXED_TYPE(SourceSizeList, RawServoSourceSizeList);
|
||||||
|
|
||||||
#undef DEFINE_BOXED_TYPE
|
#undef DEFINE_BOXED_TYPE
|
||||||
|
|
||||||
|
|||||||
@@ -495,6 +495,7 @@ structs-types = [
|
|||||||
"RawGeckoURLExtraData",
|
"RawGeckoURLExtraData",
|
||||||
"RawGeckoXBLBinding",
|
"RawGeckoXBLBinding",
|
||||||
"RawServoSelectorList",
|
"RawServoSelectorList",
|
||||||
|
"RawServoSourceSizeList",
|
||||||
"RefPtr",
|
"RefPtr",
|
||||||
"RustString",
|
"RustString",
|
||||||
"CSSPseudoClassType",
|
"CSSPseudoClassType",
|
||||||
@@ -608,6 +609,7 @@ array-types = [
|
|||||||
servo-owned-types = [
|
servo-owned-types = [
|
||||||
{ name = "RawServoStyleSet", opaque = true },
|
{ name = "RawServoStyleSet", opaque = true },
|
||||||
{ name = "RawServoSelectorList", opaque = false },
|
{ name = "RawServoSelectorList", opaque = false },
|
||||||
|
{ name = "RawServoSourceSizeList", opaque = false },
|
||||||
{ name = "ServoElementSnapshot", opaque = false },
|
{ name = "ServoElementSnapshot", opaque = false },
|
||||||
{ name = "RawServoAnimationValueMap", opaque = true },
|
{ name = "RawServoAnimationValueMap", opaque = true },
|
||||||
]
|
]
|
||||||
|
|||||||
@@ -14,6 +14,7 @@
|
|||||||
#include "mozilla/PostTraversalTask.h"
|
#include "mozilla/PostTraversalTask.h"
|
||||||
#include "mozilla/ServoBindingTypes.h"
|
#include "mozilla/ServoBindingTypes.h"
|
||||||
#include "mozilla/ServoElementSnapshot.h"
|
#include "mozilla/ServoElementSnapshot.h"
|
||||||
|
#include "mozilla/ServoBindings.h"
|
||||||
#include "mozilla/ServoUtils.h"
|
#include "mozilla/ServoUtils.h"
|
||||||
#include "mozilla/StyleSheetInlines.h"
|
#include "mozilla/StyleSheetInlines.h"
|
||||||
#include "mozilla/SheetType.h"
|
#include "mozilla/SheetType.h"
|
||||||
@@ -150,6 +151,15 @@ public:
|
|||||||
|
|
||||||
nsRestyleHint MediumFeaturesChanged(bool aViewportChanged);
|
nsRestyleHint MediumFeaturesChanged(bool aViewportChanged);
|
||||||
|
|
||||||
|
// Evaluates a given SourceSizeList, returning the optimal viewport width in
|
||||||
|
// app units.
|
||||||
|
//
|
||||||
|
// The SourceSizeList parameter can be null, in which case it will return
|
||||||
|
// 100vw.
|
||||||
|
nscoord EvaluateSourceSizeList(const RawServoSourceSizeList* aSourceSizeList) const {
|
||||||
|
return Servo_SourceSizeList_Evaluate(mRawSet.get(), aSourceSizeList);
|
||||||
|
}
|
||||||
|
|
||||||
// aViewportChanged outputs whether any viewport units is used.
|
// aViewportChanged outputs whether any viewport units is used.
|
||||||
bool MediumFeaturesChangedRules(bool* aViewportUnitsUsed);
|
bool MediumFeaturesChangedRules(bool* aViewportUnitsUsed);
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user