AUI Framework  master
Cross-platform module-based framework for developing C++20 desktop applications
Declarative.h
1/*
2 * AUI Framework - Declarative UI toolkit for modern C++20
3 * Copyright (C) 2020-2024 Alex2772 and Contributors
4 *
5 * SPDX-License-Identifier: MPL-2.0
6 *
7 * This Source Code Form is subject to the terms of the Mozilla Public
8 * License, v. 2.0. If a copy of the MPL was not distributed with this
9 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
10 */
11
12#pragma once
13
14#include <AUI/View/AViewContainer.h>
15#include <AUI/Util/kAUI.h>
16#include <AUI/Traits/callables.h>
17#include <AUI/Traits/parameter_pack.h>
18#include <AUI/ASS/ASS.h>
19
20
21namespace aui::ui_building {
22
23 using View = _<AView>;
24 using ViewContainer = _<AViewContainer>;
25 using ViewGroup = AVector<_<AView>>;
26 using ViewOrViewGroup = std::variant<_<AView>, AVector<_<AView>>>;
27
28 template<typename ViewFactory>
29 struct view_helper {
30 public:
31 view_helper() {}
32
33 operator View() const {
34 return asViewFactory()->operator()();
35 }
36 operator ViewContainer() const {
37 return asViewFactory()->operator()();
38 }
39 auto operator<<(const AString& assEntry) const {
40 return asViewFactory()->operator()() << assEntry;
41 }
42 template<typename T>
43 auto operator^(const T& t) const {
44 return asViewFactory()->operator()() ^ t;
45 }
46 template<typename T>
47 auto operator+(const T& t) const {
48 return asViewFactory()->operator()() + t;
49 }
50
51 template<typename T>
52 auto operator^(T&& t) const {
53 return asViewFactory()->operator()() ^ std::forward<T>(t);
54 }
55 template<typename T>
56 auto operator&&(T&& t) const {
57 return asViewFactory()->operator()() && std::forward<T>(t);
58 }
59 template<typename T>
60 auto operator+(T&& t) const {
61 return asViewFactory()->operator()() + std::forward<T>(t);
62 }
63
64 auto operator->() const {
65 return asViewFactory()->operator()();
66 }
67
68
69 template<typename SignalField, typename Object, typename Function>
70 auto connect(SignalField&& signalField, Object&& object, Function&& function) {
71 return asViewFactory()->operator()().connect(std::forward<SignalField>(signalField), std::forward<Object>(object), std::forward<Function>(function));
72 }
73
74 template<typename Object, typename Function>
75 auto clicked(Object&& object, Function&& function) {
76 return connect(&AView::clicked, std::forward<Object>(object), std::forward<Function>(function));
77 }
78
79 template<typename SignalField, typename Function>
80 auto connect(SignalField&& signalField, Function&& function) {
81 return asViewFactory()->operator()().connect(std::forward<SignalField>(signalField), std::forward<Function>(function));
82 }
83 private:
84 [[nodiscard]]
85 ViewFactory* asViewFactory() const {
86 return const_cast<ViewFactory*>(static_cast<const ViewFactory*>(this));
87 }
88 };
89
90 template<typename View>
91 struct view: view_helper<view<View>> {
92
93 public:
94 template<typename... Args>
95 view(Args&&... args): mView(_new<View>(std::forward<Args>(args)...)) {}
96
97 _<View>& operator()() {
98 return mView;
99 }
100
101 operator _<View>&() {
102 return mView;
103 }
104
105 private:
106 _<View> mView;
107 };
108
109 static_assert(std::is_convertible_v<view<AView>, View>, "declarative view wrapper is not convertible to _<AView>");
110
111 template<typename Layout, aui::derived_from<AViewContainer> Container = AViewContainer>
113 private:
114 AVector<View> mViews;
115
116 public:
117 template<typename... Views>
118 layouted_container_factory_impl(Views&&... views) {
119 mViews.reserve(sizeof...(views));
120 aui::parameter_pack::for_each([this](auto&& item) {
121 using type = decltype(item);
122 constexpr bool isViewGroup = std::is_convertible_v<type, ViewGroup>;
123 constexpr bool isView = std::is_convertible_v<type, View>;
124 constexpr bool isInvokable = std::is_invocable_v<type>;
125
126 static_assert(isViewGroup || isView || isInvokable, "the item is neither convertible to View nor ViewGroup, nor invokable");
127
128 if constexpr (isViewGroup) {
129 auto asViewGroup = ViewGroup(item);
130 mViews << std::move(asViewGroup);
131 } else if constexpr (isView) {
132 auto asView = View(item);
133 mViews << std::move(asView);
134 } else if constexpr(isInvokable) {
135 mViews << item();
136 }
137 }, std::forward<Views>(views)...);
138 }
139
140 _<Container> operator()() {
141 auto c = _new<Container>();
142 if constexpr(!std::is_same_v<Layout, std::nullopt_t>) {
143 c->setLayout(std::make_unique<Layout>());
144 }
145 c->setViews(std::move(mViews));
146 return c;
147 }
148 };
149
150
151 template<typename Layout, aui::derived_from<AViewContainer> Container = AViewContainer>
153 public:
155
156 struct Expanding: view_helper<Expanding>, layouted_container_factory_impl<Layout, Container> {
157 public:
158 template<typename... Views>
159 Expanding(Views&&... views): layouted_container_factory_impl<Layout>(std::forward<Views>(views)...) {
160
161 }
162
163 _<Container> operator()() {
165 it->setExpanding();
166 };
167 }
168 };
169 };
170
171 template <typename Layout, aui::derived_from<AViewContainer> Container = AViewContainer>
172 struct layouted_container_factory : view_helper<layouted_container_factory<Layout, Container>>,
174 template <typename... Views>
175 layouted_container_factory(Views&&... views)
177 };
178}
179
180namespace declarative {
181
199 struct Style {
200 public:
201 Style(std::initializer_list<Rule> rules): mStylesheet(_new<AStylesheet>(AStylesheet(rules))) {
202
203 }
204
205 Style& operator()(AVector<_<AView>> views) {
206 for (const auto& view : views) {
207 AUI_ASSERTX(view->extraStylesheet() == nullptr, "extra stylesheet already specified");
208 view->setExtraStylesheet(mStylesheet);
209 }
210 mViews = std::move(views);
211 return *this;
212 }
213
214 operator AVector<_<AView>>() noexcept {
215 return std::move(mViews);
216 }
217
218 private:
219 _<AStylesheet> mStylesheet;
220 AVector<_<AView>> mViews;
221 };
222}
Represents a Unicode character string.
Definition: AString.h:37
Definition: AStylesheet.h:21
A std::vector with AUI extensions.
Definition: AVector.h:38
emits clicked
Left mouse button clicked.
Definition: AView.h:1073
An std::weak_ptr with AUI extensions.
Definition: SharedPtrTypes.h:177
API_AUI_CORE const ACommandLineArgs & args() noexcept
Definition: OSAndroid.cpp:29
#define let
Performs multiple operations on a single object without repeating its name (in place) This function c...
Definition: kAUI.h:262
#define AUI_ASSERTX(condition, what)
Asserts that the passed condition evaluates to true. Adds extra message string.
Definition: Assert.h:74
Definition: Type.h:16
Definition: Declarative.h:29
Definition: Declarative.h:91
Extra styles wrapper.
Definition: Declarative.h:199