// Copyright 2014 The Cobalt Authors. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#ifndef COBALT_DOM_HTML_ELEMENT_H_
#define COBALT_DOM_HTML_ELEMENT_H_

#include <memory>
#include <string>
#include <utility>
#include <vector>

#include "base/compiler_specific.h"
#include "base/memory/ref_counted.h"
#include "base/memory/weak_ptr.h"
#include "base/optional.h"
#include "base/strings/string_piece.h"
#include "cobalt/base/token.h"
#include "cobalt/cssom/animation_set.h"
#include "cobalt/cssom/css_computed_style_declaration.h"
#include "cobalt/cssom/css_declared_style_declaration.h"
#include "cobalt/cssom/css_style_declaration.h"
#include "cobalt/cssom/css_style_rule.h"
#include "cobalt/cssom/css_transition_set.h"
#include "cobalt/cssom/mutation_observer.h"
#include "cobalt/cssom/selector_tree.h"
#include "cobalt/cssom/style_sheet_list.h"
#include "cobalt/dom/css_animations_adapter.h"
#include "cobalt/dom/css_transitions_adapter.h"
#include "cobalt/dom/directionality.h"
#include "cobalt/dom/dom_rect_list.h"
#include "cobalt/dom/dom_stat_tracker.h"
#include "cobalt/dom/element.h"
#include "cobalt/dom/layout_boxes.h"
#include "cobalt/dom/pseudo_element.h"
#include "cobalt/loader/image/image_cache.h"
#include "cobalt/ui_navigation/nav_item.h"
#include "starboard/time.h"

namespace cobalt {
namespace dom {

class DOMStringMap;
class HTMLAnchorElement;
class HTMLAudioElement;
class HTMLBodyElement;
class HTMLBRElement;
class HTMLDivElement;
class HTMLElementContext;
class HTMLHeadElement;
class HTMLHeadingElement;
class HTMLHtmlElement;
class HTMLImageElement;
class HTMLLinkElement;
class HTMLMediaElement;
class HTMLMetaElement;
class HTMLParagraphElement;
class HTMLScriptElement;
class HTMLSpanElement;
class HTMLStyleElement;
class HTMLTitleElement;
class HTMLUnknownElement;
class HTMLVideoElement;
class LottiePlayer;

// The enum PseudoElementType is used to track the type of pseudo element
enum PseudoElementType {
  kAfterPseudoElementType,
  kBeforePseudoElementType,
  kMaxPseudoElementType,
  kNotPseudoElementType = kMaxPseudoElementType,
  kMaxAnyElementType,
};

// The basic interface, from which all the HTML elements' interfaces inherit,
// and which must be used by elements that have no additional requirements.
//   https://www.w3.org/TR/html50/dom.html#htmlelement
class HTMLElement : public Element, public cssom::MutationObserver {
 public:
  typedef cssom::SelectorTree::Nodes SelectorTreeNodes;

  // Cached state used with rule matching to minimize the amount of work that
  // must occur during UpdateMatchingRules() when little has changed.
  struct RuleMatchingState {
    RuleMatchingState()
        : is_set(false),
          are_descendant_nodes_dirty(true),
          are_following_sibling_nodes_dirty(true) {}

    // Fully clears the state but does not deallocate the vectors. This allows
    // the vectors to be reused without additional allocations the next time
    // they are needed and speeds up rule matching.
    void Clear();

    // Whether or not the rule matching state is set. When it is not set, the
    // next call to UpdateMatchingRules() always generates new matching rules
    // from the rule matching state.
    bool is_set;

    // The cached node state of the parent and previous sibling. Caching these
    // allows the element to know the exact nodes that have changed and
    // resultantly need to be checked during calls to UpdateMatchingRules().
    SelectorTreeNodes parent_matching_nodes;
    SelectorTreeNodes parent_descendant_nodes;

    SelectorTreeNodes previous_sibling_matching_nodes;
    SelectorTreeNodes previous_sibling_following_sibling_nodes;

    // The element's current matching nodes, along with their parent nodes.
    // These are kept in sync. This allows matching nodes to be removed when
    // their parent nodes are no longer available to the element.
    SelectorTreeNodes matching_nodes_parent_nodes;
    SelectorTreeNodes matching_nodes;

