HTMLMarqueeElement.cpp (5405B)
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */ 3 /* This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #include "mozilla/dom/HTMLMarqueeElement.h" 8 9 #include "mozilla/AsyncEventDispatcher.h" 10 #include "mozilla/dom/CustomEvent.h" 11 #include "mozilla/dom/HTMLMarqueeElementBinding.h" 12 #include "nsGenericHTMLElement.h" 13 #include "nsStyleConsts.h" 14 // This is to pick up the definition of FunctionStringCallback: 15 #include "mozilla/dom/DataTransferItemBinding.h" 16 #include "mozilla/dom/ShadowRoot.h" 17 18 NS_IMPL_NS_NEW_HTML_ELEMENT(Marquee) 19 20 namespace mozilla::dom { 21 22 HTMLMarqueeElement::~HTMLMarqueeElement() = default; 23 24 NS_IMPL_ELEMENT_CLONE(HTMLMarqueeElement) 25 26 static constexpr nsAttrValue::EnumTableEntry kBehaviorTable[] = { 27 {"scroll", 1}, {"slide", 2}, {"alternate", 3} 28 29 }; 30 31 // Default behavior value is "scroll". 32 static constexpr const nsAttrValue::EnumTableEntry* kDefaultBehavior = 33 &kBehaviorTable[0]; 34 35 static constexpr nsAttrValue::EnumTableEntry kDirectionTable[] = { 36 {"left", 1}, {"right", 2}, {"up", 3}, {"down", 4}}; 37 38 // Default direction value is "left". 39 static constexpr const nsAttrValue::EnumTableEntry* kDefaultDirection = 40 &kDirectionTable[0]; 41 42 JSObject* HTMLMarqueeElement::WrapNode(JSContext* aCx, 43 JS::Handle<JSObject*> aGivenProto) { 44 return dom::HTMLMarqueeElement_Binding::Wrap(aCx, this, aGivenProto); 45 } 46 47 nsresult HTMLMarqueeElement::BindToTree(BindContext& aContext, 48 nsINode& aParent) { 49 nsresult rv = nsGenericHTMLElement::BindToTree(aContext, aParent); 50 NS_ENSURE_SUCCESS(rv, rv); 51 52 if (IsInComposedDoc()) { 53 AttachAndSetUAShadowRoot(); 54 } 55 56 return rv; 57 } 58 59 void HTMLMarqueeElement::UnbindFromTree(UnbindContext& aContext) { 60 if (IsInComposedDoc()) { 61 // We don't want to unattach the shadow root because it used to 62 // contain a <slot>. 63 NotifyUAWidgetTeardown(UnattachShadowRoot::No); 64 } 65 66 nsGenericHTMLElement::UnbindFromTree(aContext); 67 } 68 69 void HTMLMarqueeElement::GetBehavior(nsAString& aValue) { 70 GetEnumAttr(nsGkAtoms::behavior, kDefaultBehavior->tag, aValue); 71 } 72 73 void HTMLMarqueeElement::GetDirection(nsAString& aValue) { 74 GetEnumAttr(nsGkAtoms::direction, kDefaultDirection->tag, aValue); 75 } 76 77 bool HTMLMarqueeElement::ParseAttribute(int32_t aNamespaceID, 78 nsAtom* aAttribute, 79 const nsAString& aValue, 80 nsIPrincipal* aMaybeScriptedPrincipal, 81 nsAttrValue& aResult) { 82 if (aNamespaceID == kNameSpaceID_None) { 83 if ((aAttribute == nsGkAtoms::width) || (aAttribute == nsGkAtoms::height)) { 84 return aResult.ParseHTMLDimension(aValue); 85 } 86 if (aAttribute == nsGkAtoms::bgcolor) { 87 return aResult.ParseColor(aValue); 88 } 89 if (aAttribute == nsGkAtoms::behavior) { 90 return aResult.ParseEnumValue(aValue, kBehaviorTable, false, 91 kDefaultBehavior); 92 } 93 if (aAttribute == nsGkAtoms::direction) { 94 return aResult.ParseEnumValue(aValue, kDirectionTable, false, 95 kDefaultDirection); 96 } 97 if (aAttribute == nsGkAtoms::hspace || aAttribute == nsGkAtoms::vspace) { 98 return aResult.ParseHTMLDimension(aValue); 99 } 100 101 if (aAttribute == nsGkAtoms::loop) { 102 return aResult.ParseIntValue(aValue); 103 } 104 105 if (aAttribute == nsGkAtoms::scrollamount || 106 aAttribute == nsGkAtoms::scrolldelay) { 107 return aResult.ParseNonNegativeIntValue(aValue); 108 } 109 } 110 111 return nsGenericHTMLElement::ParseAttribute(aNamespaceID, aAttribute, aValue, 112 aMaybeScriptedPrincipal, aResult); 113 } 114 115 void HTMLMarqueeElement::MapAttributesIntoRule( 116 MappedDeclarationsBuilder& aBuilder) { 117 nsGenericHTMLElement::MapImageMarginAttributeInto(aBuilder); 118 nsGenericHTMLElement::MapImageSizeAttributesInto(aBuilder); 119 nsGenericHTMLElement::MapCommonAttributesInto(aBuilder); 120 nsGenericHTMLElement::MapBGColorInto(aBuilder); 121 } 122 123 NS_IMETHODIMP_(bool) 124 HTMLMarqueeElement::IsAttributeMapped(const nsAtom* aAttribute) const { 125 static const MappedAttributeEntry* const map[] = { 126 sImageMarginSizeAttributeMap, sBackgroundColorAttributeMap, 127 sCommonAttributeMap}; 128 return FindAttributeDependence(aAttribute, map); 129 } 130 131 nsMapRuleToAttributesFunc HTMLMarqueeElement::GetAttributeMappingFunction() 132 const { 133 return &MapAttributesIntoRule; 134 } 135 136 void HTMLMarqueeElement::DispatchEventToShadowRoot( 137 const nsAString& aEventTypeArg) { 138 // Dispatch the event to the UA Widget Shadow Root, make it inaccessible to 139 // document. 140 RefPtr<nsINode> shadow = GetShadowRoot(); 141 MOZ_ASSERT(shadow); 142 RefPtr<Event> event = new Event(shadow, nullptr, nullptr); 143 event->InitEvent(aEventTypeArg, false, false); 144 event->SetTrusted(true); 145 shadow->DispatchEvent(*event, IgnoreErrors()); 146 } 147 148 void HTMLMarqueeElement::Start() { 149 if (GetShadowRoot()) { 150 DispatchEventToShadowRoot(u"marquee-start"_ns); 151 } 152 } 153 154 void HTMLMarqueeElement::Stop() { 155 if (GetShadowRoot()) { 156 DispatchEventToShadowRoot(u"marquee-stop"_ns); 157 } 158 } 159 160 } // namespace mozilla::dom