Bug 1409083 Part 2: Stub webidl definitions to support flex container/item properties. draft
authorBrad Werth <bwerth@mozilla.com>
Wed, 15 Nov 2017 13:20:35 -0800
changeset 710141 4a5d0b1920bc1fd06fd8bc7f8e431ceb921383e6
parent 710140 fa07c3e741aec19b2e148cf1b0826116ab225720
child 710142 49a7d68e3522d466e475c0c73a30abaa4c894d01
push id92753
push userbwerth@mozilla.com
push dateFri, 08 Dec 2017 18:49:19 +0000
bugs1409083
milestone59.0a1
Bug 1409083 Part 2: Stub webidl definitions to support flex container/item properties. MozReview-Commit-ID: KwNykBkJfPi
dom/base/Element.cpp
dom/base/Element.h
dom/flex/Flex.cpp
dom/flex/Flex.h
dom/flex/FlexItem.cpp
dom/flex/FlexItem.h
dom/flex/FlexLine.cpp
dom/flex/FlexLine.h
dom/flex/moz.build
dom/moz.build
dom/webidl/Element.webidl
dom/webidl/Flex.webidl
dom/webidl/moz.build
--- a/dom/base/Element.cpp
+++ b/dom/base/Element.cpp
@@ -11,27 +11,29 @@
  */
 
 #include "mozilla/dom/ElementInlines.h"
 
 #include "AnimationCommon.h"
 #include "mozilla/DebugOnly.h"
 #include "mozilla/dom/Animation.h"
 #include "mozilla/dom/Attr.h"
+#include "mozilla/dom/Flex.h"
 #include "mozilla/dom/Grid.h"
 #include "mozilla/gfx/Matrix.h"
 #include "nsDOMAttributeMap.h"
 #include "nsAtom.h"
 #include "nsIContentInlines.h"
 #include "mozilla/dom/NodeInfo.h"
 #include "nsIDocumentInlines.h"
 #include "mozilla/dom/DocumentTimeline.h"
 #include "nsIDOMNodeList.h"
 #include "nsIDOMDocument.h"
 #include "nsIContentIterator.h"
+#include "nsFlexContainerFrame.h"
 #include "nsFocusManager.h"
 #include "nsFrameManager.h"
 #include "nsILinkHandler.h"
 #include "nsIScriptGlobalObject.h"
 #include "nsIURL.h"
 #include "nsContainerFrame.h"
 #include "nsIAnonymousContentCreator.h"
 #include "nsIPresShell.h"
@@ -3702,16 +3704,33 @@ Element::RequestFullscreen(CallerType aC
 }
 
 void
 Element::RequestPointerLock(CallerType aCallerType)
 {
   OwnerDoc()->RequestPointerLock(this, aCallerType);
 }
 
