michael@0: /* vim: set shiftwidth=4 tabstop=8 autoindent cindent expandtab: */ michael@0: /* This Source Code Form is subject to the terms of the Mozilla Public michael@0: * License, v. 2.0. If a copy of the MPL was not distributed with this michael@0: * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ michael@0: michael@0: /* the features that media queries can test */ michael@0: michael@0: #include "nsMediaFeatures.h" michael@0: #include "nsGkAtoms.h" michael@0: #include "nsCSSKeywords.h" michael@0: #include "nsStyleConsts.h" michael@0: #include "nsPresContext.h" michael@0: #include "nsCSSValue.h" michael@0: #ifdef XP_WIN michael@0: #include "mozilla/LookAndFeel.h" michael@0: #endif michael@0: #include "nsCSSRuleProcessor.h" michael@0: #include "nsDeviceContext.h" michael@0: #include "nsIDocument.h" michael@0: michael@0: using namespace mozilla; michael@0: michael@0: static const nsCSSProps::KTableValue kOrientationKeywords[] = { michael@0: eCSSKeyword_portrait, NS_STYLE_ORIENTATION_PORTRAIT, michael@0: eCSSKeyword_landscape, NS_STYLE_ORIENTATION_LANDSCAPE, michael@0: eCSSKeyword_UNKNOWN, -1 michael@0: }; michael@0: michael@0: static const nsCSSProps::KTableValue kScanKeywords[] = { michael@0: eCSSKeyword_progressive, NS_STYLE_SCAN_PROGRESSIVE, michael@0: eCSSKeyword_interlace, NS_STYLE_SCAN_INTERLACE, michael@0: eCSSKeyword_UNKNOWN, -1 michael@0: }; michael@0: michael@0: #ifdef XP_WIN michael@0: struct WindowsThemeName { michael@0: LookAndFeel::WindowsTheme id; michael@0: const wchar_t* name; michael@0: }; michael@0: michael@0: // Windows theme identities used in the -moz-windows-theme media query. michael@0: const WindowsThemeName themeStrings[] = { michael@0: { LookAndFeel::eWindowsTheme_Aero, L"aero" }, michael@0: { LookAndFeel::eWindowsTheme_AeroLite, L"aero-lite" }, michael@0: { LookAndFeel::eWindowsTheme_LunaBlue, L"luna-blue" }, michael@0: { LookAndFeel::eWindowsTheme_LunaOlive, L"luna-olive" }, michael@0: { LookAndFeel::eWindowsTheme_LunaSilver, L"luna-silver" }, michael@0: { LookAndFeel::eWindowsTheme_Royale, L"royale" }, michael@0: { LookAndFeel::eWindowsTheme_Zune, L"zune" }, michael@0: { LookAndFeel::eWindowsTheme_Generic, L"generic" } michael@0: }; michael@0: michael@0: struct OperatingSystemVersionInfo { michael@0: LookAndFeel::OperatingSystemVersion id; michael@0: const wchar_t* name; michael@0: }; michael@0: michael@0: // Os version identities used in the -moz-os-version media query. michael@0: const OperatingSystemVersionInfo osVersionStrings[] = { michael@0: { LookAndFeel::eOperatingSystemVersion_WindowsXP, L"windows-xp" }, michael@0: { LookAndFeel::eOperatingSystemVersion_WindowsVista, L"windows-vista" }, michael@0: { LookAndFeel::eOperatingSystemVersion_Windows7, L"windows-win7" }, michael@0: { LookAndFeel::eOperatingSystemVersion_Windows8, L"windows-win8" }, michael@0: }; michael@0: #endif michael@0: michael@0: // A helper for four features below michael@0: static nsSize michael@0: GetSize(nsPresContext* aPresContext) michael@0: { michael@0: nsSize size; michael@0: if (aPresContext->IsRootPaginatedDocument()) michael@0: // We want the page size, including unprintable areas and margins. michael@0: size = aPresContext->GetPageSize(); michael@0: else michael@0: size = aPresContext->GetVisibleArea().Size(); michael@0: return size; michael@0: } michael@0: michael@0: static nsresult michael@0: GetWidth(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: nsSize size = GetSize(aPresContext); michael@0: float pixelWidth = aPresContext->AppUnitsToFloatCSSPixels(size.width); michael@0: aResult.SetFloatValue(pixelWidth, eCSSUnit_Pixel); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetHeight(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: nsSize size = GetSize(aPresContext); michael@0: float pixelHeight = aPresContext->AppUnitsToFloatCSSPixels(size.height); michael@0: aResult.SetFloatValue(pixelHeight, eCSSUnit_Pixel); michael@0: return NS_OK; michael@0: } michael@0: michael@0: inline static nsDeviceContext* michael@0: GetDeviceContextFor(nsPresContext* aPresContext) michael@0: { michael@0: // It would be nice to call michael@0: // nsLayoutUtils::GetDeviceContextForScreenInfo here, except for two michael@0: // things: (1) it can flush, and flushing is bad here, and (2) it michael@0: // doesn't really get us consistency in multi-monitor situations michael@0: // *anyway*. michael@0: return aPresContext->DeviceContext(); michael@0: } michael@0: michael@0: // A helper for three features below. michael@0: static nsSize michael@0: GetDeviceSize(nsPresContext* aPresContext) michael@0: { michael@0: nsSize size; michael@0: michael@0: if (!aPresContext->IsChrome() || aPresContext->IsDeviceSizePageSize()) { michael@0: size = GetSize(aPresContext); michael@0: } else if (aPresContext->IsRootPaginatedDocument()) { michael@0: // We want the page size, including unprintable areas and margins. michael@0: // XXX The spec actually says we want the "page sheet size", but michael@0: // how is that different? michael@0: size = aPresContext->GetPageSize(); michael@0: } else { michael@0: GetDeviceContextFor(aPresContext)-> michael@0: GetDeviceSurfaceDimensions(size.width, size.height); michael@0: } michael@0: return size; michael@0: } michael@0: michael@0: static nsresult michael@0: GetDeviceWidth(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: nsSize size = GetDeviceSize(aPresContext); michael@0: float pixelWidth = aPresContext->AppUnitsToFloatCSSPixels(size.width); michael@0: aResult.SetFloatValue(pixelWidth, eCSSUnit_Pixel); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetDeviceHeight(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: nsSize size = GetDeviceSize(aPresContext); michael@0: float pixelHeight = aPresContext->AppUnitsToFloatCSSPixels(size.height); michael@0: aResult.SetFloatValue(pixelHeight, eCSSUnit_Pixel); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetOrientation(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: nsSize size = GetSize(aPresContext); michael@0: int32_t orientation; michael@0: if (size.width > size.height) { michael@0: orientation = NS_STYLE_ORIENTATION_LANDSCAPE; michael@0: } else { michael@0: // Per spec, square viewports should be 'portrait' michael@0: orientation = NS_STYLE_ORIENTATION_PORTRAIT; michael@0: } michael@0: michael@0: aResult.SetIntValue(orientation, eCSSUnit_Enumerated); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetDeviceOrientation(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: nsSize size = GetDeviceSize(aPresContext); michael@0: int32_t orientation; michael@0: if (size.width > size.height) { michael@0: orientation = NS_STYLE_ORIENTATION_LANDSCAPE; michael@0: } else { michael@0: // Per spec, square viewports should be 'portrait' michael@0: orientation = NS_STYLE_ORIENTATION_PORTRAIT; michael@0: } michael@0: michael@0: aResult.SetIntValue(orientation, eCSSUnit_Enumerated); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetIsResourceDocument(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: nsIDocument* doc = aPresContext->Document(); michael@0: aResult.SetIntValue(doc && doc->IsResourceDoc() ? 1 : 0, eCSSUnit_Integer); michael@0: return NS_OK; michael@0: } michael@0: michael@0: // Helper for two features below michael@0: static nsresult michael@0: MakeArray(const nsSize& aSize, nsCSSValue& aResult) michael@0: { michael@0: nsRefPtr a = nsCSSValue::Array::Create(2); michael@0: michael@0: a->Item(0).SetIntValue(aSize.width, eCSSUnit_Integer); michael@0: a->Item(1).SetIntValue(aSize.height, eCSSUnit_Integer); michael@0: michael@0: aResult.SetArrayValue(a, eCSSUnit_Array); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetAspectRatio(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: return MakeArray(GetSize(aPresContext), aResult); michael@0: } michael@0: michael@0: static nsresult michael@0: GetDeviceAspectRatio(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: return MakeArray(GetDeviceSize(aPresContext), aResult); michael@0: } michael@0: michael@0: static nsresult michael@0: GetColor(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: uint32_t depth = 24; // Always assume 24-bit depth for non-chrome callers. michael@0: michael@0: if (aPresContext->IsChrome()) { michael@0: // FIXME: This implementation is bogus. nsDeviceContext michael@0: // doesn't provide reliable information (should be fixed in bug michael@0: // 424386). michael@0: // FIXME: On a monochrome device, return 0! michael@0: nsDeviceContext *dx = GetDeviceContextFor(aPresContext); michael@0: dx->GetDepth(depth); michael@0: } michael@0: michael@0: // The spec says to use bits *per color component*, so divide by 3, michael@0: // and round down, since the spec says to use the smallest when the michael@0: // color components differ. michael@0: depth /= 3; michael@0: aResult.SetIntValue(int32_t(depth), eCSSUnit_Integer); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetColorIndex(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: // We should return zero if the device does not use a color lookup michael@0: // table. Stuart says that our handling of displays with 8-bit michael@0: // color is bad enough that we never change the lookup table to michael@0: // match what we're trying to display, so perhaps we should always michael@0: // return zero. Given that there isn't any better information michael@0: // exposed, we don't have much other choice. michael@0: aResult.SetIntValue(0, eCSSUnit_Integer); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetMonochrome(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: // For color devices we should return 0. michael@0: // FIXME: On a monochrome device, return the actual color depth, not michael@0: // 0! michael@0: aResult.SetIntValue(0, eCSSUnit_Integer); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetResolution(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: float dpi = 96; // Always return 96 to non-chrome callers. michael@0: michael@0: if (aPresContext->IsChrome()) { michael@0: // Resolution measures device pixels per CSS (inch/cm/pixel). We michael@0: // return it in device pixels per CSS inches. michael@0: dpi = float(nsPresContext::AppUnitsPerCSSInch()) / michael@0: float(aPresContext->AppUnitsPerDevPixel()); michael@0: } michael@0: michael@0: aResult.SetFloatValue(dpi, eCSSUnit_Inch); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetScan(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: // Since Gecko doesn't support the 'tv' media type, the 'scan' michael@0: // feature is never present. michael@0: aResult.Reset(); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetGrid(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: // Gecko doesn't support grid devices (e.g., ttys), so the 'grid' michael@0: // feature is always 0. michael@0: aResult.SetIntValue(0, eCSSUnit_Integer); michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetDevicePixelRatio(nsPresContext* aPresContext, const nsMediaFeature*, michael@0: nsCSSValue& aResult) michael@0: { michael@0: if (aPresContext->IsChrome()) { michael@0: float ratio = aPresContext->CSSPixelsToDevPixels(1.0f); michael@0: aResult.SetFloatValue(ratio, eCSSUnit_Number); michael@0: } else { michael@0: aResult.SetFloatValue(1.0, eCSSUnit_Number); michael@0: } michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetSystemMetric(nsPresContext* aPresContext, const nsMediaFeature* aFeature, michael@0: nsCSSValue& aResult) michael@0: { michael@0: aResult.Reset(); michael@0: if (aPresContext->IsChrome()) { michael@0: NS_ABORT_IF_FALSE(aFeature->mValueType == nsMediaFeature::eBoolInteger, michael@0: "unexpected type"); michael@0: nsIAtom *metricAtom = *aFeature->mData.mMetric; michael@0: bool hasMetric = nsCSSRuleProcessor::HasSystemMetric(metricAtom); michael@0: aResult.SetIntValue(hasMetric ? 1 : 0, eCSSUnit_Integer); michael@0: } michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetWindowsTheme(nsPresContext* aPresContext, const nsMediaFeature* aFeature, michael@0: nsCSSValue& aResult) michael@0: { michael@0: aResult.Reset(); michael@0: #ifdef XP_WIN michael@0: if (aPresContext->IsChrome()) { michael@0: uint8_t windowsThemeId = michael@0: nsCSSRuleProcessor::GetWindowsThemeIdentifier(); michael@0: michael@0: // Classic mode should fail to match. michael@0: if (windowsThemeId == LookAndFeel::eWindowsTheme_Classic) michael@0: return NS_OK; michael@0: michael@0: // Look up the appropriate theme string michael@0: for (size_t i = 0; i < ArrayLength(themeStrings); ++i) { michael@0: if (windowsThemeId == themeStrings[i].id) { michael@0: aResult.SetStringValue(nsDependentString(themeStrings[i].name), michael@0: eCSSUnit_Ident); michael@0: break; michael@0: } michael@0: } michael@0: } michael@0: #endif michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetOperatinSystemVersion(nsPresContext* aPresContext, const nsMediaFeature* aFeature, michael@0: nsCSSValue& aResult) michael@0: { michael@0: aResult.Reset(); michael@0: if (!aPresContext->IsChrome()) return NS_OK; michael@0: michael@0: #ifdef XP_WIN michael@0: int32_t metricResult; michael@0: if (NS_SUCCEEDED( michael@0: LookAndFeel::GetInt(LookAndFeel::eIntID_OperatingSystemVersionIdentifier, michael@0: &metricResult))) { michael@0: for (size_t i = 0; i < ArrayLength(osVersionStrings); ++i) { michael@0: if (metricResult == osVersionStrings[i].id) { michael@0: aResult.SetStringValue(nsDependentString(osVersionStrings[i].name), michael@0: eCSSUnit_Ident); michael@0: break; michael@0: } michael@0: } michael@0: } michael@0: #endif michael@0: return NS_OK; michael@0: } michael@0: michael@0: static nsresult michael@0: GetIsGlyph(nsPresContext* aPresContext, const nsMediaFeature* aFeature, michael@0: nsCSSValue& aResult) michael@0: { michael@0: aResult.SetIntValue(aPresContext->IsGlyph() ? 1 : 0, eCSSUnit_Integer); michael@0: return NS_OK; michael@0: } michael@0: michael@0: /* michael@0: * Adding new media features requires (1) adding the new feature to this michael@0: * array, with appropriate entries (and potentially any new code needed michael@0: * to support new types in these entries and (2) ensuring that either michael@0: * nsPresContext::MediaFeatureValuesChanged or michael@0: * nsPresContext::PostMediaFeatureValuesChangedEvent is called when the michael@0: * value that would be returned by the entry's mGetter changes. michael@0: */ michael@0: michael@0: /* static */ const nsMediaFeature michael@0: nsMediaFeatures::features[] = { michael@0: { michael@0: &nsGkAtoms::width, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eLength, michael@0: { nullptr }, michael@0: GetWidth michael@0: }, michael@0: { michael@0: &nsGkAtoms::height, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eLength, michael@0: { nullptr }, michael@0: GetHeight michael@0: }, michael@0: { michael@0: &nsGkAtoms::deviceWidth, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eLength, michael@0: { nullptr }, michael@0: GetDeviceWidth michael@0: }, michael@0: { michael@0: &nsGkAtoms::deviceHeight, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eLength, michael@0: { nullptr }, michael@0: GetDeviceHeight michael@0: }, michael@0: { michael@0: &nsGkAtoms::orientation, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eEnumerated, michael@0: { kOrientationKeywords }, michael@0: GetOrientation michael@0: }, michael@0: { michael@0: &nsGkAtoms::aspectRatio, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eIntRatio, michael@0: { nullptr }, michael@0: GetAspectRatio michael@0: }, michael@0: { michael@0: &nsGkAtoms::deviceAspectRatio, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eIntRatio, michael@0: { nullptr }, michael@0: GetDeviceAspectRatio michael@0: }, michael@0: { michael@0: &nsGkAtoms::color, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eInteger, michael@0: { nullptr }, michael@0: GetColor michael@0: }, michael@0: { michael@0: &nsGkAtoms::colorIndex, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eInteger, michael@0: { nullptr }, michael@0: GetColorIndex michael@0: }, michael@0: { michael@0: &nsGkAtoms::monochrome, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eInteger, michael@0: { nullptr }, michael@0: GetMonochrome michael@0: }, michael@0: { michael@0: &nsGkAtoms::resolution, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eResolution, michael@0: { nullptr }, michael@0: GetResolution michael@0: }, michael@0: { michael@0: &nsGkAtoms::scan, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eEnumerated, michael@0: { kScanKeywords }, michael@0: GetScan michael@0: }, michael@0: { michael@0: &nsGkAtoms::grid, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { nullptr }, michael@0: GetGrid michael@0: }, michael@0: michael@0: // Mozilla extensions michael@0: { michael@0: &nsGkAtoms::_moz_device_pixel_ratio, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eFloat, michael@0: { nullptr }, michael@0: GetDevicePixelRatio michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_device_orientation, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eEnumerated, michael@0: { kOrientationKeywords }, michael@0: GetDeviceOrientation michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_is_resource_document, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { nullptr }, michael@0: GetIsResourceDocument michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_color_picker_available, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::color_picker_available }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_scrollbar_start_backward, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::scrollbar_start_backward }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_scrollbar_start_forward, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::scrollbar_start_forward }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_scrollbar_end_backward, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::scrollbar_end_backward }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_scrollbar_end_forward, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::scrollbar_end_forward }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_scrollbar_thumb_proportional, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::scrollbar_thumb_proportional }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_images_in_menus, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::images_in_menus }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_images_in_buttons, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::images_in_buttons }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_overlay_scrollbars, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::overlay_scrollbars }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_windows_default_theme, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::windows_default_theme }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_mac_graphite_theme, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::mac_graphite_theme }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_mac_lion_theme, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::mac_lion_theme }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_windows_compositor, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::windows_compositor }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_windows_classic, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::windows_classic }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_windows_glass, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::windows_glass }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_touch_enabled, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::touch_enabled }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_menubar_drag, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::menubar_drag }, michael@0: GetSystemMetric michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_windows_theme, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eIdent, michael@0: { nullptr }, michael@0: GetWindowsTheme michael@0: }, michael@0: { michael@0: &nsGkAtoms::_moz_os_version, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eIdent, michael@0: { nullptr }, michael@0: GetOperatinSystemVersion michael@0: }, michael@0: michael@0: { michael@0: &nsGkAtoms::_moz_swipe_animation_enabled, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::swipe_animation_enabled }, michael@0: GetSystemMetric michael@0: }, michael@0: michael@0: { michael@0: &nsGkAtoms::_moz_physical_home_button, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { &nsGkAtoms::physical_home_button }, michael@0: GetSystemMetric michael@0: }, michael@0: michael@0: // Internal -moz-is-glyph media feature: applies only inside SVG glyphs. michael@0: // Internal because it is really only useful in the user agent anyway michael@0: // and therefore not worth standardizing. michael@0: { michael@0: &nsGkAtoms::_moz_is_glyph, michael@0: nsMediaFeature::eMinMaxNotAllowed, michael@0: nsMediaFeature::eBoolInteger, michael@0: { nullptr }, michael@0: GetIsGlyph michael@0: }, michael@0: // Null-mName terminator: michael@0: { michael@0: nullptr, michael@0: nsMediaFeature::eMinMaxAllowed, michael@0: nsMediaFeature::eInteger, michael@0: { nullptr }, michael@0: nullptr michael@0: }, michael@0: };