    // The nodes that are to be used by the element's descendants and following
    // siblings during their own rule matching. These are generated by combining
    // the nodes from the element's parent and previous sibling with the
    // element's own matching nodes that contain the required combinator.
    bool are_descendant_nodes_dirty;
    SelectorTreeNodes descendant_nodes;

    bool are_following_sibling_nodes_dirty;
    SelectorTreeNodes following_sibling_nodes;
  };

  enum AncestorsAreDisplayed {
    kAncestorsAreDisplayed,
    kAncestorsAreNotDisplayed,
  };

  // https://html.spec.whatwg.org/commit-snapshots/ebcac971c2add28a911283899da84ec509876c44/#the-dir-attribute
  enum DirState {
    kDirAuto,
    kDirLeftToRight,
    kDirRightToLeft,
    kDirNotDefined,
  };

  // Web API: HTMLElement
  //
  std::string dir() const;
  void set_dir(const std::string& value);

  scoped_refptr<DOMStringMap> dataset();

  int32 tab_index() const;
  void set_tab_index(int32 tab_index);

  void Focus();
  void Blur();

  // Web API: ElementCSSInlineStyle (implements)
  //   https://www.w3.org/TR/2013/WD-cssom-20131205/#elementcssinlinestyle
  const scoped_refptr<cssom::CSSDeclaredStyleDeclaration>& style() {
    return style_;
  }

  // Web API: CSSOM View Module: Extensions to the Element Interface (partial
  // interface)
  //   https://www.w3.org/TR/2013/WD-cssom-view-20131217/#extensions-to-the-element-interface
  scoped_refptr<DOMRectList> GetClientRects() override;
  float client_top() override;
  float client_left() override;
  float client_width() override;
  float client_height() override;

  // Updated version of the CSSOM View Module extensions:
  //   https://www.w3.org/TR/cssom-view-1/#extension-to-the-element-interface
  int32 scroll_width() override;
  int32 scroll_height() override;

  // These attributes are only partially implemented. They will only work with
  // elements associated with UI navigation containers.
  float scroll_left() override;
  float scroll_top() override;
  void set_scroll_left(float x) override;
  void set_scroll_top(float y) override;

  // Web API: CSSOM View Module: Extensions to the HTMLElement Interface
  // (partial interface)
  //   https://www.w3.org/TR/2013/WD-cssom-view-20131217/#extensions-to-the-htmlelement-interface
  Element* offset_parent();
  float offset_top();
  float offset_left();
  float offset_width();
  float offset_height();

  // Custom, not in any spec: Node.
  scoped_refptr<Node> Duplicate() const override;

  // Custom, not in any spec: Element.
  scoped_refptr<HTMLElement> AsHTMLElement() override { return this; }

  base::Optional<std::string> GetStyleAttribute() const override;
  void SetStyleAttribute(const std::string& value) override;
  void RemoveStyleAttribute() override;

  // Custom, not in any spec.
  //
  // From cssom::CSSStyleDeclaration::MutationObserver.
  void OnCSSMutation() override;

  // Safe type conversion methods that will downcast to the required type if
  // possible or return NULL otherwise.
  virtual scoped_refptr<HTMLAnchorElement> AsHTMLAnchorElement();
  virtual scoped_refptr<HTMLAudioElement> AsHTMLAudioElement();
  virtual scoped_refptr<HTMLBodyElement> AsHTMLBodyElement();
  virtual scoped_refptr<HTMLBRElement> AsHTMLBRElement();
  virtual scoped_refptr<HTMLDivElement> AsHTMLDivElement();
  virtual scoped_refptr<HTMLHeadElement> AsHTMLHeadElement();
  virtual scoped_refptr<HTMLHeadingElement> AsHTMLHeadingElement();
  virtual scoped_refptr<HTMLHtmlElement> AsHTMLHtmlElement();
  virtual scoped_refptr<HTMLImageElement> AsHTMLImageElement();
  virtual scoped_refptr<HTMLLinkElement> AsHTMLLinkElement();
  virtual scoped_refptr<HTMLMetaElement> AsHTMLMetaElement();
  virtual scoped_refptr<HTMLMediaElement> AsHTMLMediaElement();
  virtual scoped_refptr<HTMLParagraphElement> AsHTMLParagraphElement();
  virtual scoped_refptr<HTMLScriptElement> AsHTMLScriptElement();
  virtual scoped_refptr<HTMLSpanElement> AsHTMLSpanElement();
  virtual scoped_refptr<HTMLStyleElement> AsHTMLStyleElement();
  virtual scoped_refptr<HTMLTitleElement> AsHTMLTitleElement();
  virtual scoped_refptr<HTMLUnknownElement> AsHTMLUnknownElement();
  virtual scoped_refptr<HTMLVideoElement> AsHTMLVideoElement();
  virtual scoped_refptr<LottiePlayer> AsLottiePlayer();