+already_AddRefed<Flex>
+Element::GetAsFlexContainer()
+{
+  nsIFrame* frame = GetPrimaryFrame();
+
+  // We need the flex frame to compute additional info, and use
+  // that annotated version of the frame.
+  nsFlexContainerFrame* flexFrame =
+    nsFlexContainerFrame::GetFlexFrameWithComputedInfo(frame);
+
+  if (flexFrame) {
+    RefPtr<Flex> flex = new Flex(this, flexFrame);
+    return flex.forget();
+  }
+  return nullptr;
+}
+
 void
 Element::GetGridFragments(nsTArray<RefPtr<Grid>>& aResult)
 {
   nsGridContainerFrame* frame =
     nsGridContainerFrame::GetGridFrameWithComputedInfo(GetPrimaryFrame());
 
   // If we get a nsGridContainerFrame from the prior call,
   // all the next-in-flow frames will also be nsGridContainerFrames.
--- a/dom/base/Element.h
+++ b/dom/base/Element.h
@@ -184,16 +184,17 @@ class EventStateManager;
 namespace dom {
 
 class Animation;
 class CustomElementRegistry;
 class Link;
 class DOMRect;
 class DOMRectList;
 class DestinationInsertionPointList;
+class Flex;
 class Grid;
 
 // IID for the dom::Element interface
 #define NS_ELEMENT_IID \
 { 0xc67ed254, 0xfd3b, 0x4b10, \
   { 0x96, 0xa2, 0xc5, 0x8b, 0x7b, 0x64, 0x97, 0xd1 } }
 
 class Element : public FragmentOrElement
@@ -1303,16 +1304,17 @@ public:
   MOZ_CAN_RUN_SCRIPT int32_t ScrollLeftMax()
   {
     nsIScrollableFrame* sf = GetScrollFrame();
     return sf ?
            nsPresContext::AppUnitsToIntCSSPixels(sf->GetScrollRange().XMost()) :
            0;
   }
 
+  already_AddRefed<Flex> GetAsFlexContainer();
   void GetGridFragments(nsTArray<RefPtr<Grid>>& aResult);
 
   already_AddRefed<DOMMatrixReadOnly> GetTransformToAncestor(Element& aAncestor);
   already_AddRefed<DOMMatrixReadOnly> GetTransformToParent();
   already_AddRefed<DOMMatrixReadOnly> GetTransformToViewport();
 
   already_AddRefed<Animation>
   Animate(JSContext* aContext,
new file mode 100644
--- /dev/null
+++ b/dom/flex/Flex.cpp
@@ -0,0 +1,47 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#include "Flex.h"
+
+#include "FlexLine.h"
+#include "mozilla/dom/FlexBinding.h"
+#include "nsFlexContainerFrame.h"
+
+namespace mozilla {
+namespace dom {
+
+NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(Flex, mParent, mLines)
+NS_IMPL_CYCLE_COLLECTING_ADDREF(Flex)
+NS_IMPL_CYCLE_COLLECTING_RELEASE(Flex)
+NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(Flex)
+  NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
+  NS_INTERFACE_MAP_ENTRY(nsISupports)
+NS_INTERFACE_MAP_END
+
+Flex::Flex(Element* aParent,
+           nsFlexContainerFrame* aFrame)
+  : mParent(aParent)
+{
+  MOZ_ASSERT(aFrame,
+    "Should never be instantiated with a null nsFlexContainerFrame");
+
+  // Eagerly create mLines.
+}
+
+JSObject*
+Flex::WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto)
+{
+  return FlexBinding::Wrap(aCx, this, aGivenProto);
+}
+
+void
+Flex::GetLines(nsTArray<RefPtr<FlexLine>>& aResult)
+{
+  aResult.AppendElements(mLines);
+}
+
+} // namespace dom
+} // namespace mozilla
new file mode 100644
--- /dev/null
+++ b/dom/flex/Flex.h
@@ -0,0 +1,50 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#ifndef mozilla_dom_Flex_h
+#define mozilla_dom_Flex_h
+
+#include "mozilla/dom/Element.h"
+#include "nsISupports.h"
+#include "nsWrapperCache.h"
+
+class nsFlexContainerFrame;
+
+namespace mozilla {
+namespace dom {
+
+class FlexLine;
+
+class Flex : public nsISupports
+           , public nsWrapperCache
+{
+public:
+  explicit Flex(Element* aParent, nsFlexContainerFrame* aFrame);
+
+protected:
+  virtual ~Flex() = default;
+
+public:
+  NS_DECL_CYCLE_COLLECTING_ISUPPORTS
+  NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(Flex)
+
+  virtual JSObject* WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override;
+  Element* GetParentObject()
+  {
+    return mParent;
+  }
+
+  void GetLines(nsTArray<RefPtr<FlexLine>>& aResult);
+
+protected:
+  nsCOMPtr<Element> mParent;
+  nsTArray<RefPtr<FlexLine>> mLines;
+};
+
+} // namespace dom
+} // namespace mozilla
+
+#endif /* mozilla_dom_Flex_h */
new file mode 100644
--- /dev/null
+++ b/dom/flex/FlexItem.cpp
@@ -0,0 +1,76 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#include "FlexItem.h"
+
+#include "mozilla/dom/FlexBinding.h"
+
+namespace mozilla {
+namespace dom {
+
+NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(FlexItem, mParent)
+NS_IMPL_CYCLE_COLLECTING_ADDREF(FlexItem)
+NS_IMPL_CYCLE_COLLECTING_RELEASE(FlexItem)
+NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(FlexItem)
+  NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
+  NS_INTERFACE_MAP_ENTRY(nsISupports)
+NS_INTERFACE_MAP_END
+
+FlexItem::FlexItem(FlexLine* aParent)
+  : mParent(aParent)
+{
+}
+
+JSObject*
+FlexItem::WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto)
+{
+  return FlexItemBinding::Wrap(aCx, this, aGivenProto);
+}
+
+nsINode*
+FlexItem::GetNode() const
+{
+  return nullptr;
+}
+
+double
+FlexItem::MainBaseSize() const
+{
+  return 0;
+}
+
+double
+FlexItem::MainDeltaSize() const
+{
+  return 0;
+}
+
+double
+FlexItem::MainMinSize() const
+{
+  return 0;
+}
+
+double
+FlexItem::MainMaxSize() const
+{
+  return 0;
+}
+
+double
+FlexItem::CrossMinSize() const
+{
+  return 0;
+}
+
+double
+FlexItem::CrossMaxSize() const
+{
+  return 0;
+}
+
+} // namespace dom
+} // namespace mozilla
new file mode 100644
--- /dev/null
+++ b/dom/flex/FlexItem.h
@@ -0,0 +1,53 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#ifndef mozilla_dom_FlexItem_h
+#define mozilla_dom_FlexItem_h
+
+#include "mozilla/dom/FlexBinding.h"
+#include "nsISupports.h"
+#include "nsWrapperCache.h"
+
+namespace mozilla {
+namespace dom {
+
+class FlexLine;
+
+class FlexItem : public nsISupports
+               , public nsWrapperCache
+{
+public:
+  explicit FlexItem(FlexLine* aParent);
+
+protected:
+  virtual ~FlexItem() = default;
+
+public:
+  NS_DECL_CYCLE_COLLECTING_ISUPPORTS
+  NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(FlexItem)
+
+  virtual JSObject* WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override;
+  FlexLine* GetParentObject()
+  {
+    return mParent;
+  }
+
+  nsINode* GetNode() const;
+  double MainBaseSize() const;
+  double MainDeltaSize() const;
+  double MainMinSize() const;
+  double MainMaxSize() const;
+  double CrossMinSize() const;
+  double CrossMaxSize() const;
+
+protected:
+  RefPtr<FlexLine> mParent;
+};
+
+} // namespace dom
+} // namespace mozilla
+
+#endif /* mozilla_dom_FlexItem_h */
new file mode 100644
--- /dev/null
+++ b/dom/flex/FlexLine.cpp
@@ -0,0 +1,65 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#include "FlexLine.h"
+
+#include "FlexItem.h"
+#include "mozilla/dom/FlexBinding.h"
+
+namespace mozilla {
+namespace dom {
+
+NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(FlexLine, mParent, mItems)
+NS_IMPL_CYCLE_COLLECTING_ADDREF(FlexLine)
+NS_IMPL_CYCLE_COLLECTING_RELEASE(FlexLine)
+NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(FlexLine)
+  NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
+  NS_INTERFACE_MAP_ENTRY(nsISupports)
+NS_INTERFACE_MAP_END
+
+FlexLine::FlexLine(Flex* aParent)
+  : mParent(aParent)
+{
+}
+
+JSObject*
+FlexLine::WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto)
+{
+  return FlexLineBinding::Wrap(aCx, this, aGivenProto);
+}
+
+FlexLineGrowthState
+FlexLine::GrowthState() const
+{
+  return FlexLineGrowthState::Unchanged;
+}
+
+double
+FlexLine::CrossSize() const
+{
+  return 0;
+}
+
+double
+FlexLine::FirstBaselineOffset() const
+{
+  return 0;
+}
+
+double
+FlexLine::LastBaselineOffset() const
+{
+  return 0;
+}
+
+void
+FlexLine::GetItems(nsTArray<RefPtr<FlexItem>>& aResult)
+{
+  aResult.AppendElements(mItems);
+}
+
+} // namespace dom
+} // namespace mozilla
new file mode 100644
--- /dev/null
+++ b/dom/flex/FlexLine.h
@@ -0,0 +1,54 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set ts=8 sts=2 et sw=2 tw=80: */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#ifndef mozilla_dom_FlexLine_h
+#define mozilla_dom_FlexLine_h
+
+#include "mozilla/dom/FlexBinding.h"
+#include "nsISupports.h"
+#include "nsWrapperCache.h"
+
+namespace mozilla {
+namespace dom {
+
+class Flex;
+class FlexItem;
+
+class FlexLine : public nsISupports
+               , public nsWrapperCache
+{
+public:
+  explicit FlexLine(Flex* aParent);
+
+protected:
+  virtual ~FlexLine() = default;
+
+public:
+  NS_DECL_CYCLE_COLLECTING_ISUPPORTS
+  NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(FlexLine)
+
+  virtual JSObject* WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override;
+  Flex* GetParentObject()
+  {
+    return mParent;
+  }
+
+  FlexLineGrowthState GrowthState() const;
+  double CrossSize() const;
+  double FirstBaselineOffset() const;
+  double LastBaselineOffset() const;
+
+  void GetItems(nsTArray<RefPtr<FlexItem>>& aResult);
+
+protected:
+  RefPtr<Flex> mParent;
+  nsTArray<RefPtr<FlexItem>> mItems;
+};
+
+} // namespace dom
+} // namespace mozilla
+
+#endif /* mozilla_dom_FlexLine_h */
new file mode 100644
--- /dev/null
+++ b/dom/flex/moz.build
@@ -0,0 +1,26 @@
+# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
+# vim: set filetype=python:
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+with Files("**"):
+    BUG_COMPONENT = ("Core", "CSS Parsing and Computation")
+
+EXPORTS.mozilla.dom += [
+    'Flex.h',
+    'FlexItem.h',
+    'FlexLine.h',
+]
+
+UNIFIED_SOURCES += [
+    'Flex.cpp',
+    'FlexItem.cpp',
+    'FlexLine.cpp',
+]
+
+LOCAL_INCLUDES += [
+    '/layout/generic',
+]
+
+FINAL_LIBRARY = 'xul'
--- a/dom/moz.build
+++ b/dom/moz.build
@@ -54,16 +54,17 @@ DIRS += [
     'credentialmanagement',
     'crypto',
     'encoding',
     'events',
     'fetch',
     'file',
     'filehandle',
     'filesystem',
+    'flex',
     'gamepad',
     'geolocation',
     'grid',
     'html',
     'jsurl',
     'asmjscache',
     'mathml',
     'media',
--- a/dom/webidl/Element.webidl
+++ b/dom/webidl/Element.webidl
@@ -114,17 +114,17 @@ interface Element : Node {
 
   // Proprietary extensions
   /**
    * Set this during a mousedown event to grab and retarget all mouse events
    * to this element until the mouse button is released or releaseCapture is
    * called. If retargetToElement is true, then all events are targetted at
    * this element. If false, events can also fire at descendants of this
    * element.
-   * 
+   *
    */
   void setCapture(optional boolean retargetToElement = false);
 
   /**
    * If this element has captured the mouse, release the capture. If another
    * element has captured the mouse, this method has no effect.
    */
   void releaseCapture();
@@ -149,18 +149,27 @@ interface Element : Node {
 
   [ChromeOnly]
   /**
    * Scrolls the element by (dx, dy) CSS pixels without doing any
    * layout flushing.
    */
   boolean scrollByNoFlush(long dx, long dy);
 
+  // Support reporting of Flexbox properties
+  /**
+   * If this element has a display:flex or display:inline-flex style,
+   * this property returns an object with computed values for flex
+   * properties, as well as a property that exposes the flex lines
+   * in this container.
+   */
+  [ChromeOnly, Pure]
+  Flex? getAsFlexContainer();
+
   // Support reporting of Grid properties
-
   /**
    * If this element has a display:grid or display:inline-grid style,
    * this property returns an object with computed values for grid
    * tracks and lines.
    */
   [ChromeOnly, Pure]
   sequence<Grid> getGridFragments();
 
@@ -186,17 +195,17 @@ partial interface Element {
 
   // scrolling
   void scrollIntoView(optional (boolean or ScrollIntoViewOptions) arg);
   // None of the CSSOM attributes are [Pure], because they flush
            attribute long scrollTop;   // scroll on setting
            attribute long scrollLeft;  // scroll on setting
   readonly attribute long scrollWidth;
   readonly attribute long scrollHeight;
-  
+
   void scroll(unrestricted double x, unrestricted double y);
   void scroll(optional ScrollToOptions options);
   void scrollTo(unrestricted double x, unrestricted double y);
   void scrollTo(optional ScrollToOptions options);
   void scrollBy(unrestricted double x, unrestricted double y);
   void scrollBy(optional ScrollToOptions options);
   // mozScrollSnap is used by chrome to perform scroll snapping after the
   // user performs actions that may affect scroll position
new file mode 100644
--- /dev/null
+++ b/dom/webidl/Flex.webidl
@@ -0,0 +1,53 @@
+/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this file,
+ * You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+/**
+ * These objects support visualization of flex containers by the
+ * dev tools.
+ */
+
+[ChromeOnly]
+interface Flex
+{
+  sequence<FlexLine> getLines();
+};
+
+/**
+ * Lines with items that have been shrunk are shrinking; with items
+ * that have grown are growing, and all others are unchanged.
+ */
+enum FlexLineGrowthState { "unchanged", "shrinking", "growing" };
+
+[ChromeOnly]
+interface FlexLine
+{
+  readonly attribute FlexLineGrowthState growthState;
+  readonly attribute double crossSize;
+
+  // firstBaselineOffset measures from flex-start edge.
+  readonly attribute double firstBaselineOffset;
+
+  // lastBaselineOffset measures from flex-end edge.
+  readonly attribute double lastBaselineOffset;
+
+  /**
+   * getItems() returns FlexItems only for the Elements in this Flex
+   * container -- ignoring struts and abs-pos Elements.
+   */
+  sequence<FlexItem> getItems();
+};
+
+[ChromeOnly]
+interface FlexItem
+{
+  readonly attribute Node? node;
+  readonly attribute double mainBaseSize;
+  readonly attribute double mainDeltaSize;
+  readonly attribute double mainMinSize;
+  readonly attribute double mainMaxSize;
+  readonly attribute double crossMinSize;
+  readonly attribute double crossMaxSize;
+};
--- a/dom/webidl/moz.build
+++ b/dom/webidl/moz.build
@@ -98,16 +98,19 @@ with Files("DynamicsCompressorNode.webid
     BUG_COMPONENT = ("Core", "Web Audio")
 
 with Files("DesktopNotification.webidl"):
     BUG_COMPONENT = ("Toolkit", "Notifications and Alerts")
 
 with Files("FakePluginTagInit.webidl"):
     BUG_COMPONENT = ("Core", "Plug-ins")
 
+with Files("Flex.webidl"):
+    BUG_COMPONENT = ("Core", "CSS Parsing and Computation")
+
 with Files("FocusEvent.webidl"):
     BUG_COMPONENT = ("Core", "DOM: Events")
 
 with Files("Font*"):
     BUG_COMPONENT = ("Core", "CSS Parsing and Computation")
 
 with Files("FormData.webidl"):
     BUG_COMPONENT = ("Core", "DOM: Core & HTML")
@@ -519,16 +522,17 @@ WEBIDL_FILES = [
     'FileMode.webidl',
     'FileReader.webidl',
     'FileReaderSync.webidl',
     'FileSystem.webidl',
     'FileSystemDirectoryEntry.webidl',
     'FileSystemDirectoryReader.webidl',
     'FileSystemEntry.webidl',
     'FileSystemFileEntry.webidl',
+    'Flex.webidl',
     'FocusEvent.webidl',
     'FontFace.webidl',
     'FontFaceSet.webidl',
     'FontFaceSource.webidl',
     'FormData.webidl',
     'FrameLoader.webidl',
     'Function.webidl',
     'GainNode.webidl',