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 "mojo/services/public/cpp/view_manager/view.h"
6
7#include "mojo/services/public/cpp/view_manager/lib/view_manager_client_impl.h"
8#include "mojo/services/public/cpp/view_manager/lib/view_private.h"
9#include "mojo/services/public/cpp/view_manager/node.h"
10#include "mojo/services/public/cpp/view_manager/view_observer.h"
11#include "ui/gfx/canvas.h"
12
13namespace mojo {
14namespace view_manager {
15
16namespace {
17class ScopedDestructionNotifier {
18 public:
19  explicit ScopedDestructionNotifier(View* view)
20      : view_(view) {
21    FOR_EACH_OBSERVER(
22        ViewObserver,
23        *ViewPrivate(view_).observers(),
24        OnViewDestroy(view_, ViewObserver::DISPOSITION_CHANGING));
25  }
26  ~ScopedDestructionNotifier() {
27    FOR_EACH_OBSERVER(
28        ViewObserver,
29        *ViewPrivate(view_).observers(),
30        OnViewDestroy(view_, ViewObserver::DISPOSITION_CHANGED));
31  }
32
33 private:
34  View* view_;
35
36  DISALLOW_COPY_AND_ASSIGN(ScopedDestructionNotifier);
37};
38}  // namespace
39
40// static
41View* View::Create(ViewManager* manager) {
42  View* view = new View(manager);
43  static_cast<ViewManagerClientImpl*>(manager)->AddView(view);
44  return view;
45}
46
47void View::Destroy() {
48  if (manager_)
49    static_cast<ViewManagerClientImpl*>(manager_)->DestroyView(id_);
50  LocalDestroy();
51}
52
53void View::AddObserver(ViewObserver* observer) {
54  observers_.AddObserver(observer);
55}
56
57void View::RemoveObserver(ViewObserver* observer) {
58  observers_.RemoveObserver(observer);
59}
60
61void View::SetContents(const SkBitmap& contents) {
62  if (manager_) {
63    static_cast<ViewManagerClientImpl*>(manager_)->SetViewContents(id_,
64                                                                   contents);
65  }
66}
67
68void View::SetColor(SkColor color) {
69  gfx::Canvas canvas(node_->bounds().size(), 1.0f, true);
70  canvas.DrawColor(color);
71  SetContents(skia::GetTopDevice(*canvas.sk_canvas())->accessBitmap(true));
72}
73
74View::View(ViewManager* manager)
75    : id_(static_cast<ViewManagerClientImpl*>(manager)->CreateView()),
76      node_(NULL),
77      manager_(manager) {}
78
79View::View()
80    : id_(-1),
81      node_(NULL),
82      manager_(NULL) {}
83
84View::~View() {
85  ScopedDestructionNotifier notifier(this);
86  // TODO(beng): It'd be better to do this via a destruction observer in the
87  //             ViewManagerClientImpl.
88  if (manager_)
89    static_cast<ViewManagerClientImpl*>(manager_)->RemoveView(id_);
90}
91
92void View::LocalDestroy() {
93  delete this;
94}
95
96}  // namespace view_manager
97}  // namespace mojo
98