  // Returns the directionality of the element, which is based upon the
  // element's "dir" attribute if it was set, or that of the parent's if not
  // set.
  //   https://html.spec.whatwg.org/commit-snapshots/ebcac971c2add28a911283899da84ec509876c44/#the-directionality
  Directionality directionality();

  // Retrieve the dir attribute state. This is similar to dir() but returns the
  // enumerated state rather than string.
  DirState dir_state() const { return dir_; }

  // This is similar to dir_state() except it will resolve kDirAuto to
  // kDirLeftToRight or kDirRightToLeft according to the spec:
  //   https://html.spec.whatwg.org/commit-snapshots/ebcac971c2add28a911283899da84ec509876c44/#the-directionality
  // If "dir" was not defined for this element, then this function will return
  // kDirNotDefined.
  virtual DirState GetUsedDirState();

  // Rule matching related methods.
  //
  // Returns the rule matching state of this element.
  RuleMatchingState* rule_matching_state() { return &rule_matching_state_; }

  void ClearRuleMatchingState();
  void ClearRuleMatchingStateOnElementAndAncestors(
      bool invalidate_tree_matching_rules);
  void ClearRuleMatchingStateOnElementAndDescendants();
  void ClearRuleMatchingStateOnElementAndSiblingsAndDescendants();

  // Returns the cached matching rules of this element.
  cssom::RulesWithCascadePrecedence* matching_rules() {
    return &matching_rules_;
  }

  void InvalidateMatchingRulesRecursively();
  void UpdateMatchingRules();
  void UpdateMatchingRulesRecursively();

  void OnMatchingRulesModified();
  void OnPseudoElementMatchingRulesModified();

  // Computed style related methods.
  //
  // Used by layout engine to cache the computed values.
  // See https://www.w3.org/TR/css-cascade-3/#computed for the definition of
  // computed value.
  scoped_refptr<cssom::CSSComputedStyleDeclaration>&
  css_computed_style_declaration() {
    return css_computed_style_declaration_;
  }
  const scoped_refptr<const cssom::CSSComputedStyleData>& computed_style()
      const {
    return css_computed_style_declaration_->data();
  }

  // Updates the cached computed style of this element and its descendants.
  void UpdateComputedStyleRecursively(
      const scoped_refptr<cssom::CSSComputedStyleDeclaration>&
          parent_computed_style,
      const scoped_refptr<const cssom::CSSComputedStyleData>&
          root_computed_style,
      const base::TimeDelta& style_change_event_time, bool ancestors_were_valid,
      int current_element_depth);

  // Updates the cached computed style of this element.
  void UpdateComputedStyle(
      const scoped_refptr<cssom::CSSComputedStyleDeclaration>&
          parent_computed_style_declaration,
      const scoped_refptr<const cssom::CSSComputedStyleData>&
          root_computed_style,
      const base::TimeDelta& style_change_event_time,
      AncestorsAreDisplayed ancestor_is_displayed);

  // Collecting HTML media element.
  void CollectHTMLMediaElementsRecursively(
      std::vector<HTMLMediaElement*>* html_media_elements,
      int current_element_depth);

  void MarkNotDisplayedOnNodeAndDescendants() override;
  void PurgeCachedBackgroundImagesOfNodeAndDescendants() override;
  void InvalidateComputedStylesOfNodeAndDescendants() override;
  void InvalidateLayoutBoxesOfNodeAndAncestors() override;
  void InvalidateLayoutBoxesOfNodeAndDescendants() override;
  void InvalidateLayoutBoxSizes() override;
  void InvalidateLayoutBoxCrossReferences() override;
  void InvalidateLayoutBoxRenderTreeNodes() override;

