Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #import <Cocoa/Cocoa.h> | 5 #import <Cocoa/Cocoa.h> |
| 6 | 6 |
| 7 #include "webkit/glue/plugins/webplugin_delegate_impl.h" | 7 #include "webkit/glue/plugins/webplugin_delegate_impl.h" |
| 8 | 8 |
| 9 #include <string> | 9 #include <string> |
| 10 #include <unistd.h> | 10 #include <unistd.h> |
| (...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 83 | 83 |
| 84 class CarbonIdleEventSource { | 84 class CarbonIdleEventSource { |
| 85 public: | 85 public: |
| 86 // Returns the shared Carbon idle event source. | 86 // Returns the shared Carbon idle event source. |
| 87 static CarbonIdleEventSource* SharedInstance() { | 87 static CarbonIdleEventSource* SharedInstance() { |
| 88 DCHECK(MessageLoop::current()->type() == MessageLoop::TYPE_UI); | 88 DCHECK(MessageLoop::current()->type() == MessageLoop::TYPE_UI); |
| 89 static CarbonIdleEventSource* event_source = new CarbonIdleEventSource(); | 89 static CarbonIdleEventSource* event_source = new CarbonIdleEventSource(); |
| 90 return event_source; | 90 return event_source; |
| 91 } | 91 } |
| 92 | 92 |
| 93 // Registers the plugin delegate as interested in receiving idle events | 93 // Registers the plugin delegate as interested in receiving idle events at |
| 94 // suitable for a visible plugin. | 94 // a rate appropriate for the given visibility. A delegate can safely be |
| 95 // Registering a delegate as visible automatically unregisters it from the | 95 // re-registered any number of times, with the latest registration winning. |
| 96 // hidden event source. | 96 void RegisterDelegate(WebPluginDelegateImpl* delegate, bool visible) { |
| 97 void RegisterVisibleDelegate(WebPluginDelegateImpl* delegate) { | 97 if (visible) { |
| 98 UnregisterDelegate(delegate); | 98 visible_delegates_->RegisterDelegate(delegate); |
| 99 if (visible_delegates_.empty()) { | 99 hidden_delegates_->UnregisterDelegate(delegate); |
| 100 visible_timer_.Start( | 100 } else { |
| 101 base::TimeDelta::FromMilliseconds(kVisibleIdlePeriodMs), this, | 101 hidden_delegates_->RegisterDelegate(delegate); |
| 102 &CarbonIdleEventSource::SendVisiblePluginEvents); | 102 visible_delegates_->UnregisterDelegate(delegate); |
| 103 } | 103 } |
| 104 visible_delegates_.insert(delegate); | |
| 105 } | |
| 106 | |
| 107 // Registers the plugin delegate as interested in receiving idle events | |
| 108 // suitable for a plugin that isn't visible. | |
| 109 // Registering a delegate as hidden automatically unregisters it from the | |
| 110 // visible event source. | |
| 111 void RegisterHiddenDelegate(WebPluginDelegateImpl* delegate) { | |
| 112 UnregisterDelegate(delegate); | |
| 113 if (hidden_delegates_.empty()) { | |
| 114 hidden_timer_.Start( | |
| 115 base::TimeDelta::FromMilliseconds(kHiddenIdlePeriodMs), this, | |
| 116 &CarbonIdleEventSource::SendHiddenPluginEvents); | |
| 117 } | |
| 118 hidden_delegates_.insert(delegate); | |
| 119 } | 104 } |
| 120 | 105 |
| 121 // Removes the plugin delegate from the list of plugins receiving idle events. | 106 // Removes the plugin delegate from the list of plugins receiving idle events. |
| 122 void UnregisterDelegate(WebPluginDelegateImpl* delegate) { | 107 void UnregisterDelegate(WebPluginDelegateImpl* delegate) { |
| 123 size_t removed = visible_delegates_.erase(delegate); | 108 visible_delegates_->UnregisterDelegate(delegate); |
| 124 if (removed > 0 && visible_delegates_.empty()) | 109 hidden_delegates_->UnregisterDelegate(delegate); |
| 125 visible_timer_.Stop(); | |
| 126 removed = hidden_delegates_.erase(delegate); | |
| 127 if (removed > 0 && hidden_delegates_.empty()) | |
| 128 hidden_timer_.Stop(); | |
| 129 } | 110 } |
| 130 | 111 |
| 131 private: | 112 private: |
| 132 CarbonIdleEventSource() {} | 113 class VisibilityGroup { |
| 114 public: | |
| 115 explicit VisibilityGroup(int timer_period) | |
| 116 : timer_period_(timer_period), iterator_(delegates_.end()) {} | |
| 133 | 117 |
| 134 void SendVisiblePluginEvents() { | 118 // Adds |delegate| to this visibility group. |
| 135 SendIdleEventsToDelegates(visible_delegates_); | 119 void RegisterDelegate(WebPluginDelegateImpl* delegate) { |
| 136 } | 120 if (delegates_.empty()) { |
| 121 timer_.Start(base::TimeDelta::FromMilliseconds(timer_period_), | |
| 122 this, &VisibilityGroup::SendIdleEvents); | |
| 123 } | |
| 124 delegates_.insert(delegate); | |
| 125 } | |
| 137 | 126 |
| 138 void SendHiddenPluginEvents() { | 127 // Removes |delegate| from this visibility group. |
| 139 SendIdleEventsToDelegates(hidden_delegates_); | 128 void UnregisterDelegate(WebPluginDelegateImpl* delegate) { |
| 140 } | 129 // If a plugin changes visibility during idle event handling, it |
| 130 // may be removed from this set while SendIdleEvents is still iterating; | |
| 131 // if that happens and it's next on the list, increment the iterator | |
|
pink (ping after 24hrs)
2010/02/05 17:31:32
doesn't any change to the list while an iterator i
| |
| 132 // before erasing so that the iteration won't be corrupted. | |
| 133 if ((iterator_ != delegates_.end()) && (*iterator_ == delegate)) | |
| 134 ++iterator_; | |
| 135 size_t removed = delegates_.erase(delegate); | |
| 136 if (removed > 0 && delegates_.empty()) | |
| 137 timer_.Stop(); | |
| 138 } | |
| 141 | 139 |
| 142 void SendIdleEventsToDelegates( | 140 private: |
| 143 const std::set<WebPluginDelegateImpl*>& delegates) const { | 141 // Fires off idle events for each delegate in the group. |
| 144 for (std::set<WebPluginDelegateImpl*>::iterator i = delegates.begin(); | 142 void SendIdleEvents() { |
| 145 i != delegates.end();) { | 143 for (iterator_ = delegates_.begin(); iterator_ != delegates_.end();) { |
| 146 // If the plugin changes size or position during idle event handling, it | 144 // Pre-increment so that the skip logic in UnregisterDelegates works. |
| 147 // may be removed from this set; increment the iterator before calling | 145 WebPluginDelegateImpl* delegate = *(iterator_++); |
| 148 // into the delegate to ensure that the iteration won't be corrupted. | 146 delegate->FireIdleEvent(); |
| 149 WebPluginDelegateImpl* delegate = *(i++); | 147 } |
| 150 delegate->FireIdleEvent(); | |
| 151 } | 148 } |
| 152 } | |
| 153 | 149 |
| 154 base::RepeatingTimer<CarbonIdleEventSource> visible_timer_; | 150 int timer_period_; |
| 155 base::RepeatingTimer<CarbonIdleEventSource> hidden_timer_; | 151 base::RepeatingTimer<VisibilityGroup> timer_; |
| 156 std::set<WebPluginDelegateImpl*> visible_delegates_; | 152 std::set<WebPluginDelegateImpl*> delegates_; |
| 157 std::set<WebPluginDelegateImpl*> hidden_delegates_; | 153 std::set<WebPluginDelegateImpl*>::iterator iterator_; |
| 154 }; | |
| 155 | |
| 156 CarbonIdleEventSource() | |
| 157 : visible_delegates_(new VisibilityGroup(kVisibleIdlePeriodMs)), | |
| 158 hidden_delegates_(new VisibilityGroup(kHiddenIdlePeriodMs)) {} | |
| 159 | |
| 160 scoped_ptr<VisibilityGroup> visible_delegates_; | |
| 161 scoped_ptr<VisibilityGroup> hidden_delegates_; | |
| 162 | |
| 163 DISALLOW_COPY_AND_ASSIGN(CarbonIdleEventSource); | |
| 158 }; | 164 }; |
| 159 #endif // !NP_NO_CARBON | 165 #endif // !NP_NO_CARBON |
| 160 | 166 |
| 161 } // namespace | 167 } // namespace |
| 162 | 168 |
| 163 WebPluginDelegateImpl::WebPluginDelegateImpl( | 169 WebPluginDelegateImpl::WebPluginDelegateImpl( |
| 164 gfx::PluginWindowHandle containing_view, | 170 gfx::PluginWindowHandle containing_view, |
| 165 NPAPI::PluginInstance *instance) | 171 NPAPI::PluginInstance *instance) |
| 166 : windowless_needs_set_window_(true), | 172 : windowless_needs_set_window_(true), |
| 167 // all Mac plugins are "windowless" in the Windows/X11 sense | 173 // all Mac plugins are "windowless" in the Windows/X11 sense |
| (...skipping 463 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 631 int width = new_width ? new_width : old_width; | 637 int width = new_width ? new_width : old_width; |
| 632 window_bounds.left = target_x; | 638 window_bounds.left = target_x; |
| 633 window_bounds.top = target_y; | 639 window_bounds.top = target_y; |
| 634 window_bounds.right = window_bounds.left + width; | 640 window_bounds.right = window_bounds.left + width; |
| 635 window_bounds.bottom = window_bounds.top + height; | 641 window_bounds.bottom = window_bounds.top + height; |
| 636 SetWindowBounds(window, kWindowContentRgn, &window_bounds); | 642 SetWindowBounds(window, kWindowContentRgn, &window_bounds); |
| 637 } | 643 } |
| 638 } | 644 } |
| 639 | 645 |
| 640 void WebPluginDelegateImpl::UpdateIdleEventRate() { | 646 void WebPluginDelegateImpl::UpdateIdleEventRate() { |
| 641 if (container_is_visible_ && !clip_rect_.IsEmpty()) | 647 bool plugin_visible = container_is_visible_ && !clip_rect_.IsEmpty(); |
| 642 CarbonIdleEventSource::SharedInstance()->RegisterVisibleDelegate(this); | 648 CarbonIdleEventSource::SharedInstance()->RegisterDelegate(this, |
| 643 else | 649 plugin_visible); |
| 644 CarbonIdleEventSource::SharedInstance()->RegisterHiddenDelegate(this); | |
| 645 } | 650 } |
| 646 #endif // !NP_NO_CARBON | 651 #endif // !NP_NO_CARBON |
| 647 | 652 |
| 648 static bool WebInputEventIsWebMouseEvent(const WebInputEvent& event) { | 653 static bool WebInputEventIsWebMouseEvent(const WebInputEvent& event) { |
| 649 switch (event.type) { | 654 switch (event.type) { |
| 650 case WebInputEvent::MouseMove: | 655 case WebInputEvent::MouseMove: |
| 651 case WebInputEvent::MouseLeave: | 656 case WebInputEvent::MouseLeave: |
| 652 case WebInputEvent::MouseEnter: | 657 case WebInputEvent::MouseEnter: |
| 653 case WebInputEvent::MouseDown: | 658 case WebInputEvent::MouseDown: |
| 654 case WebInputEvent::MouseUp: | 659 case WebInputEvent::MouseUp: |
| (...skipping 405 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1060 #ifndef NP_NO_QUICKDRAW | 1065 #ifndef NP_NO_QUICKDRAW |
| 1061 // Quickdraw-based plugins can draw at any time, so tell the renderer to | 1066 // Quickdraw-based plugins can draw at any time, so tell the renderer to |
| 1062 // repaint. | 1067 // repaint. |
| 1063 // TODO: only do this if the contents of the offscreen window has changed, | 1068 // TODO: only do this if the contents of the offscreen window has changed, |
| 1064 // so as not to spam the renderer with an unchanging image. | 1069 // so as not to spam the renderer with an unchanging image. |
| 1065 if (instance()->drawing_model() == NPDrawingModelQuickDraw) | 1070 if (instance()->drawing_model() == NPDrawingModelQuickDraw) |
| 1066 instance()->webplugin()->Invalidate(); | 1071 instance()->webplugin()->Invalidate(); |
| 1067 #endif | 1072 #endif |
| 1068 } | 1073 } |
| 1069 #endif // !NP_NO_CARBON | 1074 #endif // !NP_NO_CARBON |
| OLD | NEW |