OLD | NEW |
(Empty) | |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. |
| 4 |
| 5 #include "config.h" |
| 6 #include "ScreenOrientation.h" |
| 7 |
| 8 #include "core/frame/Frame.h" |
| 9 #include "core/frame/Screen.h" |
| 10 #include "core/page/ChromeClient.h" |
| 11 #include "modules/screen_orientation/ScreenOrientationClient.h" |
| 12 #include "modules/screen_orientation/ScreenOrientationController.h" |
| 13 |
| 14 namespace WebCore { |
| 15 |
| 16 ScreenOrientation::ScreenOrientation(Screen* screen) |
| 17 : DOMWindowProperty(screen->frame()) |
| 18 , PageLifecycleObserver(page()) |
| 19 , ActiveDOMObject(frame() ? frame()->document() : 0) |
| 20 , m_screen(screen) |
| 21 , m_orientationLockTimer(this, &ScreenOrientation::orientationLockTimerFired
) |
| 22 , m_lockedOrientations(OrientationAny) |
| 23 { |
| 24 ScreenOrientationController* controller = ScreenOrientationController::from(
page()); |
| 25 if (controller) |
| 26 controller->addObserver(this); |
| 27 } |
| 28 |
| 29 ScreenOrientation::~ScreenOrientation() |
| 30 { |
| 31 } |
| 32 |
| 33 const char* ScreenOrientation::supplementName() |
| 34 { |
| 35 return "ScreenOrientation"; |
| 36 } |
| 37 |
| 38 void ScreenOrientation::orientationLockTimerFired(Timer<ScreenOrientation>*) |
| 39 { |
| 40 ScreenOrientationClient* client = ScreenOrientationController::clientFrom(pa
ge()); |
| 41 if (!client) |
| 42 return; |
| 43 |
| 44 client->lockOrientation(m_lockedOrientations); |
| 45 } |
| 46 |
| 47 void ScreenOrientation::didCommitLoad(Frame*) |
| 48 { |
| 49 // New page loaded, unlock screen orientation. |
| 50 unlockOrientation(); |
| 51 } |
| 52 |
| 53 void ScreenOrientation::willDestroyGlobalObjectInFrame() |
| 54 { |
| 55 m_screen = 0; |
| 56 DOMWindowProperty::willDestroyGlobalObjectInFrame(); |
| 57 } |
| 58 |
| 59 void ScreenOrientation::willDetachGlobalObjectFromFrame() |
| 60 { |
| 61 m_screen = 0; |
| 62 DOMWindowProperty::willDetachGlobalObjectFromFrame(); |
| 63 } |
| 64 |
| 65 void ScreenOrientation::stop() |
| 66 { |
| 67 ScreenOrientationController* controller = ScreenOrientationController::from(
page()); |
| 68 if (controller) |
| 69 controller->removeObserver(this); |
| 70 } |
| 71 |
| 72 Page* ScreenOrientation::page() const |
| 73 { |
| 74 return frame() ? frame()->page() : 0; |
| 75 } |
| 76 |
| 77 ScreenOrientation* ScreenOrientation::from(Screen* screen) |
| 78 { |
| 79 ScreenOrientation* supplement = static_cast<ScreenOrientation*>(Supplement<S
creen>::from(screen, supplementName())); |
| 80 if (!supplement) { |
| 81 ASSERT(screen); |
| 82 supplement = new ScreenOrientation(screen); |
| 83 supplement->suspendIfNeeded(); |
| 84 provideTo(screen, supplementName(), adoptPtr(supplement)); |
| 85 } |
| 86 return supplement; |
| 87 } |
| 88 |
| 89 struct ScreenOrientationInfo { |
| 90 const AtomicString& name; |
| 91 ScreenOrientationValues orientation; |
| 92 }; |
| 93 |
| 94 static ScreenOrientationInfo* allowedOrientationsMap(unsigned& length) |
| 95 { |
| 96 DEFINE_STATIC_LOCAL(const AtomicString, portrait, ("portrait", AtomicString:
:ConstructFromLiteral)); |
| 97 DEFINE_STATIC_LOCAL(const AtomicString, portraitPrimary, ("portrait-primary"
, AtomicString::ConstructFromLiteral)); |
| 98 DEFINE_STATIC_LOCAL(const AtomicString, portraitSecondary, ("portrait-second
ary", AtomicString::ConstructFromLiteral)); |
| 99 DEFINE_STATIC_LOCAL(const AtomicString, landscape, ("landscape", AtomicStrin
g::ConstructFromLiteral)); |
| 100 DEFINE_STATIC_LOCAL(const AtomicString, landscapePrimary, ("landscape-primar
y", AtomicString::ConstructFromLiteral)); |
| 101 DEFINE_STATIC_LOCAL(const AtomicString, landscapeSecondary, ("landscape-seco
ndary", AtomicString::ConstructFromLiteral)); |
| 102 |
| 103 static ScreenOrientationInfo orientationMap[] = { |
| 104 { portrait, OrientationPortrait }, |
| 105 { portraitPrimary, OrientationPortraitPrimary }, |
| 106 { portraitSecondary, OrientationPortraitSecondary }, |
| 107 { landscape, OrientationLandscape }, |
| 108 { landscapePrimary, OrientationLandscapePrimary }, |
| 109 { landscapeSecondary, OrientationLandscapeSecondary } |
| 110 }; |
| 111 length = WTF_ARRAY_LENGTH(orientationMap); |
| 112 return orientationMap; |
| 113 } |
| 114 |
| 115 const AtomicString& ScreenOrientation::orientationToString(ScreenOrientationValu
e orientation) |
| 116 { |
| 117 unsigned length = 0; |
| 118 ScreenOrientationInfo* orientationMap = allowedOrientationsMap(length); |
| 119 for (unsigned i = 0; i < length; ++i) { |
| 120 if (orientationMap[i].orientation == orientation) |
| 121 return orientationMap[i].name; |
| 122 } |
| 123 // We do no handle OrientationInvalid and OrientationAny but this is fine be
cause screen.orientation |
| 124 // should never return these and WebScreenOrientation does not define those
values. |
| 125 ASSERT_NOT_REACHED(); |
| 126 return nullAtom; |
| 127 } |
| 128 |
| 129 ScreenOrientationValues ScreenOrientation::stringToOrientationValues(const Atomi
cString& orientation) |
| 130 { |
| 131 unsigned length = 0; |
| 132 ScreenOrientationInfo* orientationMap = allowedOrientationsMap(length); |
| 133 for (unsigned i = 0; i < length; ++i) { |
| 134 if (orientationMap[i].name == orientation) |
| 135 return orientationMap[i].orientation; |
| 136 } |
| 137 return OrientationInvalid; |
| 138 } |
| 139 |
| 140 const AtomicString& ScreenOrientation::orientation(Screen* screen) |
| 141 { |
| 142 ScreenOrientation* screenOrientation = ScreenOrientation::from(screen); |
| 143 ASSERT(screenOrientation); |
| 144 |
| 145 ScreenOrientationController* controller = ScreenOrientationController::from(
screenOrientation->page()); |
| 146 if (!controller) |
| 147 return orientationToString(OrientationPortraitPrimary); |
| 148 |
| 149 return orientationToString(controller->orientation()); |
| 150 } |
| 151 |
| 152 bool ScreenOrientation::lockOrientation(Screen* screen, const Vector<String>& or
ientationsVector) |
| 153 { |
| 154 ScreenOrientationValues orientations = OrientationInvalid; |
| 155 |
| 156 for (unsigned i = 0; i < orientationsVector.size(); ++i) { |
| 157 ScreenOrientationValues inputOrientation = stringToOrientationValues(Ato
micString(orientationsVector[i])); |
| 158 if (inputOrientation == OrientationInvalid) |
| 159 return false; |
| 160 orientations |= inputOrientation; |
| 161 } |
| 162 |
| 163 if (!orientations) |
| 164 return false; |
| 165 |
| 166 ScreenOrientation* screenOrientation = ScreenOrientation::from(screen); |
| 167 ASSERT(screenOrientation); |
| 168 screenOrientation->lockOrientationAsync(orientations); |
| 169 return true; |
| 170 } |
| 171 |
| 172 bool ScreenOrientation::lockOrientation(Screen* screen, const AtomicString& orie
ntationString) |
| 173 { |
| 174 ScreenOrientationValues orientation = stringToOrientationValues(orientationS
tring); |
| 175 if (!orientation) |
| 176 return false; |
| 177 |
| 178 ScreenOrientation* screenOrientation = ScreenOrientation::from(screen); |
| 179 ASSERT(screenOrientation); |
| 180 screenOrientation->lockOrientationAsync(orientation); |
| 181 return true; |
| 182 } |
| 183 |
| 184 void ScreenOrientation::lockOrientationAsync(ScreenOrientationValues orientation
s) |
| 185 { |
| 186 ASSERT(!(orientations & OrientationInvalid)); |
| 187 |
| 188 m_lockedOrientations = orientations; |
| 189 if (!m_orientationLockTimer.isActive()) |
| 190 m_orientationLockTimer.startOneShot(0); |
| 191 } |
| 192 |
| 193 void ScreenOrientation::unlockOrientation(Screen* screen) |
| 194 { |
| 195 ScreenOrientation* screenOrientation = ScreenOrientation::from(screen); |
| 196 ASSERT(screenOrientation); |
| 197 screenOrientation->unlockOrientation(); |
| 198 } |
| 199 |
| 200 void ScreenOrientation::unlockOrientation() |
| 201 { |
| 202 if (m_lockedOrientations == OrientationAny) |
| 203 return; // Not currently locked. |
| 204 |
| 205 m_lockedOrientations = OrientationAny; |
| 206 |
| 207 ScreenOrientationClient* client = ScreenOrientationController::clientFrom(pa
ge()); |
| 208 if (client) |
| 209 client->unlockOrientation(); |
| 210 } |
| 211 |
| 212 void ScreenOrientation::orientationChanged() |
| 213 { |
| 214 if (m_screen) |
| 215 m_screen->dispatchEvent(Event::create(EventTypeNames::orientationchange)
); |
| 216 } |
| 217 |
| 218 } // namespace WebCore |
OLD | NEW |