• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2016 The Chromium Embedded Framework Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be found
3 // in the LICENSE file.
4 
5 #ifndef CEF_LIBCEF_BROWSER_VIEWS_PANEL_IMPL_H_
6 #define CEF_LIBCEF_BROWSER_VIEWS_PANEL_IMPL_H_
7 #pragma once
8 
9 #include "include/views/cef_fill_layout.h"
10 #include "include/views/cef_layout.h"
11 #include "include/views/cef_panel.h"
12 #include "include/views/cef_window.h"
13 
14 #include "libcef/browser/views/box_layout_impl.h"
15 #include "libcef/browser/views/fill_layout_impl.h"
16 #include "libcef/browser/views/layout_util.h"
17 #include "libcef/browser/views/view_impl.h"
18 
19 #include "base/logging.h"
20 
21 // Helpers for template boiler-plate.
22 #define CEF_PANEL_IMPL_T CEF_VIEW_IMPL_T
23 #define CEF_PANEL_IMPL_A CEF_VIEW_IMPL_A
24 #define CEF_PANEL_IMPL_D CefPanelImpl<CEF_PANEL_IMPL_A>
25 
26 // Template for implementing CefPanel-derived classes. See comments in
27 // view_impl.h for a usage overview.
28 CEF_PANEL_IMPL_T class CefPanelImpl : public CEF_VIEW_IMPL_D {
29  public:
30   using ParentClass = CEF_VIEW_IMPL_D;
31 
32   // CefPanel methods. When adding new As*() methods make sure to update
33   // CefViewAdapter::GetFor() in view_adapter.cc.
AsWindow()34   CefRefPtr<CefWindow> AsWindow() override { return nullptr; }
35   CefRefPtr<CefFillLayout> SetToFillLayout() override;
36   CefRefPtr<CefBoxLayout> SetToBoxLayout(
37       const CefBoxLayoutSettings& settings) override;
38   CefRefPtr<CefLayout> GetLayout() override;
39   void Layout() override;
40   void AddChildView(CefRefPtr<CefView> view) override;
41   void AddChildViewAt(CefRefPtr<CefView> view, int index) override;
42   void ReorderChildView(CefRefPtr<CefView> view, int index) override;
43   void RemoveChildView(CefRefPtr<CefView> view) override;
44   void RemoveAllChildViews() override;
45   size_t GetChildViewCount() override;
46   CefRefPtr<CefView> GetChildViewAt(int index) override;
47 
48   // CefView methods:
AsPanel()49   CefRefPtr<CefPanel> AsPanel() override { return this; }
50 
51   // CefViewAdapter methods:
GetDebugInfo(base::DictionaryValue * info,bool include_children)52   void GetDebugInfo(base::DictionaryValue* info,
53                     bool include_children) override {
54     ParentClass::GetDebugInfo(info, include_children);
55     if (include_children) {
56       const size_t count = ParentClass::content_view()->children().size();
57       if (count > 0U) {
58         std::unique_ptr<base::ListValue> children(new base::ListValue());
59 
60         for (size_t i = 0U; i < count; ++i) {
61           views::View* view = ParentClass::content_view()->children()[i];
62           CefViewAdapter* adapter = CefViewAdapter::GetFor(view);
63           if (adapter) {
64             std::unique_ptr<base::DictionaryValue> child_info(
65                 new base::DictionaryValue());
66             adapter->GetDebugInfo(child_info.get(), include_children);
67             children->Append(std::move(child_info));
68           }
69         }
70 
71         info->Set("children", std::move(children));
72       }
73     }
74   }
75 
76  protected:
77   // Create a new implementation object.
78   // Always call Initialize() after creation.
79   // |delegate| may be nullptr.
CefPanelImpl(CefRefPtr<CefViewDelegateClass> delegate)80   explicit CefPanelImpl(CefRefPtr<CefViewDelegateClass> delegate)
81       : ParentClass(delegate) {}
82 
Initialize()83   void Initialize() override {
84     ParentClass::Initialize();
85 
86     // Create the default layout object.
87     SetToFillLayout();
88   }
89 };
90 
SetToFillLayout()91 CEF_PANEL_IMPL_T CefRefPtr<CefFillLayout> CEF_PANEL_IMPL_D::SetToFillLayout() {
92   CEF_REQUIRE_VALID_RETURN(nullptr);
93   return CefFillLayoutImpl::Create(ParentClass::content_view());
94 }
95 
SetToBoxLayout(const CefBoxLayoutSettings & settings)96 CEF_PANEL_IMPL_T CefRefPtr<CefBoxLayout> CEF_PANEL_IMPL_D::SetToBoxLayout(
97     const CefBoxLayoutSettings& settings) {
98   CEF_REQUIRE_VALID_RETURN(nullptr);
99   return CefBoxLayoutImpl::Create(settings, ParentClass::content_view());
100 }
101 
GetLayout()102 CEF_PANEL_IMPL_T CefRefPtr<CefLayout> CEF_PANEL_IMPL_D::GetLayout() {
103   CEF_REQUIRE_VALID_RETURN(nullptr);
104   return layout_util::GetFor(ParentClass::content_view());
105 }
106 
Layout()107 CEF_PANEL_IMPL_T void CEF_PANEL_IMPL_D::Layout() {
108   CEF_REQUIRE_VALID_RETURN_VOID();
109   return ParentClass::root_view()->Layout();
110 }
111 
AddChildView(CefRefPtr<CefView> view)112 CEF_PANEL_IMPL_T void CEF_PANEL_IMPL_D::AddChildView(CefRefPtr<CefView> view) {
113   CEF_REQUIRE_VALID_RETURN_VOID();
114   DCHECK(view.get());
115   DCHECK(view->IsValid());
116   if (!view.get() || !view->IsValid())
117     return;
118 
119   auto* view_ptr = view->IsAttached()
120                        ? view_util::GetFor(view)
121                        : view_util::PassOwnership(view).release();
122   DCHECK(view_ptr);
123   ParentClass::content_view()->AddChildView(view_ptr);
124 }
125 
AddChildViewAt(CefRefPtr<CefView> view,int index)126 CEF_PANEL_IMPL_T void CEF_PANEL_IMPL_D::AddChildViewAt(CefRefPtr<CefView> view,
127                                                        int index) {
128   CEF_REQUIRE_VALID_RETURN_VOID();
129   DCHECK(view.get());
130   DCHECK(view->IsValid());
131   DCHECK_GE(index, 0);
132   DCHECK_LE(static_cast<unsigned int>(index),
133             ParentClass::content_view()->children().size());
134   if (!view.get() || !view->IsValid() || index < 0 ||
135       (static_cast<unsigned int>(index) >
136        ParentClass::content_view()->children().size())) {
137     return;
138   }
139 
140   auto* view_ptr = view->IsAttached()
141                        ? view_util::GetFor(view)
142                        : view_util::PassOwnership(view).release();
143   DCHECK(view_ptr);
144   ParentClass::content_view()->AddChildViewAt(view_ptr, index);
145 }
146 
ReorderChildView(CefRefPtr<CefView> view,int index)147 CEF_PANEL_IMPL_T void CEF_PANEL_IMPL_D::ReorderChildView(
148     CefRefPtr<CefView> view,
149     int index) {
150   CEF_REQUIRE_VALID_RETURN_VOID();
151   DCHECK(view.get());
152   DCHECK(view->IsValid());
153   DCHECK(view->IsAttached());
154   if (!view.get() || !view->IsValid() || !view->IsAttached())
155     return;
156 
157   views::View* view_ptr = view_util::GetFor(view);
158   DCHECK(view_ptr);
159   DCHECK_EQ(view_ptr->parent(), ParentClass::content_view());
160   if (!view_ptr || view_ptr->parent() != ParentClass::content_view())
161     return;
162 
163   ParentClass::content_view()->ReorderChildView(view_ptr, index);
164 }
165 
RemoveChildView(CefRefPtr<CefView> view)166 CEF_PANEL_IMPL_T void CEF_PANEL_IMPL_D::RemoveChildView(
167     CefRefPtr<CefView> view) {
168   CEF_REQUIRE_VALID_RETURN_VOID();
169   DCHECK(view.get());
170   DCHECK(view->IsValid());
171   DCHECK(view->IsAttached());
172   if (!view.get() || !view->IsValid() || !view->IsAttached())
173     return;
174 
175   views::View* view_ptr = view_util::GetFor(view);
176   DCHECK(view_ptr);
177   DCHECK_EQ(view_ptr->parent(), ParentClass::content_view());
178   if (!view_ptr || view_ptr->parent() != ParentClass::content_view())
179     return;
180 
181   ParentClass::content_view()->RemoveChildView(view_ptr);
182   view_util::ResumeOwnership(view);
183 }
184 
RemoveAllChildViews()185 CEF_PANEL_IMPL_T void CEF_PANEL_IMPL_D::RemoveAllChildViews() {
186   CEF_REQUIRE_VALID_RETURN_VOID();
187   while (!ParentClass::content_view()->children().empty()) {
188     CefRefPtr<CefView> view = view_util::GetFor(
189         ParentClass::content_view()->children().front(), false);
190     RemoveChildView(view);
191   }
192 }
193 
GetChildViewCount()194 CEF_PANEL_IMPL_T size_t CEF_PANEL_IMPL_D::GetChildViewCount() {
195   CEF_REQUIRE_VALID_RETURN(0U);
196   return ParentClass::content_view()->children().size();
197 }
198 
GetChildViewAt(int index)199 CEF_PANEL_IMPL_T CefRefPtr<CefView> CEF_PANEL_IMPL_D::GetChildViewAt(
200     int index) {
201   CEF_REQUIRE_VALID_RETURN(nullptr);
202   DCHECK_GE(index, 0);
203   DCHECK_LT(static_cast<unsigned int>(index),
204             ParentClass::content_view()->children().size());
205   if (index < 0 || (static_cast<unsigned int>(index) >=
206                     ParentClass::content_view()->children().size()))
207     return nullptr;
208 
209   CefRefPtr<CefView> view =
210       view_util::GetFor(ParentClass::content_view()->children()[index], false);
211   DCHECK(view);
212   return view;
213 }
214 
215 #endif  // CEF_LIBCEF_BROWSER_VIEWS_PANEL_IMPL_H_
216