summaryrefslogtreecommitdiff
path: root/chromium/third_party/blink/renderer/core/resize_observer/resize_observer_entry.cc
blob: 16fd0f2431707b444f3b5326d0f33404b2414930 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
// Copyright 2016 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "third_party/blink/renderer/core/resize_observer/resize_observer_entry.h"
#include "third_party/blink/renderer/core/dom/element.h"
#include "third_party/blink/renderer/core/frame/local_frame.h"
#include "third_party/blink/renderer/core/geometry/dom_rect_read_only.h"
#include "third_party/blink/renderer/core/layout/adjust_for_absolute_zoom.h"
#include "third_party/blink/renderer/core/layout/layout_box.h"
#include "third_party/blink/renderer/core/page/page.h"
#include "third_party/blink/renderer/core/resize_observer/resize_observation.h"
#include "third_party/blink/renderer/core/resize_observer/resize_observer_size.h"
#include "third_party/blink/renderer/core/style/computed_style.h"
#include "third_party/blink/renderer/core/svg/svg_graphics_element.h"
#include "third_party/blink/renderer/platform/geometry/layout_rect.h"
#include "third_party/blink/renderer/platform/geometry/layout_size.h"
#include "third_party/blink/renderer/platform/geometry/layout_unit.h"
#include "third_party/blink/renderer/platform/runtime_enabled_features.h"

namespace blink {

DOMRectReadOnly* ResizeObserverEntry::ZoomAdjustedLayoutRect(
    LayoutRect content_rect,
    const ComputedStyle& style) {
  content_rect.SetX(
      AdjustForAbsoluteZoom::AdjustLayoutUnit(content_rect.X(), style));
  content_rect.SetY(
      AdjustForAbsoluteZoom::AdjustLayoutUnit(content_rect.Y(), style));
  content_rect.SetWidth(
      AdjustForAbsoluteZoom::AdjustLayoutUnit(content_rect.Width(), style));
  content_rect.SetHeight(
      AdjustForAbsoluteZoom::AdjustLayoutUnit(content_rect.Height(), style));

  return DOMRectReadOnly::FromFloatRect(FloatRect(
      FloatPoint(content_rect.Location()), FloatSize(content_rect.Size())));
}

ResizeObserverSize* ResizeObserverEntry::ZoomAdjustedSize(
    const LayoutSize box_size,
    const ComputedStyle& style) {
  return ResizeObserverSize::Create(
      AdjustForAbsoluteZoom::AdjustLayoutUnit(box_size.Width(), style),
      AdjustForAbsoluteZoom::AdjustLayoutUnit(box_size.Height(), style));
}

ResizeObserverEntry::ResizeObserverEntry(Element* target) : target_(target) {
  if (LayoutObject* layout_object = target->GetLayoutObject()) {
    const ComputedStyle& style = layout_object->StyleRef();
    // SVG box properties are always based on bounding box
    if (auto* svg_graphics_element = DynamicTo<SVGGraphicsElement>(target)) {
      LayoutSize bounding_box_size =
          LayoutSize(svg_graphics_element->GetBBox().Size());
      content_rect_ = DOMRectReadOnly::FromFloatRect(
          FloatRect(FloatPoint(), FloatSize(bounding_box_size)));
      if (RuntimeEnabledFeatures::ResizeObserverUpdatesEnabled()) {
        ResizeObserverSize* size = ResizeObserverSize::Create(
            bounding_box_size.Width(), bounding_box_size.Height());
        content_box_size_.push_back(size);
        border_box_size_.push_back(size);
        device_pixel_content_box_size_.push_back(size);
      }
    } else if (layout_object->IsBox()) {
      LayoutBox* layout_box = target->GetLayoutBox();
      LayoutRect content_rect(
          LayoutPoint(layout_box->PaddingLeft(), layout_box->PaddingTop()),
          layout_box->ContentSize());
      content_rect_ = ZoomAdjustedLayoutRect(content_rect, style);

      if (RuntimeEnabledFeatures::ResizeObserverUpdatesEnabled()) {
        LayoutSize content_box_size =
            LayoutSize(layout_box->ContentLogicalWidth(),
                       layout_box->ContentLogicalHeight());
        LayoutSize border_box_size =
            LayoutSize(layout_box->LogicalWidth(), layout_box->LogicalHeight());

        // Get Device Scale Factor for cases where use-zoom-for-dsf is disabled.
        // This is 1 if use-zoom-for-dsf is enabled.
        float device_scale_factor =
            layout_object->GetFrame()->GetPage()->DeviceScaleFactorDeprecated();

        LayoutSize paint_offset =
            layout_object->FirstFragment().PaintOffset().ToLayoutSize();

        ResizeObserverSize* device_pixel_content_box_size =
            ResizeObserverSize::Create(
                SnapSizeToPixel(layout_box->ContentLogicalWidth(),
                                style.IsHorizontalWritingMode()
                                    ? paint_offset.Width()
                                    : paint_offset.Height()) *
                    device_scale_factor,
                SnapSizeToPixel(layout_box->ContentLogicalHeight(),
                                style.IsHorizontalWritingMode()
                                    ? paint_offset.Height()
                                    : paint_offset.Width()) *
                    device_scale_factor);

        content_box_size_.push_back(ZoomAdjustedSize(content_box_size, style));
        border_box_size_.push_back(ZoomAdjustedSize(border_box_size, style));
        device_pixel_content_box_size_.push_back(device_pixel_content_box_size);
      }
    }
  }
  if (!content_rect_)
    content_rect_ = DOMRectReadOnly::FromFloatRect(
        FloatRect(FloatPoint(LayoutPoint()), FloatSize(LayoutSize())));
  if (RuntimeEnabledFeatures::ResizeObserverUpdatesEnabled()) {
    if (content_box_size_.size() == 0)
      content_box_size_.push_back(ResizeObserverSize::Create(0, 0));
    if (border_box_size_.size() == 0)
      border_box_size_.push_back(ResizeObserverSize::Create(0, 0));
    if (device_pixel_content_box_size_.size() == 0) {
      device_pixel_content_box_size_.push_back(
          ResizeObserverSize::Create(0, 0));
    }
  }
}

void ResizeObserverEntry::Trace(Visitor* visitor) const {
  visitor->Trace(target_);
  visitor->Trace(content_rect_);
  visitor->Trace(content_box_size_);
  visitor->Trace(border_box_size_);
  visitor->Trace(device_pixel_content_box_size_);
  ScriptWrappable::Trace(visitor);
}

}  // namespace blink