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
|
// Copyright 2013 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 "cc/pinch_zoom_viewport.h"
#include "base/logging.h"
namespace cc {
PinchZoomViewport::PinchZoomViewport()
: page_scale_factor_(1),
page_scale_delta_(1),
sent_page_scale_delta_(1),
min_page_scale_factor_(0),
max_page_scale_factor_(0),
device_scale_factor_(1) {
}
void PinchZoomViewport::set_page_scale_delta(float delta) {
// Clamp to the current min/max limits.
float totalPageScaleFactor = page_scale_factor_ * delta;
if (min_page_scale_factor_ && totalPageScaleFactor < min_page_scale_factor_)
delta = min_page_scale_factor_ / page_scale_factor_;
else if (max_page_scale_factor_ &&
totalPageScaleFactor > max_page_scale_factor_)
delta = max_page_scale_factor_ / page_scale_factor_;
if (delta == page_scale_delta_)
return;
page_scale_delta_ = delta;
}
bool PinchZoomViewport::SetPageScaleFactorAndLimits(
float page_scale_factor,
float min_page_scale_factor,
float max_page_scale_factor) {
DCHECK(page_scale_factor);
if (sent_page_scale_delta_ == 1 && page_scale_factor == page_scale_factor_ &&
min_page_scale_factor == min_page_scale_factor_ &&
max_page_scale_factor == max_page_scale_factor_)
return false;
min_page_scale_factor_ = min_page_scale_factor;
max_page_scale_factor_ = max_page_scale_factor;
page_scale_factor_ = page_scale_factor;
return true;
}
gfx::RectF PinchZoomViewport::ZoomedViewport() const {
gfx::SizeF layout_space_device_viewport_size = gfx::ScaleSize(
device_viewport_size_,
1 / (device_scale_factor_ * total_page_scale_factor()));
return gfx::RectF(gfx::PointAtOffsetFromOrigin(zoomed_viewport_offset_),
layout_space_device_viewport_size);
}
gfx::Vector2dF PinchZoomViewport::ApplyScroll(const gfx::Vector2dF delta) {
gfx::Vector2dF overflow;
gfx::RectF pinched_bounds = ZoomedViewport() + delta;
if (pinched_bounds.x() < 0) {
overflow.set_x(pinched_bounds.x());
pinched_bounds.set_x(0);
}
if (pinched_bounds.y() < 0) {
overflow.set_y(pinched_bounds.y());
pinched_bounds.set_y(0);
}
if (pinched_bounds.right() > layout_viewport_size_.width()) {
overflow.set_x(pinched_bounds.right() - layout_viewport_size_.width());
pinched_bounds += gfx::Vector2dF(
layout_viewport_size_.width() - pinched_bounds.right(), 0);
}
if (pinched_bounds.bottom() > layout_viewport_size_.height()) {
overflow.set_y(pinched_bounds.bottom() - layout_viewport_size_.height());
pinched_bounds += gfx::Vector2dF(
0, layout_viewport_size_.height() - pinched_bounds.bottom());
}
zoomed_viewport_offset_ = pinched_bounds.OffsetFromOrigin();
return overflow;
}
gfx::Transform PinchZoomViewport::ImplTransform(
bool page_scale_pinch_zoom_enabled) const {
gfx::Transform transform;
transform.Scale(page_scale_delta_, page_scale_delta_);
// If the pinch state is applied in the impl, then push it to the
// impl transform, otherwise the scale is handled by WebCore.
if (page_scale_pinch_zoom_enabled) {
transform.Scale(page_scale_factor_, page_scale_factor_);
// The offset needs to be scaled by deviceScaleFactor as this transform
// needs to work with physical pixels.
gfx::Vector2dF zoomed_device_viewport_offset
= gfx::ScaleVector2d(zoomed_viewport_offset_, device_scale_factor_);
transform.Translate(-zoomed_device_viewport_offset.x(),
-zoomed_device_viewport_offset.y());
}
return transform;
}
} // namespace cc
|