StyleValue.h 32 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100
  1. /*
  2. * Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
  3. * Copyright (c) 2021, Tobias Christiansen <tobyase@serenityos.org>
  4. * Copyright (c) 2021, Sam Atkins <atkinssj@serenityos.org>
  5. *
  6. * SPDX-License-Identifier: BSD-2-Clause
  7. */
  8. #pragma once
  9. #include <AK/NonnullOwnPtr.h>
  10. #include <AK/NonnullOwnPtrVector.h>
  11. #include <AK/NonnullRefPtrVector.h>
  12. #include <AK/RefCounted.h>
  13. #include <AK/RefPtr.h>
  14. #include <AK/String.h>
  15. #include <AK/StringView.h>
  16. #include <AK/URL.h>
  17. #include <AK/Variant.h>
  18. #include <AK/Vector.h>
  19. #include <AK/WeakPtr.h>
  20. #include <LibGfx/Bitmap.h>
  21. #include <LibGfx/Color.h>
  22. #include <LibWeb/CSS/Length.h>
  23. #include <LibWeb/CSS/Parser/StyleComponentValueRule.h>
  24. #include <LibWeb/CSS/PropertyID.h>
  25. #include <LibWeb/CSS/ValueID.h>
  26. #include <LibWeb/Forward.h>
  27. #include <LibWeb/Loader/ImageResource.h>
  28. namespace Web::CSS {
  29. enum class Position {
  30. Static,
  31. Relative,
  32. Absolute,
  33. Fixed,
  34. Sticky,
  35. };
  36. enum class TextAlign {
  37. Left,
  38. Center,
  39. Right,
  40. Justify,
  41. LibwebCenter,
  42. };
  43. enum class TextDecorationLine {
  44. None,
  45. Underline,
  46. Overline,
  47. LineThrough,
  48. Blink,
  49. };
  50. enum class TextTransform {
  51. None,
  52. Capitalize,
  53. Uppercase,
  54. Lowercase,
  55. FullWidth,
  56. FullSizeKana,
  57. };
  58. enum class Display {
  59. None,
  60. Block,
  61. Inline,
  62. InlineBlock,
  63. ListItem,
  64. Table,
  65. TableRow,
  66. TableCell,
  67. TableHeaderGroup,
  68. TableRowGroup,
  69. TableFooterGroup,
  70. TableColumn,
  71. TableColumnGroup,
  72. TableCaption,
  73. Flex,
  74. };
  75. enum class FlexDirection {
  76. Row,
  77. RowReverse,
  78. Column,
  79. ColumnReverse,
  80. };
  81. enum class FlexWrap {
  82. Nowrap,
  83. Wrap,
  84. WrapReverse
  85. };
  86. enum class FlexBasis {
  87. Content,
  88. Length,
  89. Auto,
  90. };
  91. enum class WhiteSpace {
  92. Normal,
  93. Pre,
  94. Nowrap,
  95. PreLine,
  96. PreWrap,
  97. };
  98. enum class Float {
  99. None,
  100. Left,
  101. Right,
  102. };
  103. enum class Clear {
  104. None,
  105. Left,
  106. Right,
  107. Both,
  108. };
  109. enum class Cursor {
  110. Auto,
  111. Default,
  112. None,
  113. ContextMenu,
  114. Help,
  115. Pointer,
  116. Progress,
  117. Wait,
  118. Cell,
  119. Crosshair,
  120. Text,
  121. VerticalText,
  122. Alias,
  123. Copy,
  124. Move,
  125. NoDrop,
  126. NotAllowed,
  127. Grab,
  128. Grabbing,
  129. EResize,
  130. NResize,
  131. NeResize,
  132. NwResize,
  133. SResize,
  134. SeResize,
  135. SwResize,
  136. WResize,
  137. EwResize,
  138. NsResize,
  139. NeswResize,
  140. NwseResize,
  141. ColResize,
  142. RowResize,
  143. AllScroll,
  144. ZoomIn,
  145. ZoomOut,
  146. };
  147. enum class LineStyle {
  148. None,
  149. Hidden,
  150. Dotted,
  151. Dashed,
  152. Solid,
  153. Double,
  154. Groove,
  155. Ridge,
  156. Inset,
  157. Outset,
  158. };
  159. enum class ListStyleType {
  160. None,
  161. Disc,
  162. Circle,
  163. Square,
  164. Decimal,
  165. DecimalLeadingZero,
  166. LowerAlpha,
  167. LowerLatin,
  168. LowerRoman,
  169. UpperAlpha,
  170. UpperLatin,
  171. UpperRoman,
  172. };
  173. enum class Overflow : u8 {
  174. Auto,
  175. Clip,
  176. Hidden,
  177. Scroll,
  178. Visible,
  179. };
  180. enum class Repeat : u8 {
  181. NoRepeat,
  182. Repeat,
  183. Round,
  184. Space,
  185. };
  186. enum class JustifyContent {
  187. FlexStart,
  188. FlexEnd,
  189. Center,
  190. SpaceBetween,
  191. SpaceAround,
  192. };
  193. enum class AlignItems {
  194. FlexStart,
  195. FlexEnd,
  196. Center,
  197. Baseline,
  198. Stretch,
  199. };
  200. class StyleValue : public RefCounted<StyleValue> {
  201. public:
  202. virtual ~StyleValue();
  203. enum class Type {
  204. Invalid,
  205. Inherit,
  206. Initial,
  207. Unset,
  208. String,
  209. Length,
  210. Color,
  211. Identifier,
  212. Image,
  213. CustomProperty,
  214. Numeric,
  215. ValueList,
  216. Calculated,
  217. Background,
  218. BackgroundRepeat,
  219. Border,
  220. BorderRadius,
  221. CombinedBorderRadius,
  222. BoxShadow,
  223. Flex,
  224. FlexFlow,
  225. Font,
  226. ListStyle,
  227. Overflow,
  228. TextDecoration,
  229. };
  230. Type type() const { return m_type; }
  231. bool is_inherit() const { return type() == Type::Inherit; }
  232. bool is_initial() const { return type() == Type::Initial; }
  233. bool is_unset() const { return type() == Type::Unset; }
  234. bool is_color() const { return type() == Type::Color; }
  235. bool is_identifier() const { return type() == Type::Identifier || is_auto(); }
  236. bool is_image() const { return type() == Type::Image; }
  237. bool is_string() const { return type() == Type::String; }
  238. virtual bool is_length() const { return type() == Type::Length; }
  239. bool is_custom_property() const { return type() == Type::CustomProperty; }
  240. bool is_numeric() const { return type() == Type::Numeric; }
  241. bool is_value_list() const { return type() == Type::ValueList; }
  242. bool is_calculated() const { return type() == Type::Calculated; }
  243. bool is_background() const { return type() == Type::Background; }
  244. bool is_background_repeat() const { return type() == Type::BackgroundRepeat; }
  245. bool is_border() const { return type() == Type::Border; }
  246. bool is_border_radius() const { return type() == Type::BorderRadius; }
  247. bool is_box_shadow() const { return type() == Type::BoxShadow; }
  248. bool is_flex() const { return type() == Type::Flex; }
  249. bool is_flex_flow() const { return type() == Type::FlexFlow; }
  250. bool is_font() const { return type() == Type::Font; }
  251. bool is_list_style() const { return type() == Type::ListStyle; }
  252. bool is_overflow() const { return type() == Type::Overflow; }
  253. bool is_text_decoration() const { return type() == Type::TextDecoration; }
  254. bool is_builtin() const { return is_inherit() || is_initial() || is_unset(); }
  255. bool is_builtin_or_dynamic() const
  256. {
  257. return is_builtin() || is_custom_property() || is_calculated();
  258. }
  259. virtual String to_string() const = 0;
  260. virtual Length to_length() const { return {}; }
  261. virtual Color to_color(const DOM::Document&) const { return {}; }
  262. CSS::ValueID to_identifier() const;
  263. virtual bool is_auto() const { return false; }
  264. bool operator==(const StyleValue& other) const { return equals(other); }
  265. bool operator!=(const StyleValue& other) const { return !(*this == other); }
  266. virtual bool equals(const StyleValue& other) const
  267. {
  268. if (type() != other.type())
  269. return false;
  270. return to_string() == other.to_string();
  271. }
  272. protected:
  273. explicit StyleValue(Type);
  274. private:
  275. Type m_type { Type::Invalid };
  276. };
  277. // FIXME: Allow for fallback
  278. class CustomStyleValue : public StyleValue {
  279. public:
  280. static NonnullRefPtr<CustomStyleValue> create(const String& custom_property_name)
  281. {
  282. return adopt_ref(*new CustomStyleValue(custom_property_name));
  283. }
  284. String custom_property_name() const { return m_custom_property_name; }
  285. String to_string() const override { return m_custom_property_name; }
  286. private:
  287. explicit CustomStyleValue(const String& custom_property_name)
  288. : StyleValue(Type::CustomProperty)
  289. , m_custom_property_name(custom_property_name)
  290. {
  291. }
  292. String m_custom_property_name {};
  293. };
  294. class NumericStyleValue : public StyleValue {
  295. public:
  296. static NonnullRefPtr<NumericStyleValue> create(float value)
  297. {
  298. return adopt_ref(*new NumericStyleValue(value));
  299. }
  300. virtual bool is_length() const override { return m_value == 0; }
  301. virtual Length to_length() const override { return Length(0, Length::Type::Px); }
  302. float value() const { return m_value; }
  303. String to_string() const override { return String::formatted("{}", m_value); }
  304. private:
  305. explicit NumericStyleValue(float value)
  306. : StyleValue(Type::Numeric)
  307. , m_value(value)
  308. {
  309. }
  310. float m_value { 0 };
  311. };
  312. class StringStyleValue : public StyleValue {
  313. public:
  314. static NonnullRefPtr<StringStyleValue> create(const String& string)
  315. {
  316. return adopt_ref(*new StringStyleValue(string));
  317. }
  318. virtual ~StringStyleValue() override { }
  319. String to_string() const override { return m_string; }
  320. private:
  321. explicit StringStyleValue(const String& string)
  322. : StyleValue(Type::String)
  323. , m_string(string)
  324. {
  325. }
  326. String m_string;
  327. };
  328. class BoxShadowStyleValue : public StyleValue {
  329. public:
  330. static NonnullRefPtr<BoxShadowStyleValue> create(Length const& offset_x, Length const& offset_y, Length const& blur_radius, Color const& color)
  331. {
  332. return adopt_ref(*new BoxShadowStyleValue(offset_x, offset_y, blur_radius, color));
  333. }
  334. virtual ~BoxShadowStyleValue() override { }
  335. Length const& offset_x() const { return m_offset_x; }
  336. Length const& offset_y() const { return m_offset_y; }
  337. Length const& blur_radius() const { return m_blur_radius; }
  338. Color const& color() const { return m_color; }
  339. String to_string() const override { return String::formatted("BoxShadow offset_x: {}, offset_y: {}, blur_radius: {}, color: {}",
  340. m_offset_x.to_string(), m_offset_y.to_string(), m_blur_radius.to_string(), m_color.to_string()); }
  341. private:
  342. explicit BoxShadowStyleValue(Length const& offset_x, Length const& offset_y, Length const& blur_radius, Color const& color)
  343. : StyleValue(Type::BoxShadow)
  344. , m_offset_x(offset_x)
  345. , m_offset_y(offset_y)
  346. , m_blur_radius(blur_radius)
  347. , m_color(color)
  348. {
  349. }
  350. Length m_offset_x;
  351. Length m_offset_y;
  352. Length m_blur_radius;
  353. Color m_color;
  354. };
  355. class LengthStyleValue : public StyleValue {
  356. public:
  357. static NonnullRefPtr<LengthStyleValue> create(const Length& length)
  358. {
  359. return adopt_ref(*new LengthStyleValue(length));
  360. }
  361. virtual ~LengthStyleValue() override { }
  362. virtual String to_string() const override { return m_length.to_string(); }
  363. virtual Length to_length() const override { return m_length; }
  364. const Length& length() const { return m_length; }
  365. virtual bool is_auto() const override { return m_length.is_auto(); }
  366. virtual bool equals(const StyleValue& other) const override
  367. {
  368. if (type() != other.type())
  369. return false;
  370. return m_length == static_cast<const LengthStyleValue&>(other).m_length;
  371. }
  372. private:
  373. explicit LengthStyleValue(const Length& length)
  374. : StyleValue(Type::Length)
  375. , m_length(length)
  376. {
  377. }
  378. Length m_length;
  379. };
  380. class CalculatedStyleValue : public StyleValue {
  381. public:
  382. struct CalcSum;
  383. struct CalcSumPartWithOperator;
  384. struct CalcProduct;
  385. struct CalcProductPartWithOperator;
  386. struct CalcNumberSum;
  387. struct CalcNumberSumPartWithOperator;
  388. struct CalcNumberProduct;
  389. struct CalcNumberProductPartWithOperator;
  390. using CalcNumberValue = Variant<float, NonnullOwnPtr<CalcNumberSum>>;
  391. using CalcValue = Variant<float, CSS::Length, NonnullOwnPtr<CalcSum>>;
  392. // This represents that: https://drafts.csswg.org/css-values-3/#calc-syntax
  393. struct CalcSum {
  394. CalcSum(NonnullOwnPtr<CalcProduct> first_calc_product, NonnullOwnPtrVector<CalcSumPartWithOperator> additional)
  395. : first_calc_product(move(first_calc_product))
  396. , zero_or_more_additional_calc_products(move(additional)) {};
  397. NonnullOwnPtr<CalcProduct> first_calc_product;
  398. NonnullOwnPtrVector<CalcSumPartWithOperator> zero_or_more_additional_calc_products;
  399. };
  400. struct CalcNumberSum {
  401. CalcNumberSum(NonnullOwnPtr<CalcNumberProduct> first_calc_number_product, NonnullOwnPtrVector<CalcNumberSumPartWithOperator> additional)
  402. : first_calc_number_product(move(first_calc_number_product))
  403. , zero_or_more_additional_calc_number_products(move(additional)) {};
  404. NonnullOwnPtr<CalcNumberProduct> first_calc_number_product;
  405. NonnullOwnPtrVector<CalcNumberSumPartWithOperator> zero_or_more_additional_calc_number_products;
  406. };
  407. struct CalcProduct {
  408. CalcValue first_calc_value;
  409. NonnullOwnPtrVector<CalcProductPartWithOperator> zero_or_more_additional_calc_values;
  410. };
  411. struct CalcSumPartWithOperator {
  412. enum Operation {
  413. Add,
  414. Subtract,
  415. };
  416. CalcSumPartWithOperator(Operation op, NonnullOwnPtr<CalcProduct> calc_product)
  417. : op(op)
  418. , calc_product(move(calc_product)) {};
  419. Operation op;
  420. NonnullOwnPtr<CalcProduct> calc_product;
  421. };
  422. struct CalcProductPartWithOperator {
  423. enum {
  424. Multiply,
  425. Divide,
  426. } op;
  427. Variant<CalcValue, CalcNumberValue> value;
  428. };
  429. struct CalcNumberProduct {
  430. CalcNumberValue first_calc_number_value;
  431. NonnullOwnPtrVector<CalcNumberProductPartWithOperator> zero_or_more_additional_calc_number_values;
  432. };
  433. struct CalcNumberProductPartWithOperator {
  434. enum {
  435. Multiply,
  436. Divide,
  437. } op;
  438. CalcNumberValue value;
  439. };
  440. struct CalcNumberSumPartWithOperator {
  441. enum Operation {
  442. Add,
  443. Subtract,
  444. };
  445. CalcNumberSumPartWithOperator(Operation op, NonnullOwnPtr<CalcNumberProduct> calc_number_product)
  446. : op(op)
  447. , calc_number_product(move(calc_number_product)) {};
  448. Operation op;
  449. NonnullOwnPtr<CalcNumberProduct> calc_number_product;
  450. };
  451. static NonnullRefPtr<CalculatedStyleValue> create(String const& expression_string, NonnullOwnPtr<CalcSum> calc_sum)
  452. {
  453. return adopt_ref(*new CalculatedStyleValue(expression_string, move(calc_sum)));
  454. }
  455. String to_string() const override { return m_expression_string; }
  456. NonnullOwnPtr<CalcSum> const& expression() const { return m_expression; }
  457. private:
  458. explicit CalculatedStyleValue(String const& expression_string, NonnullOwnPtr<CalcSum> calc_sum)
  459. : StyleValue(Type::Calculated)
  460. , m_expression_string(expression_string)
  461. , m_expression(move(calc_sum))
  462. {
  463. }
  464. String m_expression_string;
  465. NonnullOwnPtr<CalcSum> m_expression;
  466. };
  467. class InitialStyleValue final : public StyleValue {
  468. public:
  469. static NonnullRefPtr<InitialStyleValue> the()
  470. {
  471. static NonnullRefPtr<InitialStyleValue> instance = adopt_ref(*new InitialStyleValue);
  472. return instance;
  473. }
  474. virtual ~InitialStyleValue() override { }
  475. String to_string() const override { return "initial"; }
  476. private:
  477. InitialStyleValue()
  478. : StyleValue(Type::Initial)
  479. {
  480. }
  481. };
  482. class InheritStyleValue final : public StyleValue {
  483. public:
  484. static NonnullRefPtr<InheritStyleValue> the()
  485. {
  486. static NonnullRefPtr<InheritStyleValue> instance = adopt_ref(*new InheritStyleValue);
  487. return instance;
  488. }
  489. virtual ~InheritStyleValue() override { }
  490. String to_string() const override { return "inherit"; }
  491. private:
  492. InheritStyleValue()
  493. : StyleValue(Type::Inherit)
  494. {
  495. }
  496. };
  497. class UnsetStyleValue final : public StyleValue {
  498. public:
  499. static NonnullRefPtr<UnsetStyleValue> the()
  500. {
  501. static NonnullRefPtr<UnsetStyleValue> instance = adopt_ref(*new UnsetStyleValue);
  502. return instance;
  503. }
  504. virtual ~UnsetStyleValue() override { }
  505. String to_string() const override { return "unset"; }
  506. private:
  507. UnsetStyleValue()
  508. : StyleValue(Type::Unset)
  509. {
  510. }
  511. };
  512. class ColorStyleValue : public StyleValue {
  513. public:
  514. static NonnullRefPtr<ColorStyleValue> create(Color color)
  515. {
  516. return adopt_ref(*new ColorStyleValue(color));
  517. }
  518. virtual ~ColorStyleValue() override { }
  519. Color color() const { return m_color; }
  520. String to_string() const override { return m_color.to_string(); }
  521. Color to_color(const DOM::Document&) const override { return m_color; }
  522. virtual bool equals(const StyleValue& other) const override
  523. {
  524. if (type() != other.type())
  525. return false;
  526. return m_color == static_cast<const ColorStyleValue&>(other).m_color;
  527. }
  528. private:
  529. explicit ColorStyleValue(Color color)
  530. : StyleValue(Type::Color)
  531. , m_color(color)
  532. {
  533. }
  534. Color m_color;
  535. };
  536. class IdentifierStyleValue final : public StyleValue {
  537. public:
  538. static NonnullRefPtr<IdentifierStyleValue> create(CSS::ValueID id)
  539. {
  540. return adopt_ref(*new IdentifierStyleValue(id));
  541. }
  542. virtual ~IdentifierStyleValue() override { }
  543. CSS::ValueID id() const { return m_id; }
  544. virtual String to_string() const override;
  545. virtual Color to_color(const DOM::Document&) const override;
  546. virtual bool equals(const StyleValue& other) const override
  547. {
  548. if (type() != other.type())
  549. return false;
  550. return m_id == static_cast<const IdentifierStyleValue&>(other).m_id;
  551. }
  552. private:
  553. explicit IdentifierStyleValue(CSS::ValueID id)
  554. : StyleValue(Type::Identifier)
  555. , m_id(id)
  556. {
  557. }
  558. CSS::ValueID m_id { CSS::ValueID::Invalid };
  559. };
  560. class ImageStyleValue final
  561. : public StyleValue
  562. , public ImageResourceClient {
  563. public:
  564. static NonnullRefPtr<ImageStyleValue> create(const AK::URL& url, DOM::Document& document) { return adopt_ref(*new ImageStyleValue(url, document)); }
  565. virtual ~ImageStyleValue() override { }
  566. String to_string() const override { return String::formatted("Image({})", m_url.to_string()); }
  567. const Gfx::Bitmap* bitmap() const { return m_bitmap; }
  568. private:
  569. ImageStyleValue(const AK::URL&, DOM::Document&);
  570. // ^ResourceClient
  571. virtual void resource_did_load() override;
  572. AK::URL m_url;
  573. WeakPtr<DOM::Document> m_document;
  574. RefPtr<Gfx::Bitmap> m_bitmap;
  575. };
  576. class BackgroundStyleValue final : public StyleValue {
  577. public:
  578. static NonnullRefPtr<BackgroundStyleValue> create(
  579. NonnullRefPtr<StyleValue> color,
  580. NonnullRefPtr<StyleValue> image,
  581. NonnullRefPtr<StyleValue> repeat_x,
  582. NonnullRefPtr<StyleValue> repeat_y)
  583. {
  584. return adopt_ref(*new BackgroundStyleValue(color, image, repeat_x, repeat_y));
  585. }
  586. virtual ~BackgroundStyleValue() override { }
  587. NonnullRefPtr<StyleValue> color() const { return m_color; }
  588. NonnullRefPtr<StyleValue> image() const { return m_image; }
  589. NonnullRefPtr<StyleValue> repeat_x() const { return m_repeat_x; }
  590. NonnullRefPtr<StyleValue> repeat_y() const { return m_repeat_y; }
  591. virtual String to_string() const override
  592. {
  593. return String::formatted("{} {} {} {}", m_color->to_string(), m_image->to_string(), m_repeat_x->to_string(), m_repeat_y->to_string());
  594. }
  595. private:
  596. BackgroundStyleValue(
  597. NonnullRefPtr<StyleValue> color,
  598. NonnullRefPtr<StyleValue> image,
  599. NonnullRefPtr<StyleValue> repeat_x,
  600. NonnullRefPtr<StyleValue> repeat_y)
  601. : StyleValue(Type::Background)
  602. , m_color(color)
  603. , m_image(image)
  604. , m_repeat_x(repeat_x)
  605. , m_repeat_y(repeat_y)
  606. {
  607. }
  608. NonnullRefPtr<StyleValue> m_color;
  609. NonnullRefPtr<StyleValue> m_image;
  610. // FIXME: background-position
  611. // FIXME: background-size
  612. NonnullRefPtr<StyleValue> m_repeat_x;
  613. NonnullRefPtr<StyleValue> m_repeat_y;
  614. // FIXME: background-attachment
  615. // FIXME: background-clip
  616. // FIXME: background-origin
  617. };
  618. class BackgroundRepeatStyleValue final : public StyleValue {
  619. public:
  620. static NonnullRefPtr<BackgroundRepeatStyleValue> create(NonnullRefPtr<StyleValue> repeat_x, NonnullRefPtr<StyleValue> repeat_y)
  621. {
  622. return adopt_ref(*new BackgroundRepeatStyleValue(repeat_x, repeat_y));
  623. }
  624. virtual ~BackgroundRepeatStyleValue() override { }
  625. NonnullRefPtr<StyleValue> repeat_x() const { return m_repeat_x; }
  626. NonnullRefPtr<StyleValue> repeat_y() const { return m_repeat_y; }
  627. virtual String to_string() const override
  628. {
  629. return String::formatted("{} {}", m_repeat_x->to_string(), m_repeat_y->to_string());
  630. }
  631. private:
  632. BackgroundRepeatStyleValue(NonnullRefPtr<StyleValue> repeat_x, NonnullRefPtr<StyleValue> repeat_y)
  633. : StyleValue(Type::BackgroundRepeat)
  634. , m_repeat_x(repeat_x)
  635. , m_repeat_y(repeat_y)
  636. {
  637. }
  638. NonnullRefPtr<StyleValue> m_repeat_x;
  639. NonnullRefPtr<StyleValue> m_repeat_y;
  640. };
  641. class BorderStyleValue final : public StyleValue {
  642. public:
  643. static NonnullRefPtr<BorderStyleValue> create(
  644. NonnullRefPtr<StyleValue> border_width,
  645. NonnullRefPtr<StyleValue> border_style,
  646. NonnullRefPtr<StyleValue> border_color)
  647. {
  648. return adopt_ref(*new BorderStyleValue(border_width, border_style, border_color));
  649. }
  650. virtual ~BorderStyleValue() override { }
  651. NonnullRefPtr<StyleValue> border_width() const { return m_border_width; }
  652. NonnullRefPtr<StyleValue> border_style() const { return m_border_style; }
  653. NonnullRefPtr<StyleValue> border_color() const { return m_border_color; }
  654. virtual String to_string() const override
  655. {
  656. return String::formatted("Border border_width: {}, border_style: {}, border_color: {}", m_border_width->to_string(), m_border_style->to_string(), m_border_color->to_string());
  657. }
  658. private:
  659. BorderStyleValue(
  660. NonnullRefPtr<StyleValue> border_width,
  661. NonnullRefPtr<StyleValue> border_style,
  662. NonnullRefPtr<StyleValue> border_color)
  663. : StyleValue(Type::Border)
  664. , m_border_width(border_width)
  665. , m_border_style(border_style)
  666. , m_border_color(border_color)
  667. {
  668. }
  669. NonnullRefPtr<StyleValue> m_border_width;
  670. NonnullRefPtr<StyleValue> m_border_style;
  671. NonnullRefPtr<StyleValue> m_border_color;
  672. };
  673. class BorderRadiusStyleValue final : public StyleValue {
  674. public:
  675. static NonnullRefPtr<BorderRadiusStyleValue> create(Length const& horizontal_radius, Length const& vertical_radius)
  676. {
  677. return adopt_ref(*new BorderRadiusStyleValue(horizontal_radius, vertical_radius));
  678. }
  679. virtual ~BorderRadiusStyleValue() override { }
  680. Length const& horizontal_radius() const { return m_horizontal_radius; }
  681. Length const& vertical_radius() const { return m_vertical_radius; }
  682. bool is_elliptical() const { return m_is_elliptical; }
  683. // FIXME: Remove this once we support elliptical border-radius in Layout/Node.
  684. virtual Length to_length() const override { return horizontal_radius(); }
  685. virtual String to_string() const override
  686. {
  687. return String::formatted("{} / {}", m_horizontal_radius.to_string(), m_vertical_radius.to_string());
  688. }
  689. private:
  690. BorderRadiusStyleValue(Length const& horizontal_radius, Length const& vertical_radius)
  691. : StyleValue(Type::BorderRadius)
  692. , m_horizontal_radius(horizontal_radius)
  693. , m_vertical_radius(vertical_radius)
  694. {
  695. m_is_elliptical = (m_horizontal_radius != m_vertical_radius);
  696. }
  697. bool m_is_elliptical;
  698. Length m_horizontal_radius;
  699. Length m_vertical_radius;
  700. };
  701. class CombinedBorderRadiusStyleValue final : public StyleValue {
  702. public:
  703. static NonnullRefPtr<CombinedBorderRadiusStyleValue> create(NonnullRefPtr<BorderRadiusStyleValue> top_left, NonnullRefPtr<BorderRadiusStyleValue> top_right, NonnullRefPtr<BorderRadiusStyleValue> bottom_right, NonnullRefPtr<BorderRadiusStyleValue> bottom_left)
  704. {
  705. return adopt_ref(*new CombinedBorderRadiusStyleValue(top_left, top_right, bottom_right, bottom_left));
  706. }
  707. virtual ~CombinedBorderRadiusStyleValue() override { }
  708. NonnullRefPtr<BorderRadiusStyleValue> top_left() const { return m_top_left; }
  709. NonnullRefPtr<BorderRadiusStyleValue> top_right() const { return m_top_right; }
  710. NonnullRefPtr<BorderRadiusStyleValue> bottom_right() const { return m_bottom_right; }
  711. NonnullRefPtr<BorderRadiusStyleValue> bottom_left() const { return m_bottom_left; }
  712. virtual String to_string() const override
  713. {
  714. return String::formatted("{} {} {} {} / {} {} {} {}", m_top_left->horizontal_radius().to_string(), m_top_right->horizontal_radius().to_string(), m_bottom_right->horizontal_radius().to_string(), m_bottom_left->horizontal_radius().to_string(), m_top_left->vertical_radius().to_string(), m_top_right->vertical_radius().to_string(), m_bottom_right->vertical_radius().to_string(), m_bottom_left->vertical_radius().to_string());
  715. }
  716. private:
  717. CombinedBorderRadiusStyleValue(NonnullRefPtr<BorderRadiusStyleValue> top_left, NonnullRefPtr<BorderRadiusStyleValue> top_right, NonnullRefPtr<BorderRadiusStyleValue> bottom_right, NonnullRefPtr<BorderRadiusStyleValue> bottom_left)
  718. : StyleValue(Type::CombinedBorderRadius)
  719. , m_top_left(top_left)
  720. , m_top_right(top_right)
  721. , m_bottom_right(bottom_right)
  722. , m_bottom_left(bottom_left)
  723. {
  724. }
  725. NonnullRefPtr<BorderRadiusStyleValue> m_top_left;
  726. NonnullRefPtr<BorderRadiusStyleValue> m_top_right;
  727. NonnullRefPtr<BorderRadiusStyleValue> m_bottom_right;
  728. NonnullRefPtr<BorderRadiusStyleValue> m_bottom_left;
  729. };
  730. class FlexStyleValue final : public StyleValue {
  731. public:
  732. static NonnullRefPtr<FlexStyleValue> create(
  733. NonnullRefPtr<StyleValue> grow,
  734. NonnullRefPtr<StyleValue> shrink,
  735. NonnullRefPtr<StyleValue> basis)
  736. {
  737. return adopt_ref(*new FlexStyleValue(grow, shrink, basis));
  738. }
  739. virtual ~FlexStyleValue() override { }
  740. NonnullRefPtr<StyleValue> grow() const { return m_grow; }
  741. NonnullRefPtr<StyleValue> shrink() const { return m_shrink; }
  742. NonnullRefPtr<StyleValue> basis() const { return m_basis; }
  743. virtual String to_string() const override
  744. {
  745. return String::formatted("Flex grow: {}, shrink: {}, basis: {}", m_grow->to_string(), m_shrink->to_string(), m_basis->to_string());
  746. }
  747. private:
  748. FlexStyleValue(
  749. NonnullRefPtr<StyleValue> grow,
  750. NonnullRefPtr<StyleValue> shrink,
  751. NonnullRefPtr<StyleValue> basis)
  752. : StyleValue(Type::Flex)
  753. , m_grow(grow)
  754. , m_shrink(shrink)
  755. , m_basis(basis)
  756. {
  757. }
  758. NonnullRefPtr<StyleValue> m_grow;
  759. NonnullRefPtr<StyleValue> m_shrink;
  760. NonnullRefPtr<StyleValue> m_basis;
  761. };
  762. class FlexFlowStyleValue final : public StyleValue {
  763. public:
  764. static NonnullRefPtr<FlexFlowStyleValue> create(NonnullRefPtr<StyleValue> flex_direction, NonnullRefPtr<StyleValue> flex_wrap)
  765. {
  766. return adopt_ref(*new FlexFlowStyleValue(flex_direction, flex_wrap));
  767. }
  768. virtual ~FlexFlowStyleValue() override { }
  769. NonnullRefPtr<StyleValue> flex_direction() const { return m_flex_direction; }
  770. NonnullRefPtr<StyleValue> flex_wrap() const { return m_flex_wrap; }
  771. virtual String to_string() const override
  772. {
  773. return String::formatted("FlexFlow flex_direction: {}, flex_wrap: {}", m_flex_direction->to_string(), m_flex_wrap->to_string());
  774. }
  775. private:
  776. FlexFlowStyleValue(NonnullRefPtr<StyleValue> flex_direction, NonnullRefPtr<StyleValue> flex_wrap)
  777. : StyleValue(Type::FlexFlow)
  778. , m_flex_direction(flex_direction)
  779. , m_flex_wrap(flex_wrap)
  780. {
  781. }
  782. NonnullRefPtr<StyleValue> m_flex_direction;
  783. NonnullRefPtr<StyleValue> m_flex_wrap;
  784. };
  785. class FontStyleValue final : public StyleValue {
  786. public:
  787. static NonnullRefPtr<FontStyleValue> create(NonnullRefPtr<StyleValue> font_style, NonnullRefPtr<StyleValue> font_weight, NonnullRefPtr<StyleValue> font_size, NonnullRefPtr<StyleValue> line_height, NonnullRefPtr<StyleValue> font_families) { return adopt_ref(*new FontStyleValue(font_style, font_weight, font_size, line_height, font_families)); }
  788. virtual ~FontStyleValue() override { }
  789. NonnullRefPtr<StyleValue> font_style() const { return m_font_style; }
  790. NonnullRefPtr<StyleValue> font_weight() const { return m_font_weight; }
  791. NonnullRefPtr<StyleValue> font_size() const { return m_font_size; }
  792. NonnullRefPtr<StyleValue> line_height() const { return m_line_height; }
  793. NonnullRefPtr<StyleValue> font_families() const { return m_font_families; }
  794. virtual String to_string() const override
  795. {
  796. return String::formatted("Font style: {}, weight: {}, size: {}, line_height: {}, families: {}",
  797. m_font_style->to_string(), m_font_weight->to_string(), m_font_size->to_string(), m_line_height->to_string(), m_font_families->to_string());
  798. }
  799. private:
  800. FontStyleValue(NonnullRefPtr<StyleValue> font_style, NonnullRefPtr<StyleValue> font_weight, NonnullRefPtr<StyleValue> font_size, NonnullRefPtr<StyleValue> line_height, NonnullRefPtr<StyleValue> font_families)
  801. : StyleValue(Type::Font)
  802. , m_font_style(font_style)
  803. , m_font_weight(font_weight)
  804. , m_font_size(font_size)
  805. , m_line_height(line_height)
  806. , m_font_families(font_families)
  807. {
  808. }
  809. NonnullRefPtr<StyleValue> m_font_style;
  810. NonnullRefPtr<StyleValue> m_font_weight;
  811. NonnullRefPtr<StyleValue> m_font_size;
  812. NonnullRefPtr<StyleValue> m_line_height;
  813. NonnullRefPtr<StyleValue> m_font_families;
  814. // FIXME: Implement font-stretch and font-variant.
  815. };
  816. class ListStyleStyleValue final : public StyleValue {
  817. public:
  818. static NonnullRefPtr<ListStyleStyleValue> create(
  819. NonnullRefPtr<StyleValue> position,
  820. NonnullRefPtr<StyleValue> image,
  821. NonnullRefPtr<StyleValue> style_type)
  822. {
  823. return adopt_ref(*new ListStyleStyleValue(position, image, style_type));
  824. }
  825. virtual ~ListStyleStyleValue() override { }
  826. NonnullRefPtr<StyleValue> position() const { return m_position; }
  827. NonnullRefPtr<StyleValue> image() const { return m_image; }
  828. NonnullRefPtr<StyleValue> style_type() const { return m_style_type; }
  829. virtual String to_string() const override
  830. {
  831. return String::formatted("ListStyle position: {}, image: {}, style_type: {}", m_position->to_string(), m_image->to_string(), m_style_type->to_string());
  832. }
  833. private:
  834. ListStyleStyleValue(
  835. NonnullRefPtr<StyleValue> position,
  836. NonnullRefPtr<StyleValue> image,
  837. NonnullRefPtr<StyleValue> style_type)
  838. : StyleValue(Type::ListStyle)
  839. , m_position(position)
  840. , m_image(image)
  841. , m_style_type(style_type)
  842. {
  843. }
  844. NonnullRefPtr<StyleValue> m_position;
  845. NonnullRefPtr<StyleValue> m_image;
  846. NonnullRefPtr<StyleValue> m_style_type;
  847. };
  848. class OverflowStyleValue final : public StyleValue {
  849. public:
  850. static NonnullRefPtr<OverflowStyleValue> create(NonnullRefPtr<StyleValue> overflow_x, NonnullRefPtr<StyleValue> overflow_y)
  851. {
  852. return adopt_ref(*new OverflowStyleValue(overflow_x, overflow_y));
  853. }
  854. virtual ~OverflowStyleValue() override { }
  855. NonnullRefPtr<StyleValue> overflow_x() const { return m_overflow_x; }
  856. NonnullRefPtr<StyleValue> overflow_y() const { return m_overflow_y; }
  857. virtual String to_string() const override
  858. {
  859. return String::formatted("{} {}", m_overflow_x->to_string(), m_overflow_y->to_string());
  860. }
  861. private:
  862. OverflowStyleValue(NonnullRefPtr<StyleValue> overflow_x, NonnullRefPtr<StyleValue> overflow_y)
  863. : StyleValue(Type::Overflow)
  864. , m_overflow_x(overflow_x)
  865. , m_overflow_y(overflow_y)
  866. {
  867. }
  868. NonnullRefPtr<StyleValue> m_overflow_x;
  869. NonnullRefPtr<StyleValue> m_overflow_y;
  870. };
  871. class TextDecorationStyleValue final : public StyleValue {
  872. public:
  873. static NonnullRefPtr<TextDecorationStyleValue> create(
  874. NonnullRefPtr<StyleValue> line,
  875. NonnullRefPtr<StyleValue> style,
  876. NonnullRefPtr<StyleValue> color)
  877. {
  878. return adopt_ref(*new TextDecorationStyleValue(line, style, color));
  879. }
  880. virtual ~TextDecorationStyleValue() override { }
  881. NonnullRefPtr<StyleValue> line() const { return m_line; }
  882. NonnullRefPtr<StyleValue> style() const { return m_style; }
  883. NonnullRefPtr<StyleValue> color() const { return m_color; }
  884. virtual String to_string() const override
  885. {
  886. return String::formatted("TextDecoration line: {}, style: {}, color: {}", m_line->to_string(), m_style->to_string(), m_color->to_string());
  887. }
  888. private:
  889. TextDecorationStyleValue(
  890. NonnullRefPtr<StyleValue> line,
  891. NonnullRefPtr<StyleValue> style,
  892. NonnullRefPtr<StyleValue> color)
  893. : StyleValue(Type::TextDecoration)
  894. , m_line(line)
  895. , m_style(style)
  896. , m_color(color)
  897. {
  898. }
  899. NonnullRefPtr<StyleValue> m_line;
  900. NonnullRefPtr<StyleValue> m_style;
  901. NonnullRefPtr<StyleValue> m_color;
  902. };
  903. class StyleValueList final : public StyleValue {
  904. public:
  905. static NonnullRefPtr<StyleValueList> create(NonnullRefPtrVector<StyleValue>&& values) { return adopt_ref(*new StyleValueList(move(values))); }
  906. NonnullRefPtrVector<StyleValue> const& values() const { return m_values; }
  907. virtual String to_string() const
  908. {
  909. StringBuilder builder;
  910. builder.appendff("List[{}](", m_values.size());
  911. for (size_t i = 0; i < m_values.size(); ++i) {
  912. if (i)
  913. builder.append(',');
  914. builder.append(m_values[i].to_string());
  915. }
  916. builder.append(')');
  917. return builder.to_string();
  918. }
  919. private:
  920. StyleValueList(NonnullRefPtrVector<StyleValue>&& values)
  921. : StyleValue(Type::ValueList)
  922. , m_values(move(values))
  923. {
  924. }
  925. NonnullRefPtrVector<StyleValue> m_values;
  926. };
  927. inline CSS::ValueID StyleValue::to_identifier() const
  928. {
  929. if (is_identifier())
  930. return static_cast<const IdentifierStyleValue&>(*this).id();
  931. if (is_auto())
  932. return CSS::ValueID::Auto;
  933. return CSS::ValueID::Invalid;
  934. }
  935. }