  // Layout box related methods.
  //
  // The LayoutContainerBox gives the HTML Element an interface to the container
  // box that result from it. The BoxList is set when layout is performed for a
  // node.
  void set_layout_boxes(std::unique_ptr<LayoutBoxes> layout_boxes) {
    layout_boxes_ = std::move(layout_boxes);
  }

  LayoutBoxes* layout_boxes() const { return layout_boxes_.get(); }

  PseudoElement* pseudo_element(PseudoElementType type) const {
    DCHECK(type < kMaxPseudoElementType);
    return pseudo_elements_[type].get();
  }

  void SetPseudoElement(PseudoElementType type,
                        std::unique_ptr<PseudoElement> pseudo_element);

  // Returns true if the element's computed style and all of its pseudo
  // element's computed styles are valid.
  bool AreComputedStylesValid() const;
  bool descendant_computed_styles_valid() const {
    return descendant_computed_styles_valid_;
  }

  bool matching_rules_valid() const { return matching_rules_valid_; }
  void set_matching_rules_valid() { matching_rules_valid_ = true; }

  // Returns whether the element has been designated.
  //   https://www.w3.org/TR/selectors4/#hover-pseudo
  bool IsDesignated() const;

  // Returns whether the element can be designated by a pointer.
  //   https://www.w3.org/TR/SVG11/interact.html#PointerEventsProperty
  bool CanBeDesignatedByPointerIfDisplayed() const;

  // Returns true if this node and all of its ancestors do NOT have display set
  // to 'none'.
  bool IsDisplayed() const;

  // Get the UI navigation item (if any) representing this HTML element.
  const scoped_refptr<ui_navigation::NavItem>& GetUiNavItem() const {
    return ui_nav_item_;
  }

  // Update the UI navigation system to focus on the relevant navigation item
  // for this HTML element (if any).
  void UpdateUiNavigationFocus();

  // Returns true if the element is the root element as defined in
  // https://www.w3.org/TR/html50/semantics.html#the-root-element.
  bool IsRootElement();

  // Returns true if this is a document element.
  // https://dom.spec.whatwg.org/#document-element
  bool IsDocumentElement() const {
    return parent_node() && parent_node()->IsDocument();
  }

  DEFINE_WRAPPABLE_TYPE(HTMLElement);

 protected:
  HTMLElement(Document* document, base::Token local_name);
  ~HTMLElement() override;

  void OnInsertedIntoDocument() override;
  void OnRemovedFromDocument() override;

  // From Element.
  void OnSetAttribute(const std::string& name,
                      const std::string& value) override;
  void OnRemoveAttribute(const std::string& name) override;

    // Create Performance Resource Timing entry for background image.
  void GetLoadTimingInfoAndCreateResourceTiming();

  // HTMLElement keeps a pointer to the dom stat tracker to ensure that it can
  // make stat updates even after its weak pointer to its document has been
  // deleted. This is protected because some derived classes need access to it.
  DomStatTracker* const dom_stat_tracker_;

 private:
  // From Node.
  void OnMutation() override;

  bool IsFocusable();
  bool HasTabindexFocusFlag() const;
  bool IsBeingRendered();

  void RunFocusingSteps();
  void RunUnFocusingSteps();

  // This both updates the 'dir' attribute based upon the string value and
  // invalidates layout box caching if the value has changed.
  void SetDir(const std::string& value);

  // Update the cached value of tabindex.
  void SetTabIndex(const std::string& value);

  // Update cached UI navigation focus duration.
  void SetUiNavFocusDuration(const std::string& value);

  // Invalidate the matching rules and rule matching state in this element and
  // its descendants. In the case where this is the the initial invalidation,
  // it will also invalidate the rule matching state of its siblings.
  void InvalidateMatchingRulesRecursivelyInternal(bool is_initial_element);
  // Fully clear the rule matching state of this element and optionally
  // invalidate all of its descendants matching rules.
  void ClearRuleMatchingStateInternal(bool invalidate_descendants);

  // Update the UI navigation item type for this element.
  void UpdateUiNavigation();
  void ReleaseUiNavigationItem();

  // Clear the list of active background images, and notify the animated image
  // tracker to stop the animations.
  void ClearActiveBackgroundImages();

  void UpdateCachedBackgroundImagesFromComputedStyle();

