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.
5 #define _USE_MATH_DEFINES // For VC++ to get M_PI. This has to be first.
7 #include "ui/compositor/debug_utils.h"
14 #include "base/logging.h"
15 #include "base/strings/utf_string_conversions.h"
16 #include "ui/compositor/layer.h"
17 #include "ui/gfx/interpolated_transform.h"
18 #include "ui/gfx/point.h"
19 #include "ui/gfx/point_conversions.h"
20 #include "ui/gfx/transform.h"
22 using base::UTF8ToWide
;
28 void PrintLayerHierarchyImp(const Layer
* layer
,
30 gfx::Point mouse_location
,
31 std::wostringstream
* out
) {
32 std::string
indent_str(indent
, ' ');
34 layer
->transform().TransformPointReverse(&mouse_location
);
35 bool mouse_inside_layer_bounds
= layer
->bounds().Contains(mouse_location
);
36 mouse_location
.Offset(-layer
->bounds().x(), -layer
->bounds().y());
38 *out
<< UTF8ToWide(indent_str
);
39 if (mouse_inside_layer_bounds
)
44 *out
<< UTF8ToWide(layer
->name()) << L
' ' << layer
;
46 switch (layer
->type()) {
47 case ui::LAYER_NOT_DRAWN
:
48 *out
<< L
" not_drawn";
50 case ui::LAYER_TEXTURED
:
52 if (layer
->fills_bounds_opaquely())
55 case ui::LAYER_SOLID_COLOR
:
58 case ui::LAYER_NINE_PATCH
:
59 *out
<< L
" nine_patch";
63 if (!layer
->visible())
66 std::string
property_indent_str(indent
+3, ' ');
67 *out
<< L
'\n' << UTF8ToWide(property_indent_str
);
68 *out
<< L
"bounds: " << layer
->bounds().x() << L
',' << layer
->bounds().y();
69 *out
<< L
' ' << layer
->bounds().width() << L
'x' << layer
->bounds().height();
70 if (!layer
->subpixel_position_offset().IsZero())
71 *out
<< " " << UTF8ToWide(layer
->subpixel_position_offset().ToString());
73 const ui::Layer
* mask
= const_cast<ui::Layer
*>(layer
)->layer_mask_layer();
76 *out
<< L
'\n' << UTF8ToWide(property_indent_str
);
77 *out
<< L
"mask layer: " << std::setprecision(2)
78 << UTF8ToWide(mask
->bounds().ToString())
79 << UTF8ToWide(mask
->subpixel_position_offset().ToString());
82 if (layer
->opacity() != 1.0f
) {
83 *out
<< L
'\n' << UTF8ToWide(property_indent_str
);
84 *out
<< L
"opacity: " << std::setprecision(2) << layer
->opacity();
87 gfx::DecomposedTransform decomp
;
88 if (!layer
->transform().IsIdentity() &&
89 gfx::DecomposeTransform(&decomp
, layer
->transform())) {
90 *out
<< L
'\n' << UTF8ToWide(property_indent_str
);
91 *out
<< L
"translation: " << std::fixed
<< decomp
.translate
[0];
92 *out
<< L
", " << decomp
.translate
[1];
94 *out
<< L
'\n' << UTF8ToWide(property_indent_str
);
95 *out
<< L
"rotation: ";
96 *out
<< std::acos(decomp
.quaternion
[3]) * 360.0 / M_PI
;
98 *out
<< L
'\n' << UTF8ToWide(property_indent_str
);
99 *out
<< L
"scale: " << decomp
.scale
[0];
100 *out
<< L
", " << decomp
.scale
[1];
105 for (size_t i
= 0, count
= layer
->children().size(); i
< count
; ++i
) {
106 PrintLayerHierarchyImp(
107 layer
->children()[i
], indent
+ 3, mouse_location
, out
);
113 void PrintLayerHierarchy(const Layer
* layer
, gfx::Point mouse_location
) {
114 std::wostringstream out
;
115 out
<< L
"Layer hierarchy:\n";
116 PrintLayerHierarchyImp(layer
, 0, mouse_location
, &out
);
117 // Error so logs can be collected from end-users.
118 LOG(ERROR
) << out
.str();