1/**************************************************************************/
2/* asset_library_editor_plugin.h */
3/**************************************************************************/
4/* This file is part of: */
5/* GODOT ENGINE */
6/* https://godotengine.org */
7/**************************************************************************/
8/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */
9/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */
10/* */
11/* Permission is hereby granted, free of charge, to any person obtaining */
12/* a copy of this software and associated documentation files (the */
13/* "Software"), to deal in the Software without restriction, including */
14/* without limitation the rights to use, copy, modify, merge, publish, */
15/* distribute, sublicense, and/or sell copies of the Software, and to */
16/* permit persons to whom the Software is furnished to do so, subject to */
17/* the following conditions: */
18/* */
19/* The above copyright notice and this permission notice shall be */
20/* included in all copies or substantial portions of the Software. */
21/* */
22/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
23/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
24/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */
25/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
26/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
27/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
28/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
29/**************************************************************************/
30
31#ifndef ASSET_LIBRARY_EDITOR_PLUGIN_H
32#define ASSET_LIBRARY_EDITOR_PLUGIN_H
33
34#include "editor/editor_asset_installer.h"
35#include "editor/editor_plugin.h"
36#include "editor/editor_plugin_settings.h"
37#include "scene/gui/box_container.h"
38#include "scene/gui/check_box.h"
39#include "scene/gui/grid_container.h"
40#include "scene/gui/line_edit.h"
41#include "scene/gui/link_button.h"
42#include "scene/gui/margin_container.h"
43#include "scene/gui/option_button.h"
44#include "scene/gui/panel_container.h"
45#include "scene/gui/progress_bar.h"
46#include "scene/gui/rich_text_label.h"
47#include "scene/gui/scroll_container.h"
48#include "scene/gui/separator.h"
49#include "scene/gui/tab_container.h"
50#include "scene/gui/texture_button.h"
51#include "scene/main/http_request.h"
52
53class EditorFileDialog;
54class MenuButton;
55
56class EditorAssetLibraryItem : public PanelContainer {
57 GDCLASS(EditorAssetLibraryItem, PanelContainer);
58
59 TextureButton *icon = nullptr;
60 LinkButton *title = nullptr;
61 LinkButton *category = nullptr;
62 LinkButton *author = nullptr;
63 TextureRect *stars[5];
64 Label *price = nullptr;
65
66 int asset_id = 0;
67 int category_id = 0;
68 int author_id = 0;
69
70 void _asset_clicked();
71 void _category_clicked();
72 void _author_clicked();
73
74 void set_image(int p_type, int p_index, const Ref<Texture2D> &p_image);
75
76protected:
77 void _notification(int p_what);
78 static void _bind_methods();
79
80public:
81 void configure(const String &p_title, int p_asset_id, const String &p_category, int p_category_id, const String &p_author, int p_author_id, const String &p_cost);
82
83 EditorAssetLibraryItem();
84};
85
86class EditorAssetLibraryItemDescription : public ConfirmationDialog {
87 GDCLASS(EditorAssetLibraryItemDescription, ConfirmationDialog);
88
89 EditorAssetLibraryItem *item = nullptr;
90 RichTextLabel *description = nullptr;
91 ScrollContainer *previews = nullptr;
92 HBoxContainer *preview_hb = nullptr;
93 PanelContainer *previews_bg = nullptr;
94
95 struct Preview {
96 int id = 0;
97 bool is_video = false;
98 String video_link;
99 Button *button = nullptr;
100 Ref<Texture2D> image;
101 };
102
103 Vector<Preview> preview_images;
104 TextureRect *preview = nullptr;
105
106 void set_image(int p_type, int p_index, const Ref<Texture2D> &p_image);
107
108 int asset_id = 0;
109 String download_url;
110 String title;
111 String sha256;
112 Ref<Texture2D> icon;
113
114 void _link_click(const String &p_url);
115 void _preview_click(int p_id);
116
117protected:
118 void _notification(int p_what);
119 static void _bind_methods();
120
121public:
122 void configure(const String &p_title, int p_asset_id, const String &p_category, int p_category_id, const String &p_author, int p_author_id, const String &p_cost, int p_version, const String &p_version_string, const String &p_description, const String &p_download_url, const String &p_browse_url, const String &p_sha256_hash);
123 void add_preview(int p_id, bool p_video, const String &p_url);
124
125 String get_title() { return title; }
126 Ref<Texture2D> get_preview_icon() { return icon; }
127 String get_download_url() { return download_url; }
128 int get_asset_id() { return asset_id; }
129 String get_sha256() { return sha256; }
130 EditorAssetLibraryItemDescription();
131};
132
133class EditorAssetLibraryItemDownload : public MarginContainer {
134 GDCLASS(EditorAssetLibraryItemDownload, MarginContainer);
135
136 PanelContainer *panel = nullptr;
137 TextureRect *icon = nullptr;
138 Label *title = nullptr;
139 ProgressBar *progress = nullptr;
140 Button *install_button = nullptr;
141 Button *retry_button = nullptr;
142 TextureButton *dismiss_button = nullptr;
143
144 AcceptDialog *download_error = nullptr;
145 HTTPRequest *download = nullptr;
146 String host;
147 String sha256;
148 Label *status = nullptr;
149
150 int prev_status;
151
152 int asset_id = 0;
153
154 bool external_install;
155
156 EditorAssetInstaller *asset_installer = nullptr;
157
158 void _close();
159 void _make_request();
160 void _http_download_completed(int p_status, int p_code, const PackedStringArray &headers, const PackedByteArray &p_data);
161
162protected:
163 void _notification(int p_what);
164 static void _bind_methods();
165
166public:
167 void set_external_install(bool p_enable) { external_install = p_enable; }
168 int get_asset_id() { return asset_id; }
169 void configure(const String &p_title, int p_asset_id, const Ref<Texture2D> &p_preview, const String &p_download_url, const String &p_sha256_hash);
170
171 bool can_install() const;
172 void install();
173
174 EditorAssetLibraryItemDownload();
175};
176
177class EditorAssetLibrary : public PanelContainer {
178 GDCLASS(EditorAssetLibrary, PanelContainer);
179
180 String host;
181
182 EditorFileDialog *asset_open = nullptr;
183 EditorAssetInstaller *asset_installer = nullptr;
184
185 void _asset_open();
186 void _asset_file_selected(const String &p_file);
187 void _update_repository_options();
188
189 PanelContainer *library_scroll_bg = nullptr;
190 ScrollContainer *library_scroll = nullptr;
191 VBoxContainer *library_vb = nullptr;
192 Label *library_info = nullptr;
193 VBoxContainer *library_error = nullptr;
194 Label *library_error_label = nullptr;
195 Button *library_error_retry = nullptr;
196 LineEdit *filter = nullptr;
197 Timer *filter_debounce_timer = nullptr;
198 OptionButton *categories = nullptr;
199 OptionButton *repository = nullptr;
200 OptionButton *sort = nullptr;
201 HBoxContainer *error_hb = nullptr;
202 TextureRect *error_tr = nullptr;
203 Label *error_label = nullptr;
204 MenuButton *support = nullptr;
205
206 HBoxContainer *contents = nullptr;
207
208 HBoxContainer *asset_top_page = nullptr;
209 GridContainer *asset_items = nullptr;
210 HBoxContainer *asset_bottom_page = nullptr;
211
212 HTTPRequest *request = nullptr;
213
214 bool templates_only;
215 bool initial_loading;
216
217 enum Support {
218 SUPPORT_OFFICIAL,
219 SUPPORT_COMMUNITY,
220 SUPPORT_TESTING,
221 SUPPORT_MAX
222 };
223
224 enum SortOrder {
225 SORT_UPDATED,
226 SORT_UPDATED_REVERSE,
227 SORT_NAME,
228 SORT_NAME_REVERSE,
229 SORT_COST,
230 SORT_COST_REVERSE,
231 SORT_MAX
232 };
233
234 static const char *sort_key[SORT_MAX];
235 static const char *sort_text[SORT_MAX];
236 static const char *support_key[SUPPORT_MAX];
237 static const char *support_text[SUPPORT_MAX];
238
239 ///MainListing
240
241 enum ImageType {
242 IMAGE_QUEUE_ICON,
243 IMAGE_QUEUE_THUMBNAIL,
244 IMAGE_QUEUE_SCREENSHOT,
245
246 };
247
248 struct ImageQueue {
249 bool active = false;
250 int queue_id = 0;
251 ImageType image_type = ImageType::IMAGE_QUEUE_ICON;
252 int image_index = 0;
253 String image_url;
254 HTTPRequest *request = nullptr;
255 ObjectID target;
256 };
257
258 int last_queue_id;
259 HashMap<int, ImageQueue> image_queue;
260
261 void _image_update(bool use_cache, bool final, const PackedByteArray &p_data, int p_queue_id);
262 void _image_request_completed(int p_status, int p_code, const PackedStringArray &headers, const PackedByteArray &p_data, int p_queue_id);
263 void _request_image(ObjectID p_for, String p_image_url, ImageType p_type, int p_image_index);
264 void _update_image_queue();
265
266 HBoxContainer *_make_pages(int p_page, int p_page_count, int p_page_len, int p_total_items, int p_current_items);
267
268 //
269 EditorAssetLibraryItemDescription *description = nullptr;
270 //
271
272 enum RequestType {
273 REQUESTING_NONE,
274 REQUESTING_CONFIG,
275 REQUESTING_SEARCH,
276 REQUESTING_ASSET,
277 };
278
279 RequestType requesting;
280 Dictionary category_map;
281
282 ScrollContainer *downloads_scroll = nullptr;
283 HBoxContainer *downloads_hb = nullptr;
284
285 void _install_asset();
286
287 void _select_author(int p_id);
288 void _select_category(int p_id);
289 void _select_asset(int p_id);
290
291 void _manage_plugins();
292
293 void _search(int p_page = 0);
294 void _rerun_search(int p_ignore);
295 void _search_text_changed(const String &p_text = "");
296 void _search_text_submitted(const String &p_text = "");
297 void _api_request(const String &p_request, RequestType p_request_type, const String &p_arguments = "");
298 void _http_request_completed(int p_status, int p_code, const PackedStringArray &headers, const PackedByteArray &p_data);
299 void _filter_debounce_timer_timeout();
300 void _request_current_config();
301 EditorAssetLibraryItemDownload *_get_asset_in_progress(int p_asset_id) const;
302
303 void _repository_changed(int p_repository_id);
304 void _support_toggled(int p_support);
305
306 void _install_external_asset(String p_zip_path, String p_title);
307
308 void _update_asset_items_columns();
309
310 friend class EditorAssetLibraryItemDescription;
311 friend class EditorAssetLibraryItem;
312
313protected:
314 static void _bind_methods();
315 void _notification(int p_what);
316 virtual void shortcut_input(const Ref<InputEvent> &p_event) override;
317
318public:
319 void disable_community_support();
320
321 EditorAssetLibrary(bool p_templates_only = false);
322};
323
324class AssetLibraryEditorPlugin : public EditorPlugin {
325 GDCLASS(AssetLibraryEditorPlugin, EditorPlugin);
326
327 EditorAssetLibrary *addon_library = nullptr;
328
329public:
330 static bool is_available();
331
332 virtual String get_name() const override { return "AssetLib"; }
333 bool has_main_screen() const override { return true; }
334 virtual void edit(Object *p_object) override {}
335 virtual bool handles(Object *p_object) const override { return false; }
336 virtual void make_visible(bool p_visible) override;
337 //virtual bool get_remove_list(List<Node*> *p_list) { return canvas_item_editor->get_remove_list(p_list); }
338 //virtual Dictionary get_state() const;
339 //virtual void set_state(const Dictionary& p_state);
340
341 AssetLibraryEditorPlugin();
342 ~AssetLibraryEditorPlugin();
343};
344
345#endif // ASSET_LIBRARY_EDITOR_PLUGIN_H
346