Update To 11.40.268.0
[platform/framework/web/crosswalk.git] / src / ui / compositor / layer.cc
1 // Copyright (c) 2012 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 "ui/compositor/layer.h"
6
7 #include <algorithm>
8
9 #include "base/command_line.h"
10 #include "base/debug/trace_event.h"
11 #include "base/json/json_writer.h"
12 #include "base/logging.h"
13 #include "base/memory/scoped_ptr.h"
14 #include "cc/base/scoped_ptr_algorithm.h"
15 #include "cc/layers/content_layer.h"
16 #include "cc/layers/delegated_renderer_layer.h"
17 #include "cc/layers/nine_patch_layer.h"
18 #include "cc/layers/picture_layer.h"
19 #include "cc/layers/solid_color_layer.h"
20 #include "cc/layers/surface_layer.h"
21 #include "cc/layers/texture_layer.h"
22 #include "cc/output/copy_output_request.h"
23 #include "cc/output/delegated_frame_data.h"
24 #include "cc/output/filter_operation.h"
25 #include "cc/output/filter_operations.h"
26 #include "cc/resources/transferable_resource.h"
27 #include "ui/compositor/compositor_switches.h"
28 #include "ui/compositor/dip_util.h"
29 #include "ui/compositor/layer_animator.h"
30 #include "ui/gfx/animation/animation.h"
31 #include "ui/gfx/canvas.h"
32 #include "ui/gfx/display.h"
33 #include "ui/gfx/interpolated_transform.h"
34 #include "ui/gfx/point3_f.h"
35 #include "ui/gfx/point_conversions.h"
36 #include "ui/gfx/size_conversions.h"
37
38 namespace {
39
40 const ui::Layer* GetRoot(const ui::Layer* layer) {
41   while (layer->parent())
42     layer = layer->parent();
43   return layer;
44 }
45
46 struct UIImplSidePaintingStatus {
47   UIImplSidePaintingStatus()
48       : enabled(ui::IsUIImplSidePaintingEnabled()) {
49   }
50   bool enabled;
51 };
52 base::LazyInstance<UIImplSidePaintingStatus> g_ui_impl_side_painting_status =
53     LAZY_INSTANCE_INITIALIZER;
54
55 }  // namespace
56
57 namespace ui {
58
59 Layer::Layer()
60     : type_(LAYER_TEXTURED),
61       compositor_(NULL),
62       parent_(NULL),
63       visible_(true),
64       force_render_surface_(false),
65       fills_bounds_opaquely_(true),
66       fills_bounds_completely_(false),
67       background_blur_radius_(0),
68       layer_saturation_(0.0f),
69       layer_brightness_(0.0f),
70       layer_grayscale_(0.0f),
71       layer_inverted_(false),
72       layer_mask_(NULL),
73       layer_mask_back_link_(NULL),
74       zoom_(1),
75       zoom_inset_(0),
76       delegate_(NULL),
77       owner_(NULL),
78       cc_layer_(NULL),
79       device_scale_factor_(1.0f) {
80   CreateCcLayer();
81 }
82
83 Layer::Layer(LayerType type)
84     : type_(type),
85       compositor_(NULL),
86       parent_(NULL),
87       visible_(true),
88       force_render_surface_(false),
89       fills_bounds_opaquely_(true),
90       fills_bounds_completely_(false),
91       background_blur_radius_(0),
92       layer_saturation_(0.0f),
93       layer_brightness_(0.0f),
94       layer_grayscale_(0.0f),
95       layer_inverted_(false),
96       layer_mask_(NULL),
97       layer_mask_back_link_(NULL),
98       zoom_(1),
99       zoom_inset_(0),
100       delegate_(NULL),
101       owner_(NULL),
102       cc_layer_(NULL),
103       device_scale_factor_(1.0f) {
104   CreateCcLayer();
105 }
106
107 Layer::~Layer() {
108   // Destroying the animator may cause observers to use the layer (and
109   // indirectly the WebLayer). Destroy the animator first so that the WebLayer
110   // is still around.
111   if (animator_.get())
112     animator_->SetDelegate(NULL);
113   animator_ = NULL;
114   if (compositor_)
115     compositor_->SetRootLayer(NULL);
116   if (parent_)
117     parent_->Remove(this);
118   if (layer_mask_)
119     SetMaskLayer(NULL);
120   if (layer_mask_back_link_)
121     layer_mask_back_link_->SetMaskLayer(NULL);
122   for (size_t i = 0; i < children_.size(); ++i)
123     children_[i]->parent_ = NULL;
124   cc_layer_->RemoveLayerAnimationEventObserver(this);
125   cc_layer_->RemoveFromParent();
126 }
127
128 // static
129 bool Layer::UsingPictureLayer() {
130   return g_ui_impl_side_painting_status.Get().enabled;
131 }
132
133 const Compositor* Layer::GetCompositor() const {
134   return GetRoot(this)->compositor_;
135 }
136
137 float Layer::opacity() const {
138   return cc_layer_->opacity();
139 }
140
141 void Layer::SetCompositor(Compositor* compositor) {
142   // This function must only be called to set the compositor on the root layer,
143   // or to reset it.
144   DCHECK(!compositor || !compositor_);
145   DCHECK(!compositor || compositor->root_layer() == this);
146   DCHECK(!parent_);
147   if (compositor_) {
148     RemoveAnimatorsInTreeFromCollection(
149         compositor_->layer_animator_collection());
150   }
151   compositor_ = compositor;
152   if (compositor) {
153     OnDeviceScaleFactorChanged(compositor->device_scale_factor());
154     SendPendingThreadedAnimations();
155     AddAnimatorsInTreeToCollection(compositor_->layer_animator_collection());
156   }
157 }
158
159 void Layer::Add(Layer* child) {
160   DCHECK(!child->compositor_);
161   if (child->parent_)
162     child->parent_->Remove(child);
163   child->parent_ = this;
164   children_.push_back(child);
165   cc_layer_->AddChild(child->cc_layer_);
166   child->OnDeviceScaleFactorChanged(device_scale_factor_);
167   if (GetCompositor())
168     child->SendPendingThreadedAnimations();
169   LayerAnimatorCollection* collection = GetLayerAnimatorCollection();
170   if (collection)
171     child->AddAnimatorsInTreeToCollection(collection);
172 }
173
174 void Layer::Remove(Layer* child) {
175   // Current bounds are used to calculate offsets when layers are reparented.
176   // Stop (and complete) an ongoing animation to update the bounds immediately.
177   LayerAnimator* child_animator = child->animator_.get();
178   if (child_animator)
179     child_animator->StopAnimatingProperty(ui::LayerAnimationElement::BOUNDS);
180   LayerAnimatorCollection* collection = GetLayerAnimatorCollection();
181   if (collection)
182     child->RemoveAnimatorsInTreeFromCollection(collection);
183
184   std::vector<Layer*>::iterator i =
185       std::find(children_.begin(), children_.end(), child);
186   DCHECK(i != children_.end());
187   children_.erase(i);
188   child->parent_ = NULL;
189   child->cc_layer_->RemoveFromParent();
190 }
191
192 void Layer::StackAtTop(Layer* child) {
193   if (children_.size() <= 1 || child == children_.back())
194     return;  // Already in front.
195   StackAbove(child, children_.back());
196 }
197
198 void Layer::StackAbove(Layer* child, Layer* other) {
199   StackRelativeTo(child, other, true);
200 }
201
202 void Layer::StackAtBottom(Layer* child) {
203   if (children_.size() <= 1 || child == children_.front())
204     return;  // Already on bottom.
205   StackBelow(child, children_.front());
206 }
207
208 void Layer::StackBelow(Layer* child, Layer* other) {
209   StackRelativeTo(child, other, false);
210 }
211
212 bool Layer::Contains(const Layer* other) const {
213   for (const Layer* parent = other; parent; parent = parent->parent()) {
214     if (parent == this)
215       return true;
216   }
217   return false;
218 }
219
220 void Layer::SetAnimator(LayerAnimator* animator) {
221   if (animator)
222     animator->SetDelegate(this);
223   animator_ = animator;
224 }
225
226 LayerAnimator* Layer::GetAnimator() {
227   if (!animator_.get())
228     SetAnimator(LayerAnimator::CreateDefaultAnimator());
229   return animator_.get();
230 }
231
232 void Layer::SetTransform(const gfx::Transform& transform) {
233   GetAnimator()->SetTransform(transform);
234 }
235
236 gfx::Transform Layer::GetTargetTransform() const {
237   if (animator_.get() && animator_->IsAnimatingProperty(
238       LayerAnimationElement::TRANSFORM)) {
239     return animator_->GetTargetTransform();
240   }
241   return transform();
242 }
243
244 void Layer::SetBounds(const gfx::Rect& bounds) {
245   GetAnimator()->SetBounds(bounds);
246 }
247
248 void Layer::SetSubpixelPositionOffset(const gfx::Vector2dF offset) {
249   subpixel_position_offset_ = offset;
250   RecomputePosition();
251 }
252
253 gfx::Rect Layer::GetTargetBounds() const {
254   if (animator_.get() && animator_->IsAnimatingProperty(
255       LayerAnimationElement::BOUNDS)) {
256     return animator_->GetTargetBounds();
257   }
258   return bounds_;
259 }
260
261 void Layer::SetMasksToBounds(bool masks_to_bounds) {
262   cc_layer_->SetMasksToBounds(masks_to_bounds);
263 }
264
265 bool Layer::GetMasksToBounds() const {
266   return cc_layer_->masks_to_bounds();
267 }
268
269 void Layer::SetOpacity(float opacity) {
270   GetAnimator()->SetOpacity(opacity);
271 }
272
273 float Layer::GetCombinedOpacity() const {
274   float opacity = this->opacity();
275   Layer* current = this->parent_;
276   while (current) {
277     opacity *= current->opacity();
278     current = current->parent_;
279   }
280   return opacity;
281 }
282
283 void Layer::SetBackgroundBlur(int blur_radius) {
284   background_blur_radius_ = blur_radius;
285
286   SetLayerBackgroundFilters();
287 }
288
289 void Layer::SetLayerSaturation(float saturation) {
290   layer_saturation_ = saturation;
291   SetLayerFilters();
292 }
293
294 void Layer::SetLayerBrightness(float brightness) {
295   GetAnimator()->SetBrightness(brightness);
296 }
297
298 float Layer::GetTargetBrightness() const {
299   if (animator_.get() && animator_->IsAnimatingProperty(
300       LayerAnimationElement::BRIGHTNESS)) {
301     return animator_->GetTargetBrightness();
302   }
303   return layer_brightness();
304 }
305
306 void Layer::SetLayerGrayscale(float grayscale) {
307   GetAnimator()->SetGrayscale(grayscale);
308 }
309
310 float Layer::GetTargetGrayscale() const {
311   if (animator_.get() && animator_->IsAnimatingProperty(
312       LayerAnimationElement::GRAYSCALE)) {
313     return animator_->GetTargetGrayscale();
314   }
315   return layer_grayscale();
316 }
317
318 void Layer::SetLayerInverted(bool inverted) {
319   layer_inverted_ = inverted;
320   SetLayerFilters();
321 }
322
323 void Layer::SetMaskLayer(Layer* layer_mask) {
324   // The provided mask should not have a layer mask itself.
325   DCHECK(!layer_mask ||
326          (!layer_mask->layer_mask_layer() &&
327           layer_mask->children().empty() &&
328           !layer_mask->layer_mask_back_link_));
329   DCHECK(!layer_mask_back_link_);
330   if (layer_mask_ == layer_mask)
331     return;
332   // We need to de-reference the currently linked object so that no problem
333   // arises if the mask layer gets deleted before this object.
334   if (layer_mask_)
335     layer_mask_->layer_mask_back_link_ = NULL;
336   layer_mask_ = layer_mask;
337   cc_layer_->SetMaskLayer(
338       layer_mask ? layer_mask->cc_layer() : NULL);
339   // We need to reference the linked object so that it can properly break the
340   // link to us when it gets deleted.
341   if (layer_mask) {
342     layer_mask->layer_mask_back_link_ = this;
343     layer_mask->OnDeviceScaleFactorChanged(device_scale_factor_);
344   }
345 }
346
347 void Layer::SetBackgroundZoom(float zoom, int inset) {
348   zoom_ = zoom;
349   zoom_inset_ = inset;
350
351   SetLayerBackgroundFilters();
352 }
353
354 void Layer::SetAlphaShape(scoped_ptr<SkRegion> region) {
355   alpha_shape_ = region.Pass();
356
357   SetLayerFilters();
358 }
359
360 void Layer::SetLayerFilters() {
361   cc::FilterOperations filters;
362   if (layer_saturation_) {
363     filters.Append(cc::FilterOperation::CreateSaturateFilter(
364         layer_saturation_));
365   }
366   if (layer_grayscale_) {
367     filters.Append(cc::FilterOperation::CreateGrayscaleFilter(
368         layer_grayscale_));
369   }
370   if (layer_inverted_)
371     filters.Append(cc::FilterOperation::CreateInvertFilter(1.0));
372   // Brightness goes last, because the resulting colors neeed clamping, which
373   // cause further color matrix filters to be applied separately. In this order,
374   // they all can be combined in a single pass.
375   if (layer_brightness_) {
376     filters.Append(cc::FilterOperation::CreateSaturatingBrightnessFilter(
377         layer_brightness_));
378   }
379   if (alpha_shape_) {
380     filters.Append(cc::FilterOperation::CreateAlphaThresholdFilter(
381             *alpha_shape_, 0.f, 0.f));
382   }
383
384   cc_layer_->SetFilters(filters);
385 }
386
387 void Layer::SetLayerBackgroundFilters() {
388   cc::FilterOperations filters;
389   if (zoom_ != 1)
390     filters.Append(cc::FilterOperation::CreateZoomFilter(zoom_, zoom_inset_));
391
392   if (background_blur_radius_) {
393     filters.Append(cc::FilterOperation::CreateBlurFilter(
394         background_blur_radius_));
395   }
396
397   cc_layer_->SetBackgroundFilters(filters);
398 }
399
400 float Layer::GetTargetOpacity() const {
401   if (animator_.get() && animator_->IsAnimatingProperty(
402       LayerAnimationElement::OPACITY))
403     return animator_->GetTargetOpacity();
404   return opacity();
405 }
406
407 void Layer::SetVisible(bool visible) {
408   GetAnimator()->SetVisibility(visible);
409 }
410
411 bool Layer::GetTargetVisibility() const {
412   if (animator_.get() && animator_->IsAnimatingProperty(
413       LayerAnimationElement::VISIBILITY))
414     return animator_->GetTargetVisibility();
415   return visible_;
416 }
417
418 bool Layer::IsDrawn() const {
419   const Layer* layer = this;
420   while (layer && layer->visible_)
421     layer = layer->parent_;
422   return layer == NULL;
423 }
424
425 bool Layer::ShouldDraw() const {
426   return type_ != LAYER_NOT_DRAWN && GetCombinedOpacity() > 0.0f;
427 }
428
429 // static
430 void Layer::ConvertPointToLayer(const Layer* source,
431                                 const Layer* target,
432                                 gfx::Point* point) {
433   if (source == target)
434     return;
435
436   const Layer* root_layer = GetRoot(source);
437   CHECK_EQ(root_layer, GetRoot(target));
438
439   if (source != root_layer)
440     source->ConvertPointForAncestor(root_layer, point);
441   if (target != root_layer)
442     target->ConvertPointFromAncestor(root_layer, point);
443 }
444
445 bool Layer::GetTargetTransformRelativeTo(const Layer* ancestor,
446                                          gfx::Transform* transform) const {
447   const Layer* p = this;
448   for (; p && p != ancestor; p = p->parent()) {
449     gfx::Transform translation;
450     translation.Translate(static_cast<float>(p->bounds().x()),
451                           static_cast<float>(p->bounds().y()));
452     // Use target transform so that result will be correct once animation is
453     // finished.
454     if (!p->GetTargetTransform().IsIdentity())
455       transform->ConcatTransform(p->GetTargetTransform());
456     transform->ConcatTransform(translation);
457   }
458   return p == ancestor;
459 }
460
461 void Layer::SetFillsBoundsOpaquely(bool fills_bounds_opaquely) {
462   if (fills_bounds_opaquely_ == fills_bounds_opaquely)
463     return;
464
465   fills_bounds_opaquely_ = fills_bounds_opaquely;
466
467   cc_layer_->SetContentsOpaque(fills_bounds_opaquely);
468 }
469
470 void Layer::SetFillsBoundsCompletely(bool fills_bounds_completely) {
471   fills_bounds_completely_ = fills_bounds_completely;
472 }
473
474 void Layer::SwitchToLayer(scoped_refptr<cc::Layer> new_layer) {
475   // Finish animations being handled by cc_layer_.
476   if (animator_.get()) {
477     animator_->StopAnimatingProperty(LayerAnimationElement::TRANSFORM);
478     animator_->StopAnimatingProperty(LayerAnimationElement::OPACITY);
479   }
480
481   if (texture_layer_.get())
482     texture_layer_->ClearClient();
483   // TODO(piman): delegated_renderer_layer_ cleanup.
484
485   cc_layer_->RemoveAllChildren();
486   if (cc_layer_->parent()) {
487     cc_layer_->parent()->ReplaceChild(cc_layer_, new_layer);
488   }
489   cc_layer_->SetLayerClient(NULL);
490   cc_layer_->RemoveLayerAnimationEventObserver(this);
491   new_layer->SetOpacity(cc_layer_->opacity());
492   new_layer->SetTransform(cc_layer_->transform());
493   new_layer->SetPosition(cc_layer_->position());
494   new_layer->SetBackgroundColor(cc_layer_->background_color());
495
496   cc_layer_ = new_layer.get();
497   content_layer_ = NULL;
498   solid_color_layer_ = NULL;
499   texture_layer_ = NULL;
500   delegated_renderer_layer_ = NULL;
501   surface_layer_ = NULL;
502
503   cc_layer_->AddLayerAnimationEventObserver(this);
504   for (size_t i = 0; i < children_.size(); ++i) {
505     DCHECK(children_[i]->cc_layer_);
506     cc_layer_->AddChild(children_[i]->cc_layer_);
507   }
508   cc_layer_->SetLayerClient(this);
509   cc_layer_->SetTransformOrigin(gfx::Point3F());
510   cc_layer_->SetContentsOpaque(fills_bounds_opaquely_);
511   cc_layer_->SetForceRenderSurface(force_render_surface_);
512   cc_layer_->SetIsDrawable(type_ != LAYER_NOT_DRAWN);
513   cc_layer_->SetHideLayerAndSubtree(!visible_);
514
515   SetLayerFilters();
516   SetLayerBackgroundFilters();
517 }
518
519 void Layer::SwitchCCLayerForTest() {
520   scoped_refptr<cc::Layer> new_layer;
521   if (Layer::UsingPictureLayer())
522     new_layer = cc::PictureLayer::Create(this);
523   else
524     new_layer = cc::ContentLayer::Create(this);
525   SwitchToLayer(new_layer);
526   content_layer_ = new_layer;
527 }
528
529 void Layer::SetTextureMailbox(
530     const cc::TextureMailbox& mailbox,
531     scoped_ptr<cc::SingleReleaseCallback> release_callback,
532     gfx::Size texture_size_in_dip) {
533   DCHECK(type_ == LAYER_TEXTURED || type_ == LAYER_SOLID_COLOR);
534   DCHECK(mailbox.IsValid());
535   DCHECK(release_callback);
536   if (!texture_layer_.get()) {
537     scoped_refptr<cc::TextureLayer> new_layer =
538         cc::TextureLayer::CreateForMailbox(this);
539     new_layer->SetFlipped(true);
540     SwitchToLayer(new_layer);
541     texture_layer_ = new_layer;
542   }
543   if (mailbox_release_callback_)
544     mailbox_release_callback_->Run(0, false);
545   mailbox_release_callback_ = release_callback.Pass();
546   mailbox_ = mailbox;
547   SetTextureSize(texture_size_in_dip);
548 }
549
550 void Layer::SetTextureSize(gfx::Size texture_size_in_dip) {
551   DCHECK(texture_layer_.get());
552   if (frame_size_in_dip_ == texture_size_in_dip)
553     return;
554   frame_size_in_dip_ = texture_size_in_dip;
555   RecomputeDrawsContentAndUVRect();
556   texture_layer_->SetNeedsDisplay();
557 }
558
559 void Layer::SetShowDelegatedContent(cc::DelegatedFrameProvider* frame_provider,
560                                     gfx::Size frame_size_in_dip) {
561   DCHECK(type_ == LAYER_TEXTURED || type_ == LAYER_SOLID_COLOR);
562
563   scoped_refptr<cc::DelegatedRendererLayer> new_layer =
564       cc::DelegatedRendererLayer::Create(frame_provider);
565   SwitchToLayer(new_layer);
566   delegated_renderer_layer_ = new_layer;
567
568   frame_size_in_dip_ = frame_size_in_dip;
569   RecomputeDrawsContentAndUVRect();
570 }
571
572 void Layer::SetShowSurface(
573     cc::SurfaceId surface_id,
574     const cc::SurfaceLayer::SatisfyCallback& satisfy_callback,
575     const cc::SurfaceLayer::RequireCallback& require_callback,
576     gfx::Size surface_size,
577     gfx::Size frame_size_in_dip) {
578   DCHECK(type_ == LAYER_TEXTURED || type_ == LAYER_SOLID_COLOR);
579
580   scoped_refptr<cc::SurfaceLayer> new_layer =
581       cc::SurfaceLayer::Create(satisfy_callback, require_callback);
582   new_layer->SetSurfaceId(surface_id, surface_size);
583   SwitchToLayer(new_layer);
584   surface_layer_ = new_layer;
585
586   frame_size_in_dip_ = frame_size_in_dip;
587   RecomputeDrawsContentAndUVRect();
588 }
589
590 void Layer::SetShowSolidColorContent() {
591   DCHECK_EQ(type_, LAYER_SOLID_COLOR);
592
593   if (solid_color_layer_.get())
594     return;
595
596   scoped_refptr<cc::SolidColorLayer> new_layer = cc::SolidColorLayer::Create();
597   SwitchToLayer(new_layer);
598   solid_color_layer_ = new_layer;
599
600   mailbox_ = cc::TextureMailbox();
601   if (mailbox_release_callback_) {
602     mailbox_release_callback_->Run(0, false);
603     mailbox_release_callback_.reset();
604   }
605   RecomputeDrawsContentAndUVRect();
606 }
607
608 void Layer::UpdateNinePatchLayerBitmap(const SkBitmap& bitmap) {
609   DCHECK(type_ == LAYER_NINE_PATCH && nine_patch_layer_.get());
610   SkBitmap bitmap_copy;
611   if (bitmap.isImmutable()) {
612     bitmap_copy = bitmap;
613   } else {
614     // UIResourceBitmap requires an immutable copy of the input |bitmap|.
615     bitmap.copyTo(&bitmap_copy);
616     bitmap_copy.setImmutable();
617   }
618   nine_patch_layer_->SetBitmap(bitmap_copy);
619 }
620
621 void Layer::UpdateNinePatchLayerAperture(const gfx::Rect& aperture) {
622   DCHECK(type_ == LAYER_NINE_PATCH && nine_patch_layer_.get());
623   nine_patch_layer_->SetAperture(aperture);
624 }
625
626 void Layer::UpdateNinePatchLayerBorder(const gfx::Rect& border) {
627   DCHECK(type_ == LAYER_NINE_PATCH && nine_patch_layer_.get());
628   nine_patch_layer_->SetBorder(border);
629 }
630
631 void Layer::SetColor(SkColor color) { GetAnimator()->SetColor(color); }
632
633 bool Layer::SchedulePaint(const gfx::Rect& invalid_rect) {
634   if ((type_ == LAYER_SOLID_COLOR && !texture_layer_.get()) ||
635       type_ == LAYER_NINE_PATCH || (!delegate_ && !mailbox_.IsValid()))
636     return false;
637
638   damaged_region_.op(invalid_rect.x(),
639                      invalid_rect.y(),
640                      invalid_rect.right(),
641                      invalid_rect.bottom(),
642                      SkRegion::kUnion_Op);
643   ScheduleDraw();
644   return true;
645 }
646
647 void Layer::ScheduleDraw() {
648   Compositor* compositor = GetCompositor();
649   if (compositor)
650     compositor->ScheduleDraw();
651 }
652
653 void Layer::SendDamagedRects() {
654   if ((delegate_ || mailbox_.IsValid()) && !damaged_region_.isEmpty()) {
655     for (SkRegion::Iterator iter(damaged_region_); !iter.done(); iter.next()) {
656       const SkIRect& sk_damaged = iter.rect();
657       gfx::Rect damaged(
658           sk_damaged.x(),
659           sk_damaged.y(),
660           sk_damaged.width(),
661           sk_damaged.height());
662       cc_layer_->SetNeedsDisplayRect(damaged);
663     }
664     damaged_region_.setEmpty();
665   }
666   for (size_t i = 0; i < children_.size(); ++i)
667     children_[i]->SendDamagedRects();
668 }
669
670 void Layer::CompleteAllAnimations() {
671   typedef std::vector<scoped_refptr<LayerAnimator> > LayerAnimatorVector;
672   LayerAnimatorVector animators;
673   CollectAnimators(&animators);
674   for (LayerAnimatorVector::const_iterator it = animators.begin();
675        it != animators.end();
676        ++it) {
677     (*it)->StopAnimating();
678   }
679 }
680
681 void Layer::SuppressPaint() {
682   if (!delegate_)
683     return;
684   delegate_ = NULL;
685   for (size_t i = 0; i < children_.size(); ++i)
686     children_[i]->SuppressPaint();
687 }
688
689 void Layer::OnDeviceScaleFactorChanged(float device_scale_factor) {
690   if (device_scale_factor_ == device_scale_factor)
691     return;
692   if (animator_.get())
693     animator_->StopAnimatingProperty(LayerAnimationElement::TRANSFORM);
694   device_scale_factor_ = device_scale_factor;
695   RecomputeDrawsContentAndUVRect();
696   RecomputePosition();
697   SchedulePaint(gfx::Rect(bounds_.size()));
698   if (delegate_)
699     delegate_->OnDeviceScaleFactorChanged(device_scale_factor);
700   for (size_t i = 0; i < children_.size(); ++i)
701     children_[i]->OnDeviceScaleFactorChanged(device_scale_factor);
702   if (layer_mask_)
703     layer_mask_->OnDeviceScaleFactorChanged(device_scale_factor);
704 }
705
706 void Layer::OnDelegatedFrameDamage(const gfx::Rect& damage_rect_in_dip) {
707   DCHECK(delegated_renderer_layer_.get() || surface_layer_.get());
708   if (!delegate_)
709     return;
710   delegate_->OnDelegatedFrameDamage(damage_rect_in_dip);
711 }
712
713 void Layer::RequestCopyOfOutput(scoped_ptr<cc::CopyOutputRequest> request) {
714   cc_layer_->RequestCopyOfOutput(request.Pass());
715 }
716
717 void Layer::PaintContents(SkCanvas* sk_canvas,
718                           const gfx::Rect& clip,
719                           ContentLayerClient::GraphicsContextStatus gc_status) {
720   TRACE_EVENT0("ui", "Layer::PaintContents");
721   scoped_ptr<gfx::Canvas> canvas(gfx::Canvas::CreateCanvasWithoutScaling(
722       sk_canvas, device_scale_factor_));
723   if (delegate_)
724     delegate_->OnPaintLayer(canvas.get());
725 }
726
727 bool Layer::FillsBoundsCompletely() const { return fills_bounds_completely_; }
728
729 bool Layer::PrepareTextureMailbox(
730     cc::TextureMailbox* mailbox,
731     scoped_ptr<cc::SingleReleaseCallback>* release_callback,
732     bool use_shared_memory) {
733   if (!mailbox_release_callback_)
734     return false;
735   *mailbox = mailbox_;
736   *release_callback = mailbox_release_callback_.Pass();
737   return true;
738 }
739
740 void Layer::SetForceRenderSurface(bool force) {
741   if (force_render_surface_ == force)
742     return;
743
744   force_render_surface_ = force;
745   cc_layer_->SetForceRenderSurface(force_render_surface_);
746 }
747
748 class LayerDebugInfo : public base::debug::ConvertableToTraceFormat {
749  public:
750   explicit LayerDebugInfo(std::string name) : name_(name) { }
751   void AppendAsTraceFormat(std::string* out) const override {
752     base::DictionaryValue dictionary;
753     dictionary.SetString("layer_name", name_);
754     base::JSONWriter::Write(&dictionary, out);
755   }
756
757  private:
758   ~LayerDebugInfo() override {}
759   std::string name_;
760 };
761
762 scoped_refptr<base::debug::ConvertableToTraceFormat> Layer::TakeDebugInfo() {
763   return new LayerDebugInfo(name_);
764 }
765
766 void Layer::OnAnimationStarted(const cc::AnimationEvent& event) {
767   if (animator_.get())
768     animator_->OnThreadedAnimationStarted(event);
769 }
770
771 void Layer::CollectAnimators(
772     std::vector<scoped_refptr<LayerAnimator> >* animators) {
773   if (IsAnimating())
774     animators->push_back(animator_);
775   std::for_each(children_.begin(), children_.end(),
776                 std::bind2nd(std::mem_fun(&Layer::CollectAnimators),
777                              animators));
778 }
779
780 void Layer::StackRelativeTo(Layer* child, Layer* other, bool above) {
781   DCHECK_NE(child, other);
782   DCHECK_EQ(this, child->parent());
783   DCHECK_EQ(this, other->parent());
784
785   const size_t child_i =
786       std::find(children_.begin(), children_.end(), child) - children_.begin();
787   const size_t other_i =
788       std::find(children_.begin(), children_.end(), other) - children_.begin();
789   if ((above && child_i == other_i + 1) || (!above && child_i + 1 == other_i))
790     return;
791
792   const size_t dest_i =
793       above ?
794       (child_i < other_i ? other_i : other_i + 1) :
795       (child_i < other_i ? other_i - 1 : other_i);
796   children_.erase(children_.begin() + child_i);
797   children_.insert(children_.begin() + dest_i, child);
798
799   child->cc_layer_->RemoveFromParent();
800   cc_layer_->InsertChild(child->cc_layer_, dest_i);
801 }
802
803 bool Layer::ConvertPointForAncestor(const Layer* ancestor,
804                                     gfx::Point* point) const {
805   gfx::Transform transform;
806   bool result = GetTargetTransformRelativeTo(ancestor, &transform);
807   gfx::Point3F p(*point);
808   transform.TransformPoint(&p);
809   *point = gfx::ToFlooredPoint(p.AsPointF());
810   return result;
811 }
812
813 bool Layer::ConvertPointFromAncestor(const Layer* ancestor,
814                                      gfx::Point* point) const {
815   gfx::Transform transform;
816   bool result = GetTargetTransformRelativeTo(ancestor, &transform);
817   gfx::Point3F p(*point);
818   transform.TransformPointReverse(&p);
819   *point = gfx::ToFlooredPoint(p.AsPointF());
820   return result;
821 }
822
823 void Layer::SetBoundsFromAnimation(const gfx::Rect& bounds) {
824   if (bounds == bounds_)
825     return;
826
827   base::Closure closure;
828   if (delegate_)
829     closure = delegate_->PrepareForLayerBoundsChange();
830   bool was_move = bounds_.size() == bounds.size();
831   bounds_ = bounds;
832
833   RecomputeDrawsContentAndUVRect();
834   RecomputePosition();
835
836   if (!closure.is_null())
837     closure.Run();
838
839   if (was_move) {
840     // Don't schedule a draw if we're invisible. We'll schedule one
841     // automatically when we get visible.
842     if (IsDrawn())
843       ScheduleDraw();
844   } else {
845     // Always schedule a paint, even if we're invisible.
846     SchedulePaint(gfx::Rect(bounds.size()));
847   }
848 }
849
850 void Layer::SetTransformFromAnimation(const gfx::Transform& transform) {
851   cc_layer_->SetTransform(transform);
852 }
853
854 void Layer::SetOpacityFromAnimation(float opacity) {
855   cc_layer_->SetOpacity(opacity);
856   ScheduleDraw();
857 }
858
859 void Layer::SetVisibilityFromAnimation(bool visible) {
860   if (visible_ == visible)
861     return;
862
863   visible_ = visible;
864   cc_layer_->SetHideLayerAndSubtree(!visible_);
865 }
866
867 void Layer::SetBrightnessFromAnimation(float brightness) {
868   layer_brightness_ = brightness;
869   SetLayerFilters();
870 }
871
872 void Layer::SetGrayscaleFromAnimation(float grayscale) {
873   layer_grayscale_ = grayscale;
874   SetLayerFilters();
875 }
876
877 void Layer::SetColorFromAnimation(SkColor color) {
878   DCHECK_EQ(type_, LAYER_SOLID_COLOR);
879   cc_layer_->SetBackgroundColor(color);
880   SetFillsBoundsOpaquely(SkColorGetA(color) == 0xFF);
881 }
882
883 void Layer::ScheduleDrawForAnimation() {
884   ScheduleDraw();
885 }
886
887 const gfx::Rect& Layer::GetBoundsForAnimation() const {
888   return bounds();
889 }
890
891 gfx::Transform Layer::GetTransformForAnimation() const {
892   return transform();
893 }
894
895 float Layer::GetOpacityForAnimation() const {
896   return opacity();
897 }
898
899 bool Layer::GetVisibilityForAnimation() const {
900   return visible();
901 }
902
903 float Layer::GetBrightnessForAnimation() const {
904   return layer_brightness();
905 }
906
907 float Layer::GetGrayscaleForAnimation() const {
908   return layer_grayscale();
909 }
910
911 SkColor Layer::GetColorForAnimation() const {
912   // WebColor is equivalent to SkColor, per WebColor.h.
913   // The NULL check is here since this is invoked regardless of whether we have
914   // been configured as LAYER_SOLID_COLOR.
915   return solid_color_layer_.get() ?
916       solid_color_layer_->background_color() : SK_ColorBLACK;
917 }
918
919 float Layer::GetDeviceScaleFactor() const {
920   return device_scale_factor_;
921 }
922
923 void Layer::AddThreadedAnimation(scoped_ptr<cc::Animation> animation) {
924   DCHECK(cc_layer_);
925   // Until this layer has a compositor (and hence cc_layer_ has a
926   // LayerTreeHost), addAnimation will fail.
927   if (GetCompositor())
928     cc_layer_->AddAnimation(animation.Pass());
929   else
930     pending_threaded_animations_.push_back(animation.Pass());
931 }
932
933 namespace{
934
935 struct HasAnimationId {
936   HasAnimationId(int id): id_(id) {
937   }
938
939   bool operator()(cc::Animation* animation) const {
940     return animation->id() == id_;
941   }
942
943  private:
944   int id_;
945 };
946
947 }
948
949 void Layer::RemoveThreadedAnimation(int animation_id) {
950   DCHECK(cc_layer_);
951   if (pending_threaded_animations_.size() == 0) {
952     cc_layer_->RemoveAnimation(animation_id);
953     return;
954   }
955
956   pending_threaded_animations_.erase(
957       cc::remove_if(&pending_threaded_animations_,
958                     pending_threaded_animations_.begin(),
959                     pending_threaded_animations_.end(),
960                     HasAnimationId(animation_id)),
961       pending_threaded_animations_.end());
962 }
963
964 LayerAnimatorCollection* Layer::GetLayerAnimatorCollection() {
965   Compositor* compositor = GetCompositor();
966   return compositor ? compositor->layer_animator_collection() : NULL;
967 }
968
969 void Layer::SendPendingThreadedAnimations() {
970   for (cc::ScopedPtrVector<cc::Animation>::iterator it =
971            pending_threaded_animations_.begin();
972        it != pending_threaded_animations_.end();
973        ++it)
974     cc_layer_->AddAnimation(pending_threaded_animations_.take(it));
975
976   pending_threaded_animations_.clear();
977
978   for (size_t i = 0; i < children_.size(); ++i)
979     children_[i]->SendPendingThreadedAnimations();
980 }
981
982 void Layer::CreateCcLayer() {
983   if (type_ == LAYER_SOLID_COLOR) {
984     solid_color_layer_ = cc::SolidColorLayer::Create();
985     cc_layer_ = solid_color_layer_.get();
986   } else if (type_ == LAYER_NINE_PATCH) {
987     nine_patch_layer_ = cc::NinePatchLayer::Create();
988     cc_layer_ = nine_patch_layer_.get();
989   } else {
990     if (Layer::UsingPictureLayer())
991       content_layer_ = cc::PictureLayer::Create(this);
992     else
993       content_layer_ = cc::ContentLayer::Create(this);
994     cc_layer_ = content_layer_.get();
995   }
996   cc_layer_->SetTransformOrigin(gfx::Point3F());
997   cc_layer_->SetContentsOpaque(true);
998   cc_layer_->SetIsDrawable(type_ != LAYER_NOT_DRAWN);
999   cc_layer_->AddLayerAnimationEventObserver(this);
1000   cc_layer_->SetLayerClient(this);
1001   RecomputePosition();
1002 }
1003
1004 gfx::Transform Layer::transform() const {
1005   return cc_layer_->transform();
1006 }
1007
1008 void Layer::RecomputeDrawsContentAndUVRect() {
1009   DCHECK(cc_layer_);
1010   gfx::Size size(bounds_.size());
1011   if (texture_layer_.get()) {
1012     size.SetToMin(frame_size_in_dip_);
1013     gfx::PointF uv_top_left(0.f, 0.f);
1014     gfx::PointF uv_bottom_right(
1015         static_cast<float>(size.width()) / frame_size_in_dip_.width(),
1016         static_cast<float>(size.height()) / frame_size_in_dip_.height());
1017     texture_layer_->SetUV(uv_top_left, uv_bottom_right);
1018   } else if (delegated_renderer_layer_.get() || surface_layer_.get()) {
1019     size.SetToMin(frame_size_in_dip_);
1020   }
1021   cc_layer_->SetBounds(size);
1022 }
1023
1024 void Layer::RecomputePosition() {
1025   cc_layer_->SetPosition(bounds_.origin() + subpixel_position_offset_);
1026 }
1027
1028 void Layer::AddAnimatorsInTreeToCollection(
1029     LayerAnimatorCollection* collection) {
1030   DCHECK(collection);
1031   if (IsAnimating())
1032     animator_->AddToCollection(collection);
1033   std::for_each(
1034       children_.begin(),
1035       children_.end(),
1036       std::bind2nd(std::mem_fun(&Layer::AddAnimatorsInTreeToCollection),
1037                    collection));
1038 }
1039
1040 void Layer::RemoveAnimatorsInTreeFromCollection(
1041     LayerAnimatorCollection* collection) {
1042   DCHECK(collection);
1043   if (IsAnimating())
1044     animator_->RemoveFromCollection(collection);
1045   std::for_each(
1046       children_.begin(),
1047       children_.end(),
1048       std::bind2nd(std::mem_fun(&Layer::RemoveAnimatorsInTreeFromCollection),
1049                    collection));
1050 }
1051
1052 bool Layer::IsAnimating() const {
1053   return animator_.get() && animator_->is_animating();
1054 }
1055
1056 }  // namespace ui