  // This will be called when the image data associated with this element's
  // computed style's background-image property is loaded.
  void OnBackgroundImageLoaded();

  // Purge the cached background images on only this node.
  void PurgeCachedBackgroundImages();

  // Helper function that hosts the shared code between
  // InvalidateLayoutBoxesOfNodeAndAncestors() and
  // InvalidateLayoutBoxesOfNodeAndDescendants().
  void InvalidateLayoutBoxes();

  // Handle UI navigation events.
  void OnUiNavBlur(SbTimeMonotonic time);
  void OnUiNavFocus(SbTimeMonotonic time);
  void OnUiNavScroll(SbTimeMonotonic time);

  bool locked_for_focus_;

  // This represents the enumerated value of the 'dir' attribute.
  //   https://html.spec.whatwg.org/commit-snapshots/ebcac971c2add28a911283899da84ec509876c44/#the-dir-attribute
  DirState dir_;

  // This represents the computed directionality for this element.
  //   https://html.spec.whatwg.org/commit-snapshots/ebcac971c2add28a911283899da84ec509876c44/#the-directionality
  // NOTE: Cobalt does not support either the CSS 'direction' or 'unicode-bidi'
  // properties, and instead relies entirely upon the 'dir' attribute for
  // determining directionality. Inheritance of directionality occurs via the
  // base direction of the parent element's paragraph.
  base::Optional<Directionality> directionality_;

  // Cache the tabindex value.
  base::Optional<int32> tabindex_;

  // The inline style specified via attribute's in the element's HTML tag, or
  // through JavaScript (accessed via style() defined above).
  scoped_refptr<cssom::CSSDeclaredStyleDeclaration> style_;

  // Keeps track of whether the HTML element's current computed style is out
  // of date or not.
  bool computed_style_valid_;
  // Keeps track of whether the HTML element's pseudo element's computed styles
  // are out of date or not.
  bool pseudo_elements_computed_styles_valid_;
  // Keeps track of whether the HTML element's descendants' computed styles are
  // out of date or not.
  bool descendant_computed_styles_valid_;

  // Indicates whether this node has an ancestor which has display set to none
  // or not. This value gets updated when computed style is updated.
  AncestorsAreDisplayed ancestors_are_displayed_;

  scoped_refptr<cssom::CSSComputedStyleDeclaration>
      css_computed_style_declaration_;

  dom::CSSTransitionsAdapter transitions_adapter_;
  cssom::TransitionSet css_transitions_;

  dom::CSSAnimationsAdapter animations_adapter_;
  cssom::AnimationSet css_animations_;

  // The following fields are used in rule matching.
  RuleMatchingState rule_matching_state_;
  bool matching_rules_valid_;
  cssom::RulesWithCascadePrecedence matching_rules_;

  // This contains information about the boxes generated from the element.
  std::unique_ptr<LayoutBoxes> layout_boxes_;

  std::unique_ptr<PseudoElement> pseudo_elements_[kMaxPseudoElementType];
  base::WeakPtr<DOMStringMap> dataset_;

  std::vector<GURL> active_background_images_;

  // |cached_background_images_| contains a list of CachedImage references for
  // all images referenced by the computed value for the background_image CSS
  // property and a image loaded handle to add and remove image loaded callback.
  // We maintain it here to indicate to the resource caching system
  // that the images are currently in-use, and should not be purged.
  loader::image::CachedImageReferenceVector cached_background_images_;

  // Elements with specific styles or attributes can be animated by the
  // platform's UI engine. This is done by attaching special animation nodes to
  // the boxes generated for the relevant elements; the rendering pipeline will
  // then query starboard for position data each frame, thus animating the
  // boxes without requiring a new layout.
  scoped_refptr<ui_navigation::NavItem> ui_nav_item_;

  // Specify how long focus should remain on this navigation item once it
  // becomes focused.
  base::Optional<float> ui_nav_focus_duration_;

  // Signal whether the UI navigation item may need to be updated.
  bool ui_nav_needs_update_ = false;

  // HTMLElement is a friend of Animatable so that animatable can insert and
  // remove animations into HTMLElement's set of animations.
  friend class DOMAnimatable;
};

}  // namespace dom
}  // namespace cobalt

#endif  // COBALT_DOM_HTML_ELEMENT_H_
