summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore2
-rw-r--r--core/io/resource_import.cpp29
-rw-r--r--core/io/resource_import.h7
-rw-r--r--core/io/resource_loader.cpp25
-rw-r--r--core/io/resource_loader.h2
-rw-r--r--core/variant_op.cpp357
-rw-r--r--doc/classes/EditorImportPlugin.xml54
-rw-r--r--editor/collada/collada.cpp2
-rw-r--r--editor/editor_file_system.cpp16
-rw-r--r--editor/editor_file_system.h8
-rw-r--r--editor/editor_settings.cpp72
-rw-r--r--editor/editor_themes.cpp27
-rw-r--r--editor/import/editor_import_collada.cpp15
-rw-r--r--editor/import/resource_importer_scene.cpp8
-rw-r--r--editor/import/resource_importer_scene.h2
-rw-r--r--editor/plugins/canvas_item_editor_plugin.cpp6
-rw-r--r--editor/plugins/spatial_editor_plugin.cpp69
-rw-r--r--editor/spatial_editor_gizmos.cpp34
-rw-r--r--editor/spatial_editor_gizmos.h3
-rw-r--r--main/main.cpp12
-rw-r--r--platform/haiku/detect.py15
-rw-r--r--platform/osx/SCsub13
-rw-r--r--platform/osx/detect.py11
-rw-r--r--platform/windows/SCsub11
-rw-r--r--platform/windows/detect.py12
-rw-r--r--platform/x11/SCsub9
-rw-r--r--platform/x11/detect.py13
-rw-r--r--platform/x11/os_x11.cpp10
-rw-r--r--scene/resources/dynamic_font.cpp19
29 files changed, 600 insertions, 263 deletions
diff --git a/.gitignore b/.gitignore
index 315dc7950f..d27b8b2b4b 100644
--- a/.gitignore
+++ b/.gitignore
@@ -80,6 +80,8 @@ build/
bld/
[Bb]in/
[Oo]bj/
+*.debug
+*.dSYM
# MSTest test Results
[Tt]est[Rr]esult*/
diff --git a/core/io/resource_import.cpp b/core/io/resource_import.cpp
index be486a86a3..bc7ea47762 100644
--- a/core/io/resource_import.cpp
+++ b/core/io/resource_import.cpp
@@ -87,6 +87,8 @@ Error ResourceFormatImporter::_get_path_and_type(const String &p_path, PathAndTy
path_found = true; //first match must have priority
} else if (assign == "type") {
r_path_and_type.type = value;
+ } else if (assign == "importer") {
+ r_path_and_type.importer = value;
} else if (assign == "valid") {
if (r_valid) {
*r_valid = value;
@@ -184,6 +186,29 @@ bool ResourceFormatImporter::can_be_imported(const String &p_path) const {
return ResourceFormatLoader::recognize_path(p_path);
}
+int ResourceFormatImporter::get_import_order(const String &p_path) const {
+
+ Ref<ResourceImporter> importer;
+
+ if (FileAccess::exists(p_path + ".import")) {
+
+ PathAndType pat;
+ Error err = _get_path_and_type(p_path, pat);
+
+ if (err == OK) {
+ importer = get_importer_by_name(pat.importer);
+ }
+ } else {
+
+ importer = get_importer_by_extension(p_path.get_extension().to_lower());
+ }
+
+ if (importer.is_valid())
+ return importer->get_import_order();
+
+ return 0;
+}
+
bool ResourceFormatImporter::handles_type(const String &p_type) const {
for (Set<Ref<ResourceImporter> >::Element *E = importers.front(); E; E = E->next()) {
@@ -291,7 +316,7 @@ void ResourceFormatImporter::get_dependencies(const String &p_path, List<String>
return ResourceLoader::get_dependencies(pat.path, p_dependencies, p_add_types);
}
-Ref<ResourceImporter> ResourceFormatImporter::get_importer_by_name(const String &p_name) {
+Ref<ResourceImporter> ResourceFormatImporter::get_importer_by_name(const String &p_name) const {
for (Set<Ref<ResourceImporter> >::Element *E = importers.front(); E; E = E->next()) {
if (E->get()->get_importer_name() == p_name) {
@@ -315,7 +340,7 @@ void ResourceFormatImporter::get_importers_for_extension(const String &p_extensi
}
}
-Ref<ResourceImporter> ResourceFormatImporter::get_importer_by_extension(const String &p_extension) {
+Ref<ResourceImporter> ResourceFormatImporter::get_importer_by_extension(const String &p_extension) const {
Ref<ResourceImporter> importer;
float priority = 0;
diff --git a/core/io/resource_import.h b/core/io/resource_import.h
index b10255fbab..28489b5d34 100644
--- a/core/io/resource_import.h
+++ b/core/io/resource_import.h
@@ -38,6 +38,7 @@ class ResourceFormatImporter : public ResourceFormatLoader {
struct PathAndType {
String path;
String type;
+ String importer;
};
Error _get_path_and_type(const String &p_path, PathAndType &r_path_and_type, bool *r_valid = NULL) const;
@@ -58,14 +59,15 @@ public:
virtual void get_dependencies(const String &p_path, List<String> *p_dependencies, bool p_add_types = false);
virtual bool can_be_imported(const String &p_path) const;
+ virtual int get_import_order(const String &p_path) const;
String get_internal_resource_path(const String &p_path) const;
void get_internal_resource_path_list(const String &p_path, List<String> *r_paths);
void add_importer(const Ref<ResourceImporter> &p_importer) { importers.insert(p_importer); }
void remove_importer(const Ref<ResourceImporter> &p_importer) { importers.erase(p_importer); }
- Ref<ResourceImporter> get_importer_by_name(const String &p_name);
- Ref<ResourceImporter> get_importer_by_extension(const String &p_extension);
+ Ref<ResourceImporter> get_importer_by_name(const String &p_name) const;
+ Ref<ResourceImporter> get_importer_by_extension(const String &p_extension) const;
void get_importers_for_extension(const String &p_extension, List<Ref<ResourceImporter> > *r_importers);
String get_import_base_path(const String &p_for_file) const;
@@ -82,6 +84,7 @@ public:
virtual String get_save_extension() const = 0;
virtual String get_resource_type() const = 0;
virtual float get_priority() const { return 1.0; }
+ virtual int get_import_order() const { return 0; }
struct ImportOption {
PropertyInfo option;
diff --git a/core/io/resource_loader.cpp b/core/io/resource_loader.cpp
index 4f266df43e..89cb4a22c2 100644
--- a/core/io/resource_loader.cpp
+++ b/core/io/resource_loader.cpp
@@ -308,6 +308,31 @@ void ResourceLoader::add_resource_format_loader(ResourceFormatLoader *p_format_l
}
}
+int ResourceLoader::get_import_order(const String &p_path) {
+
+ String path = _path_remap(p_path);
+
+ String local_path;
+ if (path.is_rel_path())
+ local_path = "res://" + path;
+ else
+ local_path = ProjectSettings::get_singleton()->localize_path(path);
+
+ for (int i = 0; i < loader_count; i++) {
+
+ if (!loader[i]->recognize_path(local_path))
+ continue;
+ /*
+ if (p_type_hint!="" && !loader[i]->handles_type(p_type_hint))
+ continue;
+ */
+
+ return loader[i]->get_import_order(p_path);
+ }
+
+ return 0;
+}
+
bool ResourceLoader::is_import_valid(const String &p_path) {
String path = _path_remap(p_path);
diff --git a/core/io/resource_loader.h b/core/io/resource_loader.h
index a71a568569..5deffbca1a 100644
--- a/core/io/resource_loader.h
+++ b/core/io/resource_loader.h
@@ -67,6 +67,7 @@ public:
virtual void get_dependencies(const String &p_path, List<String> *p_dependencies, bool p_add_types = false);
virtual Error rename_dependencies(const String &p_path, const Map<String, String> &p_map) { return OK; }
virtual bool is_import_valid(const String &p_path) const { return true; }
+ virtual int get_import_order(const String &p_path) const { return 0; }
virtual ~ResourceFormatLoader() {}
};
@@ -110,6 +111,7 @@ public:
static void get_dependencies(const String &p_path, List<String> *p_dependencies, bool p_add_types = false);
static Error rename_dependencies(const String &p_path, const Map<String, String> &p_map);
static bool is_import_valid(const String &p_path);
+ static int get_import_order(const String &p_path);
static void set_timestamp_on_load(bool p_timestamp) { timestamp_on_load = p_timestamp; }
diff --git a/core/variant_op.cpp b/core/variant_op.cpp
index 5d47936679..1c5a4ce8d0 100644
--- a/core/variant_op.cpp
+++ b/core/variant_op.cpp
@@ -164,50 +164,50 @@ bool Variant::booleanize() const {
return; \
}
-#define DEFAULT_OP_NUM(m_prefix, m_op_name, m_name, m_op, m_type) \
- CASE_TYPE(m_prefix, m_op_name, m_name) { \
- switch (p_b.type) { \
- case INT: _RETURN(p_a._data.m_type m_op p_b._data._int); \
- case REAL: _RETURN(p_a._data.m_type m_op p_b._data._real); \
- default: {} \
- } \
- r_valid = false; \
- return; \
+#define DEFAULT_OP_NUM(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == INT) _RETURN(p_a._data.m_type m_op p_b._data._int); \
+ if (p_b.type == REAL) _RETURN(p_a._data.m_type m_op p_b._data._real); \
+ \
+ _RETURN_FAIL \
+ };
+
+#define DEFAULT_OP_NUM_NULL(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == INT) _RETURN(p_a._data.m_type m_op p_b._data._int); \
+ if (p_b.type == REAL) _RETURN(p_a._data.m_type m_op p_b._data._real); \
+ if (p_b.type == NIL) _RETURN(!p_b.type m_op NIL); \
+ \
+ _RETURN_FAIL \
};
#ifdef DEBUG_ENABLED
#define DEFAULT_OP_NUM_DIV(m_prefix, m_op_name, m_name, m_type) \
CASE_TYPE(m_prefix, m_op_name, m_name) { \
- switch (p_b.type) { \
- case INT: { \
- if (p_b._data._int == 0) { \
- r_valid = false; \
- _RETURN("Division By Zero"); \
- } \
- _RETURN(p_a._data.m_type / p_b._data._int); \
+ if (p_b.type == INT) { \
+ if (p_b._data._int == 0) { \
+ r_valid = false; \
+ _RETURN("Division By Zero"); \
} \
- case REAL: { \
- if (p_b._data._real == 0) { \
- r_valid = false; \
- _RETURN("Division By Zero"); \
- } \
- _RETURN(p_a._data.m_type / p_b._data._real); \
+ _RETURN(p_a._data.m_type / p_b._data._int); \
+ } \
+ if (p_b.type == REAL) { \
+ if (p_b._data._real == 0) { \
+ r_valid = false; \
+ _RETURN("Division By Zero"); \
} \
- default: {} \
+ _RETURN(p_a._data.m_type / p_b._data._real); \
} \
- r_valid = false; \
- return; \
+ \
+ _RETURN_FAIL \
};
#else
-#define DEFAULT_OP_NUM_DIV(m_prefix, m_op_name, m_name, m_type) \
- CASE_TYPE(m_prefix, m_op_name, m_name) { \
- switch (p_b.type) { \
- case INT: _RETURN(p_a._data.m_type / p_b._data._int); \
- case REAL: _RETURN(p_a._data.m_type / p_b._data._real); \
- default: {} \
- } \
- r_valid = false; \
- return; \
+#define DEFAULT_OP_NUM_DIV(m_prefix, m_op_name, m_name, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == INT) _RETURN(p_a._data.m_type / p_b._data._int); \
+ if (p_b.type == REAL) _RETURN(p_a._data.m_type / p_b._data._real); \
+ \
+ _RETURN_FAIL \
};
#endif
@@ -221,55 +221,65 @@ bool Variant::booleanize() const {
_RETURN(p_a._data.m_type); \
};
-#define DEFAULT_OP_NUM_VEC(m_prefix, m_op_name, m_name, m_op, m_type) \
- CASE_TYPE(m_prefix, m_op_name, m_name) { \
- switch (p_b.type) { \
- case INT: _RETURN(p_a._data.m_type m_op p_b._data._int); \
- case REAL: _RETURN(p_a._data.m_type m_op p_b._data._real); \
- case VECTOR2: _RETURN(p_a._data.m_type m_op *reinterpret_cast<const Vector2 *>(p_b._data._mem)); \
- case VECTOR3: _RETURN(p_a._data.m_type m_op *reinterpret_cast<const Vector3 *>(p_b._data._mem)); \
- default: {} \
- } \
- r_valid = false; \
- return; \
+#define DEFAULT_OP_NUM_VEC(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == INT) _RETURN(p_a._data.m_type m_op p_b._data._int); \
+ if (p_b.type == REAL) _RETURN(p_a._data.m_type m_op p_b._data._real); \
+ if (p_b.type == VECTOR2) _RETURN(p_a._data.m_type m_op *reinterpret_cast<const Vector2 *>(p_b._data._mem)); \
+ if (p_b.type == VECTOR3) _RETURN(p_a._data.m_type m_op *reinterpret_cast<const Vector3 *>(p_b._data._mem)); \
+ \
+ _RETURN_FAIL \
+ };
+
+#define DEFAULT_OP_STR_REV(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == STRING) _RETURN(*reinterpret_cast<const m_type *>(p_b._data._mem) m_op *reinterpret_cast<const String *>(p_a._data._mem)); \
+ if (p_b.type == NODE_PATH) _RETURN(*reinterpret_cast<const m_type *>(p_b._data._mem) m_op *reinterpret_cast<const NodePath *>(p_a._data._mem)); \
+ \
+ _RETURN_FAIL \
};
-#define DEFAULT_OP_STR_REV(m_prefix, m_op_name, m_name, m_op, m_type) \
- CASE_TYPE(m_prefix, m_op_name, m_name) { \
- switch (p_b.type) { \
- case STRING: _RETURN(*reinterpret_cast<const m_type *>(p_b._data._mem) m_op *reinterpret_cast<const String *>(p_a._data._mem)); \
- case NODE_PATH: _RETURN(*reinterpret_cast<const m_type *>(p_b._data._mem) m_op *reinterpret_cast<const NodePath *>(p_a._data._mem)); \
- default: {} \
- } \
- r_valid = false; \
- return; \
+#define DEFAULT_OP_STR(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == STRING) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const String *>(p_b._data._mem)); \
+ if (p_b.type == NODE_PATH) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const NodePath *>(p_b._data._mem)); \
+ \
+ _RETURN_FAIL \
};
-#define DEFAULT_OP_STR(m_prefix, m_op_name, m_name, m_op, m_type) \
- CASE_TYPE(m_prefix, m_op_name, m_name) { \
- switch (p_b.type) { \
- case STRING: _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const String *>(p_b._data._mem)); \
- case NODE_PATH: _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const NodePath *>(p_b._data._mem)); \
- default: {} \
- } \
- r_valid = false; \
- return; \
+#define DEFAULT_OP_STR_NULL(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == STRING) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const String *>(p_b._data._mem)); \
+ if (p_b.type == NODE_PATH) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const NodePath *>(p_b._data._mem)); \
+ if (p_b.type == NIL) _RETURN(!p_b.type m_op NIL); \
+ \
+ _RETURN_FAIL \
};
#define DEFAULT_OP_LOCALMEM_REV(m_prefix, m_op_name, m_name, m_op, m_type) \
CASE_TYPE(m_prefix, m_op_name, m_name) { \
if (p_b.type == m_name) \
_RETURN(*reinterpret_cast<const m_type *>(p_b._data._mem) m_op *reinterpret_cast<const m_type *>(p_a._data._mem)); \
- r_valid = false; \
- return; \
+ \
+ _RETURN_FAIL \
};
#define DEFAULT_OP_LOCALMEM(m_prefix, m_op_name, m_name, m_op, m_type) \
CASE_TYPE(m_prefix, m_op_name, m_name) { \
if (p_b.type == m_name) \
_RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const m_type *>(p_b._data._mem)); \
- r_valid = false; \
- return; \
+ \
+ _RETURN_FAIL \
+ };
+
+#define DEFAULT_OP_LOCALMEM_NULL(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == m_name) \
+ _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const m_type *>(p_b._data._mem)); \
+ if (p_b.type == NIL) \
+ _RETURN(!p_b.type m_op NIL); \
+ \
+ _RETURN_FAIL \
};
#define DEFAULT_OP_LOCALMEM_NEG(m_prefix, m_op_name, m_name, m_type) \
@@ -282,38 +292,47 @@ bool Variant::booleanize() const {
_RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem)); \
}
-#define DEFAULT_OP_LOCALMEM_NUM(m_prefix, m_op_name, m_name, m_op, m_type) \
- CASE_TYPE(m_prefix, m_op_name, m_name) { \
- switch (p_b.type) { \
- case m_name: _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const m_type *>(p_b._data._mem)); \
- case INT: _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op p_b._data._int); \
- case REAL: _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op p_b._data._real); \
- default: {} \
- } \
- r_valid = false; \
- return; \
+#define DEFAULT_OP_LOCALMEM_NUM(m_prefix, m_op_name, m_name, m_op, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == m_name) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op *reinterpret_cast<const m_type *>(p_b._data._mem)); \
+ if (p_b.type == INT) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op p_b._data._int); \
+ if (p_b.type == REAL) _RETURN(*reinterpret_cast<const m_type *>(p_a._data._mem) m_op p_b._data._real); \
+ \
+ _RETURN_FAIL \
}
-#define DEFAULT_OP_PTR(m_op, m_name, m_sub) \
- case m_name: { \
- switch (p_b.type) { \
- case m_name: _RETURN(p_a._data.m_sub m_op p_b._data.m_sub); \
- default: {} \
- } \
- r_valid = false; \
- return; \
+#define DEFAULT_OP_PTR(m_op, m_name, m_sub) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == m_name) \
+ _RETURN(p_a._data.m_sub m_op p_b._data.m_sub); \
+ \
+ _RETURN_FAIL \
}
#define DEFAULT_OP_PTRREF(m_prefix, m_op_name, m_name, m_op, m_sub) \
CASE_TYPE(m_prefix, m_op_name, m_name) { \
if (p_b.type == m_name) \
_RETURN(*p_a._data.m_sub m_op *p_b._data.m_sub); \
- r_valid = false; \
- return; \
+ \
+ _RETURN_FAIL \
}
-#define DEFAULT_OP_ARRAY_EQ(m_prefix, m_op_name, m_name, m_type) \
- DEFAULT_OP_ARRAY_OP(m_prefix, m_op_name, m_name, m_type, !=, !=, true, false, false)
+#define DEFAULT_OP_PTRREF_NULL(m_prefix, m_op_name, m_name, m_op, m_sub) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == m_name) \
+ _RETURN(*p_a._data.m_sub m_op *p_b._data.m_sub); \
+ if (p_b.type == NIL) \
+ _RETURN(!p_b.type m_op NIL); \
+ \
+ _RETURN_FAIL \
+ }
+
+#define DEFAULT_OP_ARRAY_EQ(m_prefix, m_op_name, m_name, m_type) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ if (p_b.type == NIL) \
+ _RETURN(false) \
+ DEFAULT_OP_ARRAY_OP_BODY(m_prefix, m_op_name, m_name, m_type, !=, !=, true, false, false) \
+ }
#define DEFAULT_OP_ARRAY_LT(m_prefix, m_op_name, m_name, m_type) \
DEFAULT_OP_ARRAY_OP(m_prefix, m_op_name, m_name, m_type, <, !=, false, a_len < array_b.size(), true)
@@ -321,38 +340,39 @@ bool Variant::booleanize() const {
#define DEFAULT_OP_ARRAY_GT(m_prefix, m_op_name, m_name, m_type) \
DEFAULT_OP_ARRAY_OP(m_prefix, m_op_name, m_name, m_type, >, !=, false, a_len < array_b.size(), true)
-#define DEFAULT_OP_ARRAY_OP(m_prefix, m_op_name, m_name, m_type, m_opa, m_opb, m_ret_def, m_ret_s, m_ret_f) \
- CASE_TYPE(m_prefix, m_op_name, m_name) { \
- if (p_a.type != p_b.type) { \
- r_valid = false; \
- return; \
- } \
- const PoolVector<m_type> &array_a = *reinterpret_cast<const PoolVector<m_type> *>(p_a._data._mem); \
- const PoolVector<m_type> &array_b = *reinterpret_cast<const PoolVector<m_type> *>(p_b._data._mem); \
- \
- int a_len = array_a.size(); \
- if (a_len m_opa array_b.size()) { \
- _RETURN(m_ret_s); \
- } else { \
- \
- PoolVector<m_type>::Read ra = array_a.read(); \
- PoolVector<m_type>::Read rb = array_b.read(); \
- \
- for (int i = 0; i < a_len; i++) { \
- if (ra[i] m_opb rb[i]) \
- _RETURN(m_ret_f); \
- } \
- \
- _RETURN(m_ret_def); \
- } \
+#define DEFAULT_OP_ARRAY_OP(m_prefix, m_op_name, m_name, m_type, m_opa, m_opb, m_ret_def, m_ret_s, m_ret_f) \
+ CASE_TYPE(m_prefix, m_op_name, m_name) { \
+ DEFAULT_OP_ARRAY_OP_BODY(m_prefix, m_op_name, m_name, m_type, m_opa, m_opb, m_ret_def, m_ret_s, m_ret_f) \
+ }
+
+#define DEFAULT_OP_ARRAY_OP_BODY(m_prefix, m_op_name, m_name, m_type, m_opa, m_opb, m_ret_def, m_ret_s, m_ret_f) \
+ if (p_a.type != p_b.type) \
+ _RETURN_FAIL \
+ \
+ const PoolVector<m_type> &array_a = *reinterpret_cast<const PoolVector<m_type> *>(p_a._data._mem); \
+ const PoolVector<m_type> &array_b = *reinterpret_cast<const PoolVector<m_type> *>(p_b._data._mem); \
+ \
+ int a_len = array_a.size(); \
+ if (a_len m_opa array_b.size()) { \
+ _RETURN(m_ret_s); \
+ } else { \
+ \
+ PoolVector<m_type>::Read ra = array_a.read(); \
+ PoolVector<m_type>::Read rb = array_b.read(); \
+ \
+ for (int i = 0; i < a_len; i++) { \
+ if (ra[i] m_opb rb[i]) \
+ _RETURN(m_ret_f); \
+ } \
+ \
+ _RETURN(m_ret_def); \
}
#define DEFAULT_OP_ARRAY_ADD(m_prefix, m_op_name, m_name, m_type) \
CASE_TYPE(m_prefix, m_op_name, m_name) { \
- if (p_a.type != p_b.type) { \
- r_valid = false; \
- _RETURN(NIL); \
- } \
+ if (p_a.type != p_b.type) \
+ _RETURN_FAIL; \
+ \
const PoolVector<m_type> &array_a = *reinterpret_cast<const PoolVector<m_type> *>(p_a._data._mem); \
const PoolVector<m_type> &array_b = *reinterpret_cast<const PoolVector<m_type> *>(p_b._data._mem); \
PoolVector<m_type> sum = array_a; \
@@ -372,12 +392,17 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
if (p_b.type == NIL) _RETURN(true);
if (p_b.type == OBJECT)
_RETURN(p_b._get_obj().obj == NULL);
- _RETURN_FAIL;
+
+ _RETURN(false);
}
CASE_TYPE(math, OP_EQUAL, BOOL) {
- if (p_b.type != BOOL)
+ if (p_b.type != BOOL) {
+ if (p_b.type == NIL)
+ _RETURN(false);
_RETURN_FAIL;
+ }
+
_RETURN(p_a._data._bool == p_b._data._bool);
}
@@ -386,12 +411,16 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
_RETURN((p_a._get_obj().obj == p_b._get_obj().obj));
if (p_b.type == NIL)
_RETURN(p_a._get_obj().obj == NULL);
+
_RETURN_FAIL;
}
CASE_TYPE(math, OP_EQUAL, DICTIONARY) {
- if (p_b.type != DICTIONARY)
+ if (p_b.type != DICTIONARY) {
+ if (p_b.type == NIL)
+ _RETURN(false);
_RETURN_FAIL;
+ }
const Dictionary *arr_a = reinterpret_cast<const Dictionary *>(p_a._data._mem);
const Dictionary *arr_b = reinterpret_cast<const Dictionary *>(p_b._data._mem);
@@ -400,9 +429,11 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
}
CASE_TYPE(math, OP_EQUAL, ARRAY) {
- if (p_b.type != ARRAY)
+ if (p_b.type != ARRAY) {
+ if (p_b.type == NIL)
+ _RETURN(false);
_RETURN_FAIL;
-
+ }
const Array *arr_a = reinterpret_cast<const Array *>(p_a._data._mem);
const Array *arr_b = reinterpret_cast<const Array *>(p_b._data._mem);
@@ -418,21 +449,21 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
_RETURN(true);
}
- DEFAULT_OP_NUM(math, OP_EQUAL, INT, ==, _int);
- DEFAULT_OP_NUM(math, OP_EQUAL, REAL, ==, _real);
- DEFAULT_OP_STR(math, OP_EQUAL, STRING, ==, String);
- DEFAULT_OP_LOCALMEM(math, OP_EQUAL, VECTOR2, ==, Vector2);
- DEFAULT_OP_LOCALMEM(math, OP_EQUAL, RECT2, ==, Rect2);
- DEFAULT_OP_PTRREF(math, OP_EQUAL, TRANSFORM2D, ==, _transform2d);
- DEFAULT_OP_LOCALMEM(math, OP_EQUAL, VECTOR3, ==, Vector3);
- DEFAULT_OP_LOCALMEM(math, OP_EQUAL, PLANE, ==, Plane);
- DEFAULT_OP_LOCALMEM(math, OP_EQUAL, QUAT, ==, Quat);
- DEFAULT_OP_PTRREF(math, OP_EQUAL, RECT3, ==, _rect3);
- DEFAULT_OP_PTRREF(math, OP_EQUAL, BASIS, ==, _basis);
- DEFAULT_OP_PTRREF(math, OP_EQUAL, TRANSFORM, ==, _transform);
- DEFAULT_OP_LOCALMEM(math, OP_EQUAL, COLOR, ==, Color);
- DEFAULT_OP_STR(math, OP_EQUAL, NODE_PATH, ==, NodePath);
- DEFAULT_OP_LOCALMEM(math, OP_EQUAL, _RID, ==, RID);
+ DEFAULT_OP_NUM_NULL(math, OP_EQUAL, INT, ==, _int);
+ DEFAULT_OP_NUM_NULL(math, OP_EQUAL, REAL, ==, _real);
+ DEFAULT_OP_STR_NULL(math, OP_EQUAL, STRING, ==, String);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_EQUAL, VECTOR2, ==, Vector2);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_EQUAL, RECT2, ==, Rect2);
+ DEFAULT_OP_PTRREF_NULL(math, OP_EQUAL, TRANSFORM2D, ==, _transform2d);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_EQUAL, VECTOR3, ==, Vector3);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_EQUAL, PLANE, ==, Plane);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_EQUAL, QUAT, ==, Quat);
+ DEFAULT_OP_PTRREF_NULL(math, OP_EQUAL, RECT3, ==, _rect3);
+ DEFAULT_OP_PTRREF_NULL(math, OP_EQUAL, BASIS, ==, _basis);
+ DEFAULT_OP_PTRREF_NULL(math, OP_EQUAL, TRANSFORM, ==, _transform);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_EQUAL, COLOR, ==, Color);
+ DEFAULT_OP_STR_NULL(math, OP_EQUAL, NODE_PATH, ==, NodePath);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_EQUAL, _RID, ==, RID);
DEFAULT_OP_ARRAY_EQ(math, OP_EQUAL, POOL_BYTE_ARRAY, uint8_t);
DEFAULT_OP_ARRAY_EQ(math, OP_EQUAL, POOL_INT_ARRAY, int);
@@ -448,12 +479,18 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
if (p_b.type == NIL) _RETURN(false);
if (p_b.type == OBJECT)
_RETURN(p_b._get_obj().obj != NULL);
- _RETURN_FAIL;
+
+ _RETURN(true);
}
CASE_TYPE(math, OP_NOT_EQUAL, BOOL) {
- if (p_b.type != BOOL)
+ if (p_b.type != BOOL) {
+ if (p_b.type == NIL)
+ _RETURN(true);
+
_RETURN_FAIL;
+ }
+
_RETURN(p_a._data._bool != p_b._data._bool);
}
@@ -462,12 +499,16 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
_RETURN((p_a._get_obj().obj != p_b._get_obj().obj));
if (p_b.type == NIL)
_RETURN(p_a._get_obj().obj != NULL);
+
_RETURN_FAIL;
}
CASE_TYPE(math, OP_NOT_EQUAL, DICTIONARY) {
- if (p_b.type != DICTIONARY)
+ if (p_b.type != DICTIONARY) {
+ if (p_b.type == NIL)
+ _RETURN(true);
_RETURN_FAIL;
+ }
const Dictionary *arr_a = reinterpret_cast<const Dictionary *>(p_a._data._mem);
const Dictionary *arr_b = reinterpret_cast<const Dictionary *>(p_b._data._mem);
@@ -476,8 +517,12 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
}
CASE_TYPE(math, OP_NOT_EQUAL, ARRAY) {
- if (p_b.type != ARRAY)
+ if (p_b.type != ARRAY) {
+ if (p_b.type == NIL)
+ _RETURN(true);
+
_RETURN_FAIL;
+ }
const Array *arr_a = reinterpret_cast<const Array *>(p_a._data._mem);
const Array *arr_b = reinterpret_cast<const Array *>(p_b._data._mem);
@@ -494,21 +539,21 @@ void Variant::evaluate(const Operator &p_op, const Variant &p_a,
_RETURN(true);
}
- DEFAULT_OP_NUM(math, OP_NOT_EQUAL, INT, !=, _int);
- DEFAULT_OP_NUM(math, OP_NOT_EQUAL, REAL, !=, _real);
- DEFAULT_OP_STR(math, OP_NOT_EQUAL, STRING, !=, String);
- DEFAULT_OP_LOCALMEM(math, OP_NOT_EQUAL, VECTOR2, !=, Vector2);
- DEFAULT_OP_LOCALMEM(math, OP_NOT_EQUAL, RECT2, !=, Rect2);
- DEFAULT_OP_PTRREF(math, OP_NOT_EQUAL, TRANSFORM2D, !=, _transform2d);
- DEFAULT_OP_LOCALMEM(math, OP_NOT_EQUAL, VECTOR3, !=, Vector3);
- DEFAULT_OP_LOCALMEM(math, OP_NOT_EQUAL, PLANE, !=, Plane);
- DEFAULT_OP_LOCALMEM(math, OP_NOT_EQUAL, QUAT, !=, Quat);
- DEFAULT_OP_PTRREF(math, OP_NOT_EQUAL, RECT3, !=, _rect3);
- DEFAULT_OP_PTRREF(math, OP_NOT_EQUAL, BASIS, !=, _basis);
- DEFAULT_OP_PTRREF(math, OP_NOT_EQUAL, TRANSFORM, !=, _transform);
- DEFAULT_OP_LOCALMEM(math, OP_NOT_EQUAL, COLOR, !=, Color);
- DEFAULT_OP_STR(math, OP_NOT_EQUAL, NODE_PATH, !=, NodePath);
- DEFAULT_OP_LOCALMEM(math, OP_NOT_EQUAL, _RID, !=, RID);
+ DEFAULT_OP_NUM_NULL(math, OP_NOT_EQUAL, INT, !=, _int);
+ DEFAULT_OP_NUM_NULL(math, OP_NOT_EQUAL, REAL, !=, _real);
+ DEFAULT_OP_STR_NULL(math, OP_NOT_EQUAL, STRING, !=, String);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_NOT_EQUAL, VECTOR2, !=, Vector2);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_NOT_EQUAL, RECT2, !=, Rect2);
+ DEFAULT_OP_PTRREF_NULL(math, OP_NOT_EQUAL, TRANSFORM2D, !=, _transform2d);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_NOT_EQUAL, VECTOR3, !=, Vector3);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_NOT_EQUAL, PLANE, !=, Plane);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_NOT_EQUAL, QUAT, !=, Quat);
+ DEFAULT_OP_PTRREF_NULL(math, OP_NOT_EQUAL, RECT3, !=, _rect3);
+ DEFAULT_OP_PTRREF_NULL(math, OP_NOT_EQUAL, BASIS, !=, _basis);
+ DEFAULT_OP_PTRREF_NULL(math, OP_NOT_EQUAL, TRANSFORM, !=, _transform);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_NOT_EQUAL, COLOR, !=, Color);
+ DEFAULT_OP_STR_NULL(math, OP_NOT_EQUAL, NODE_PATH, !=, NodePath);
+ DEFAULT_OP_LOCALMEM_NULL(math, OP_NOT_EQUAL, _RID, !=, RID);
CASE_TYPE(math, OP_NOT_EQUAL, POOL_BYTE_ARRAY);
CASE_TYPE(math, OP_NOT_EQUAL, POOL_INT_ARRAY);
diff --git a/doc/classes/EditorImportPlugin.xml b/doc/classes/EditorImportPlugin.xml
index 0ced30bda6..05319e926c 100644
--- a/doc/classes/EditorImportPlugin.xml
+++ b/doc/classes/EditorImportPlugin.xml
@@ -1,8 +1,54 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="EditorImportPlugin" inherits="Reference" category="Core" version="3.0.alpha.custom_build">
<brief_description>
+ Registers a custom resource importer in the editor. Use the class to parse any file and import it as a new resource type.
</brief_description>
<description>
+ EditorImportPlugins provide a way to extend the editor's resource import functionality. Use them to import resources from custom files or to provide alternatives to the editor's existing importers. Register your [EditorPlugin] with [method EditorPlugin.add_import_plugin].
+
+ EditorImportPlugins work by associating with specific file extensions and a resource type. See [method get_recognized_extension] and [method get_resource_type]). They may optionally specify some import presets that affect the import process. EditorImportPlugins are responsible for creating the resources and saving them in the [code].import[/code] directory.
+
+
+ Below is an example EditorImportPlugin that imports a [Mesh] from a file with the extension ".special" or ".spec":
+ [codeblock]
+ tool
+ extends EditorImportPlugin
+
+ func get_importer_name():
+ return "my.special.plugin"
+
+ func get_visible_name():
+ return "Special Mesh Importer"
+
+ func get_recognized_extensions():
+ return ["special", "spec"]
+
+ func get_save_extension():
+ return "mesh"
+
+ func get_resource_type():
+ return "Mesh"
+
+ func get_preset_count():
+ return 1
+
+ func get_preset_name(i):
+ return "Default"
+
+ func get_import_optons(i):
+ return [{"name": "my_option", "default_value": false}]
+
+ func load(src, dst, opts, r_platform_variants, r_gen_files):
+ var f = File.new()
+ if f.open(src, File.READ) != OK:
+ return FAILED
+
+ var mesh = Mesh.new()
+
+ var save = dst + "." + get_save_extension()
+ ResourceSaver.save(file, mesh)
+ return OK
+ [/codeblock]
</description>
<tutorials>
</tutorials>
@@ -15,12 +61,14 @@
<argument index="0" name="preset" type="int">
</argument>
<description>
+ Get the options and default values for the preset at this index. Returns an Array of Dictionaries with the following keys: "name", "default_value", "property_hint" (optional), "hint_string" (optional), "usage" (optional).
</description>
</method>
<method name="get_importer_name" qualifiers="virtual">
<return type="String">
</return>
<description>
+ Get the unique name of the importer.
</description>
</method>
<method name="get_option_visibility" qualifiers="virtual">
@@ -37,6 +85,7 @@
<return type="int">
</return>
<description>
+ Get the number of initial presets defined by the plugin. Use [method get_import_options] to get the default options for the preset and [method get_preset_name] to get the name of the preset.
</description>
</method>
<method name="get_preset_name" qualifiers="virtual">
@@ -45,30 +94,35 @@
<argument index="0" name="preset" type="int">
</argument>
<description>
+ Get the name of the options preset at this index.
</description>
</method>
<method name="get_recognized_extensions" qualifiers="virtual">
<return type="Array">
</return>
<description>
+ Get the list of file extensions to associate with this loader (case insensitive). e.g. ["obj"].
</description>
</method>
<method name="get_resource_type" qualifiers="virtual">
<return type="String">
</return>
<description>
+ Get the godot resource type associated with this loader. e.g. "Mesh" or "Animation".
</description>
</method>
<method name="get_save_extension" qualifiers="virtual">
<return type="String">
</return>
<description>
+ Get the extension used to save this resource in the [code].import[/code] directory.
</description>
</method>
<method name="get_visible_name" qualifiers="virtual">
<return type="String">
</return>
<description>
+ Get the name to display in the import window.
</description>
</method>
<method name="import" qualifiers="virtual">
diff --git a/editor/collada/collada.cpp b/editor/collada/collada.cpp
index 4986d97e8f..2d49840683 100644
--- a/editor/collada/collada.cpp
+++ b/editor/collada/collada.cpp
@@ -1918,7 +1918,7 @@ void Collada::_parse_animation(XMLParser &parser) {
for (int j = 0; j < key_count; j++) {
track.keys[j].data.resize(output_len);
for (int k = 0; k < output_len; k++)
- track.keys[j].data[k] = output[l + j * stride + k]; //super weird but should work
+ track.keys[j].data[k] = output[l + j * stride + k]; //super weird but should work:
}
if (sampler.has("INTERPOLATION")) {
diff --git a/editor/editor_file_system.cpp b/editor/editor_file_system.cpp
index 6e12a8fd02..481f2a8179 100644
--- a/editor/editor_file_system.cpp
+++ b/editor/editor_file_system.cpp
@@ -1498,10 +1498,22 @@ void EditorFileSystem::reimport_files(const Vector<String> &p_files) {
importing = true;
EditorProgress pr("reimport", TTR("(Re)Importing Assets"), p_files.size());
+
+ Vector<ImportFile> files;
+
for (int i = 0; i < p_files.size(); i++) {
- pr.step(p_files[i].get_file(), i);
+ ImportFile ifile;
+ ifile.path = p_files[i];
+ ifile.order = ResourceFormatImporter::get_singleton()->get_import_order(p_files[i]);
+ files.push_back(ifile);
+ }
+
+ files.sort();
+
+ for (int i = 0; i < files.size(); i++) {
+ pr.step(files[i].path.get_file(), i);
- _reimport_file(p_files[i]);
+ _reimport_file(files[i].path);
}
_save_filesystem_cache();
diff --git a/editor/editor_file_system.h b/editor/editor_file_system.h
index cee3219b43..ebcc091b0a 100644
--- a/editor/editor_file_system.h
+++ b/editor/editor_file_system.h
@@ -206,6 +206,14 @@ class EditorFileSystem : public Node {
Vector<String> _get_dependencies(const String &p_path);
+ struct ImportFile {
+ String path;
+ int order;
+ bool operator<(const ImportFile &p_if) const {
+ return order < p_if.order;
+ }
+ };
+
protected:
void _notification(int p_what);
static void _bind_methods();
diff --git a/editor/editor_settings.cpp b/editor/editor_settings.cpp
index eb72fdf64b..4de1c32fe7 100644
--- a/editor/editor_settings.cpp
+++ b/editor/editor_settings.cpp
@@ -584,6 +584,8 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) {
set("interface/theme/border_size", 1);
set("interface/theme/use_graph_node_headers", false);
hints["interface/theme/border_size"] = PropertyInfo(Variant::INT, "interface/theme/border_size", PROPERTY_HINT_RANGE, "0,2,1", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_RESTART_IF_CHANGED);
+ set("interface/theme/additional_spacing", 0);
+ hints["interface/theme/additional_spacing"] = PropertyInfo(Variant::REAL, "interface/theme/additional_spacing", PROPERTY_HINT_RANGE, "0,5,0.1", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_RESTART_IF_CHANGED);
set("interface/theme/custom_theme", "");
hints["interface/theme/custom_theme"] = PropertyInfo(Variant::STRING, "interface/theme/custom_theme", PROPERTY_HINT_GLOBAL_FILE, "*.res,*.tres,*.theme", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_RESTART_IF_CHANGED);
@@ -663,35 +665,47 @@ void EditorSettings::_load_defaults(Ref<ConfigFile> p_extra_config) {
set("editors/3d/default_z_near", 0.1);
set("editors/3d/default_z_far", 500.0);
- set("editors/3d/navigation_scheme", 0);
- hints["editors/3d/navigation_scheme"] = PropertyInfo(Variant::INT, "editors/3d/navigation_scheme", PROPERTY_HINT_ENUM, "Godot,Maya,Modo");
- set("editors/3d/zoom_style", 0);
- hints["editors/3d/zoom_style"] = PropertyInfo(Variant::INT, "editors/3d/zoom_style", PROPERTY_HINT_ENUM, "Vertical, Horizontal");
- set("editors/3d/orbit_modifier", 0);
- hints["editors/3d/orbit_modifier"] = PropertyInfo(Variant::INT, "editors/3d/orbit_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
- set("editors/3d/pan_modifier", 1);
- hints["editors/3d/pan_modifier"] = PropertyInfo(Variant::INT, "editors/3d/pan_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
- set("editors/3d/zoom_modifier", 4);
- hints["editors/3d/zoom_modifier"] = PropertyInfo(Variant::INT, "editors/3d/zoom_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
- set("editors/3d/emulate_numpad", false);
- set("editors/3d/emulate_3_button_mouse", false);
- set("editors/3d/warped_mouse_panning", true);
-
- set("editors/3d/orbit_sensitivity", 0.4);
-
- set("editors/3d/orbit_inertia", 0.2);
- hints["editors/3d/orbit_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/orbit_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
-
- set("editors/3d/freelook_inertia", 0.2);
- hints["editors/3d/freelook_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/freelook_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
-
- set("editors/3d/freelook_base_speed", 0.5);
- hints["editors/3d/freelook_base_speed"] = PropertyInfo(Variant::REAL, "editors/3d/freelook_base_speed", PROPERTY_HINT_RANGE, "0.0, 10, 0.1");
-
- set("editors/3d/freelook_activation_modifier", 0);
- hints["editors/3d/freelook_activation_modifier"] = PropertyInfo(Variant::INT, "editors/3d/freelook_activation_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
-
- set("editors/3d/freelook_modifier_speed_factor", 5.0);
+ // navigation
+ set("editors/3d/navigation/navigation_scheme", 0);
+ hints["editors/3d/navigation/navigation_scheme"] = PropertyInfo(Variant::INT, "editors/3d/navigation/navigation_scheme", PROPERTY_HINT_ENUM, "Godot,Maya,Modo");
+ set("editors/3d/navigation/zoom_style", 0);
+ hints["editors/3d/navigation/zoom_style"] = PropertyInfo(Variant::INT, "editors/3d/navigation/zoom_style", PROPERTY_HINT_ENUM, "Vertical, Horizontal");
+
+ set("editors/3d/navigation/emulate_3_button_mouse", false);
+ set("editors/3d/navigation/orbit_modifier", 3);
+ hints["editors/3d/navigation/orbit_modifier"] = PropertyInfo(Variant::INT, "editors/3d/navigation/orbit_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
+ set("editors/3d/navigation/pan_modifier", 1);
+ hints["editors/3d/navigation/pan_modifier"] = PropertyInfo(Variant::INT, "editors/3d/navigation/pan_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
+ set("editors/3d/navigation/zoom_modifier", 4);
+ hints["editors/3d/navigation/zoom_modifier"] = PropertyInfo(Variant::INT, "editors/3d/navigation/zoom_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
+
+ // set("editors/3d/navigation/emulate_numpad", false); not used at the moment
+ set("editors/3d/navigation/warped_mouse_panning", true);
+
+ // navigation feel
+ set("editors/3d/navigation_feel/orbit_sensitivity", 0.4);
+ hints["editors/3d/navigation_feel/orbit_sensitivity"] = PropertyInfo(Variant::REAL, "editors/3d/navigation_feel/orbit_sensitivity", PROPERTY_HINT_RANGE, "0.0, 2, 0.01");
+
+ set("editors/3d/navigation_feel/orbit_inertia", 0.15);
+ hints["editors/3d/navigation_feel/orbit_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/navigation_feel/orbit_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
+ set("editors/3d/navigation_feel/translation_inertia", 0.15);
+ hints["editors/3d/navigation_feel/translation_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/navigation_feel/translation_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
+ set("editors/3d/navigation_feel/zoom_inertia", 0.1);
+ hints["editors/3d/navigation_feel/zoom_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/navigation_feel/zoom_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
+ set("editors/3d/navigation_feel/manipulation_orbit_inertia", 0.1);
+ hints["editors/3d/navigation_feel/manipulation_orbit_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/navigation_feel/manipulation_orbit_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
+ set("editors/3d/navigation_feel/manipulation_translation_inertia", 0.1);
+ hints["editors/3d/navigation_feel/manipulation_translation_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/navigation_feel/manipulation_translation_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
+
+ // freelook
+ set("editors/3d/freelook/freelook_inertia", 0.1);
+ hints["editors/3d/freelook/freelook_inertia"] = PropertyInfo(Variant::REAL, "editors/3d/freelook/freelook_inertia", PROPERTY_HINT_RANGE, "0.0, 1, 0.01");
+ set("editors/3d/freelook/freelook_base_speed", 0.5);
+ hints["editors/3d/freelook/freelook_base_speed"] = PropertyInfo(Variant::REAL, "editors/3d/freelook/freelook_base_speed", PROPERTY_HINT_RANGE, "0.0, 10, 0.1");
+ set("editors/3d/freelook/freelook_activation_modifier", 0);
+ hints["editors/3d/freelook/freelook_activation_modifier"] = PropertyInfo(Variant::INT, "editors/3d/freelook/freelook_activation_modifier", PROPERTY_HINT_ENUM, "None,Shift,Alt,Meta,Ctrl");
+ set("editors/3d/freelook/freelook_modifier_speed_factor", 3.0);
+ hints["editors/3d/freelook/freelook_modifier_speed_factor"] = PropertyInfo(Variant::REAL, "editors/3d/freelook/freelook_modifier_speed_factor", PROPERTY_HINT_RANGE, "0.0, 10.0, 0.1");
set("editors/2d/bone_width", 5);
set("editors/2d/bone_color1", Color(1.0, 1.0, 1.0, 0.9));
diff --git a/editor/editor_themes.cpp b/editor/editor_themes.cpp
index 4aa1ccaa81..a4f2368794 100644
--- a/editor/editor_themes.cpp
+++ b/editor/editor_themes.cpp
@@ -345,11 +345,14 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
style_default->set_draw_center(true);
// Button and widgets
- Ref<StyleBoxFlat> style_widget = style_default->duplicate();
+ const float extra_spacing = EDITOR_DEF("interface/theme/additional_spacing", 0.0);
+ Ref<StyleBoxFlat> style_widget = style_default->duplicate();
+ style_widget->set_default_margin(MARGIN_LEFT, (extra_spacing + 6) * EDSCALE);
+ style_widget->set_default_margin(MARGIN_TOP, (extra_spacing + default_margin_size) * EDSCALE);
+ style_widget->set_default_margin(MARGIN_RIGHT, (extra_spacing + 6) * EDSCALE);
+ style_widget->set_default_margin(MARGIN_BOTTOM, (extra_spacing + default_margin_size) * EDSCALE);
style_widget->set_bg_color(dark_color_1);
- style_widget->set_default_margin(MARGIN_LEFT, 6 * EDSCALE);
- style_widget->set_default_margin(MARGIN_RIGHT, 6 * EDSCALE);
style_widget->set_border_color_all(dark_color_2);
Ref<StyleBoxFlat> style_widget_disabled = style_widget->duplicate();
@@ -381,7 +384,7 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
// Tabs
const int tab_default_margin_side = 10 * EDSCALE;
- Ref<StyleBoxFlat> style_tab_selected = style_default->duplicate();
+ Ref<StyleBoxFlat> style_tab_selected = style_widget->duplicate();
style_tab_selected->set_border_width_all(border_width);
style_tab_selected->set_border_width(MARGIN_BOTTOM, 0);
style_tab_selected->set_border_color_all(dark_color_3);
@@ -404,7 +407,9 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
theme->set_stylebox("Focus", "EditorStyles", style_focus);
// Menu
- Ref<StyleBoxEmpty> style_menu = style_empty;
+ Ref<StyleBoxFlat> style_menu = style_widget->duplicate();
+ style_menu->set_draw_center(false);
+ style_menu->set_border_width_all(0);
theme->set_stylebox("panel", "PanelContainer", style_menu);
theme->set_stylebox("MenuPanel", "EditorStyles", style_menu);
@@ -416,13 +421,13 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
theme->set_stylebox("PlayButtonPanel", "EditorStyles", style_empty); //make_stylebox(theme->get_icon("GuiPlayButtonGroup", "EditorIcons"), 16, 16, 16, 16, 8, 4, 8, 4));
//MenuButton
- Ref<StyleBoxFlat> style_menu_hover_border = style_default->duplicate();
+ Ref<StyleBoxFlat> style_menu_hover_border = style_widget->duplicate();
style_menu_hover_border->set_draw_center(false);
style_menu_hover_border->set_border_width_all(0);
style_menu_hover_border->set_border_width(MARGIN_BOTTOM, border_width);
style_menu_hover_border->set_border_color_all(accent_color);
- Ref<StyleBoxFlat> style_menu_hover_bg = style_default->duplicate();
+ Ref<StyleBoxFlat> style_menu_hover_bg = style_widget->duplicate();
style_menu_hover_bg->set_border_width_all(0);
style_menu_hover_bg->set_bg_color(dark_color_1);
@@ -517,7 +522,7 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
theme->set_icon("unchecked", "PopupMenu", theme->get_icon("GuiUnchecked", "EditorIcons"));
theme->set_icon("radio_checked", "PopupMenu", theme->get_icon("GuiChecked", "EditorIcons"));
theme->set_icon("radio_unchecked", "PopupMenu", theme->get_icon("GuiUnchecked", "EditorIcons"));
-
+ theme->set_constant("vseparation", "PopupMenu", (extra_spacing + default_margin_size) * EDSCALE);
// Tree & ItemList background
Ref<StyleBoxFlat> style_tree_bg = style_default->duplicate();
style_tree_bg->set_bg_color(dark_color_1);
@@ -537,6 +542,7 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
theme->set_color("custom_button_font_highlight", "Tree", font_color_hl);
theme->set_color("font_color", "Tree", font_color);
theme->set_color("font_color_selected", "Tree", font_color);
+ theme->set_constant("vseparation", "Tree", (extra_spacing + default_margin_size) * EDSCALE);
Ref<StyleBoxFlat> style_tree_btn = style_default->duplicate();
style_tree_btn->set_bg_color(contrast_color_1);
@@ -592,7 +598,7 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
theme->set_stylebox("selected", "ItemList", style_tree_selected);
theme->set_stylebox("bg_focus", "ItemList", style_focus);
theme->set_stylebox("bg", "ItemList", style_itemlist_bg);
- theme->set_constant("vseparation", "ItemList", 5 * EDSCALE);
+ theme->set_constant("vseparation", "ItemList", (extra_spacing + default_margin_size) * EDSCALE);
theme->set_color("font_color", "ItemList", font_color);
// Tabs & TabContainer
@@ -840,6 +846,9 @@ Ref<Theme> create_editor_theme(const Ref<Theme> p_theme) {
theme->set_icon("resizer", "GraphNode", theme->get_icon("GuiResizer", "EditorIcons"));
theme->set_icon("port", "GraphNode", theme->get_icon("GuiGraphNodePort", "EditorIcons"));
+ // GridContainer
+ theme->set_constant("vseperation", "GridContainer", (extra_spacing + default_margin_size) * EDSCALE);
+
// FileDialog
theme->set_color("files_disabled", "FileDialog", font_color_disabled);
diff --git a/editor/import/editor_import_collada.cpp b/editor/import/editor_import_collada.cpp
index b1991d755b..6ef1758363 100644
--- a/editor/import/editor_import_collada.cpp
+++ b/editor/import/editor_import_collada.cpp
@@ -381,6 +381,9 @@ Error ColladaImport::_create_material(const String &p_target) {
String texfile = effect.get_texture_path(effect.diffuse.texture, collada);
if (texfile != "") {
+ if (texfile.begins_with("/")) {
+ texfile = texfile.replace_first("/", "res://");
+ }
Ref<Texture> texture = ResourceLoader::load(texfile, "Texture");
if (texture.is_valid()) {
@@ -402,6 +405,10 @@ Error ColladaImport::_create_material(const String &p_target) {
String texfile = effect.get_texture_path(effect.specular.texture, collada);
if (texfile != "") {
+ if (texfile.begins_with("/")) {
+ texfile = texfile.replace_first("/", "res://");
+ }
+
Ref<Texture> texture = ResourceLoader::load(texfile, "Texture");
if (texture.is_valid()) {
material->set_texture(SpatialMaterial::TEXTURE_METALLIC, texture);
@@ -425,6 +432,10 @@ Error ColladaImport::_create_material(const String &p_target) {
String texfile = effect.get_texture_path(effect.emission.texture, collada);
if (texfile != "") {
+ if (texfile.begins_with("/")) {
+ texfile = texfile.replace_first("/", "res://");
+ }
+
Ref<Texture> texture = ResourceLoader::load(texfile, "Texture");
if (texture.is_valid()) {
@@ -451,6 +462,10 @@ Error ColladaImport::_create_material(const String &p_target) {
String texfile = effect.get_texture_path(effect.bump.texture, collada);
if (texfile != "") {
+ if (texfile.begins_with("/")) {
+ texfile = texfile.replace_first("/", "res://");
+ }
+
Ref<Texture> texture = ResourceLoader::load(texfile, "Texture");
if (texture.is_valid()) {
material->set_feature(SpatialMaterial::FEATURE_NORMAL_MAPPING, true);
diff --git a/editor/import/resource_importer_scene.cpp b/editor/import/resource_importer_scene.cpp
index b448ab8920..6d5ff822ef 100644
--- a/editor/import/resource_importer_scene.cpp
+++ b/editor/import/resource_importer_scene.cpp
@@ -114,7 +114,7 @@ bool ResourceImporterScene::get_option_visibility(const String &p_option, const
}
int ResourceImporterScene::get_preset_count() const {
- return 6;
+ return PRESET_MAX;
}
String ResourceImporterScene::get_preset_name(int p_idx) const {
@@ -955,9 +955,9 @@ void ResourceImporterScene::get_import_options(List<ImportOption> *r_options, in
}
bool materials_out = p_preset == PRESET_SEPARATE_MATERIALS || p_preset == PRESET_SEPARATE_MESHES_AND_MATERIALS || p_preset == PRESET_MULTIPLE_SCENES_AND_MATERIALS || p_preset == PRESET_SEPARATE_MATERIALS_AND_ANIMATIONS || p_preset == PRESET_SEPARATE_MESHES_MATERIALS_AND_ANIMATIONS;
- bool meshes_out = p_preset == PRESET_SEPARATE_MESHES || p_preset == PRESET_SEPARATE_MESHES_AND_MATERIALS || PRESET_SEPARATE_MESHES_AND_ANIMATIONS || PRESET_SEPARATE_MESHES_MATERIALS_AND_ANIMATIONS;
+ bool meshes_out = p_preset == PRESET_SEPARATE_MESHES || p_preset == PRESET_SEPARATE_MESHES_AND_MATERIALS || p_preset == PRESET_SEPARATE_MESHES_AND_ANIMATIONS || p_preset == PRESET_SEPARATE_MESHES_MATERIALS_AND_ANIMATIONS;
bool scenes_out = p_preset == PRESET_MULTIPLE_SCENES || p_preset == PRESET_MULTIPLE_SCENES_AND_MATERIALS;
- bool animations_out = p_preset == PRESET_SEPARATE_ANIMATIONS || PRESET_SEPARATE_MESHES_AND_ANIMATIONS || p_preset == PRESET_SEPARATE_MATERIALS_AND_ANIMATIONS || p_preset == PRESET_SEPARATE_MESHES_MATERIALS_AND_ANIMATIONS;
+ bool animations_out = p_preset == PRESET_SEPARATE_ANIMATIONS || p_preset == PRESET_SEPARATE_MESHES_AND_ANIMATIONS || p_preset == PRESET_SEPARATE_MATERIALS_AND_ANIMATIONS || p_preset == PRESET_SEPARATE_MESHES_MATERIALS_AND_ANIMATIONS;
r_options->push_back(ImportOption(PropertyInfo(Variant::STRING, "nodes/custom_script", PROPERTY_HINT_FILE, script_ext_hint), ""));
r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "nodes/storage", PROPERTY_HINT_ENUM, "Single Scene,Instanced Sub-Scenes"), scenes_out ? 1 : 0));
@@ -966,7 +966,7 @@ void ResourceImporterScene::get_import_options(List<ImportOption> *r_options, in
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "materials/keep_on_reimport"), materials_out ? true : false));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "meshes/compress"), true));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "meshes/ensure_tangents"), true));
- r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "meshes/storage", PROPERTY_HINT_ENUM, "Built-In,Files"), meshes_out ? true : false));
+ r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "meshes/storage", PROPERTY_HINT_ENUM, "Built-In,Files"), meshes_out ? 1 : 0));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "external_files/store_in_subdir"), false));
r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "animation/import", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_UPDATE_ALL_IF_MODIFIED), true));
r_options->push_back(ImportOption(PropertyInfo(Variant::REAL, "animation/fps", PROPERTY_HINT_RANGE, "1,120,1"), 15));
diff --git a/editor/import/resource_importer_scene.h b/editor/import/resource_importer_scene.h
index c3a66aa8b8..9c7e791719 100644
--- a/editor/import/resource_importer_scene.h
+++ b/editor/import/resource_importer_scene.h
@@ -96,6 +96,7 @@ class ResourceImporterScene : public ResourceImporter {
PRESET_MULTIPLE_SCENES,
PRESET_MULTIPLE_SCENES_AND_MATERIALS,
+ PRESET_MAX
};
void _replace_owner(Node *p_node, Node *p_scene, Node *p_new_owner);
@@ -118,6 +119,7 @@ public:
virtual void get_import_options(List<ImportOption> *r_options, int p_preset = 0) const;
virtual bool get_option_visibility(const String &p_option, const Map<StringName, Variant> &p_options) const;
+ virtual int get_import_order() const { return 100; } //after everything
void _make_external_resources(Node *p_node, const String &p_base_path, bool p_make_animations, bool p_make_materials, bool p_keep_materials, bool p_make_meshes, Map<Ref<Animation>, Ref<Animation> > &p_animations, Map<Ref<Material>, Ref<Material> > &p_materials, Map<Ref<ArrayMesh>, Ref<ArrayMesh> > &p_meshes);
diff --git a/editor/plugins/canvas_item_editor_plugin.cpp b/editor/plugins/canvas_item_editor_plugin.cpp
index 28de1ad940..bb25576007 100644
--- a/editor/plugins/canvas_item_editor_plugin.cpp
+++ b/editor/plugins/canvas_item_editor_plugin.cpp
@@ -2577,6 +2577,8 @@ void CanvasItemEditor::_draw_bones() {
}
void CanvasItemEditor::_draw_locks_and_groups(Node *p_node, const Transform2D &p_xform) {
+ ERR_FAIL_COND(!p_node);
+
RID viewport_ci = viewport->get_canvas_item();
Transform2D transform_ci = p_xform;
@@ -2605,6 +2607,8 @@ void CanvasItemEditor::_draw_locks_and_groups(Node *p_node, const Transform2D &p
}
void CanvasItemEditor::_build_bones_list(Node *p_node) {
+ ERR_FAIL_COND(!p_node);
+
for (int i = 0; i < p_node->get_child_count(); i++) {
_build_bones_list(p_node->get_child(i));
}
@@ -2626,6 +2630,8 @@ void CanvasItemEditor::_build_bones_list(Node *p_node) {
}
void CanvasItemEditor::_get_encompassing_rect(Node *p_node, Rect2 &r_rect, const Transform2D &p_xform) {
+ ERR_FAIL_COND(!p_node);
+
for (int i = 0; i < p_node->get_child_count(); i++) {
_get_encompassing_rect(p_node->get_child(i), r_rect, p_xform);
}
diff --git a/editor/plugins/spatial_editor_plugin.cpp b/editor/plugins/spatial_editor_plugin.cpp
index 6b485aab7c..008dcac2c1 100644
--- a/editor/plugins/spatial_editor_plugin.cpp
+++ b/editor/plugins/spatial_editor_plugin.cpp
@@ -77,11 +77,13 @@ void SpatialEditorViewport::_update_camera(float p_interp_delta) {
camera->set_perspective(get_fov(), get_znear(), get_zfar());
//when not being manipulated, move softly
- float free_orbit_inertia = EDITOR_DEF("editors/3d/free_orbit_inertia", 0.15);
- float free_translation_inertia = EDITOR_DEF("editors/3d/free_translation_inertia", 0.15);
+ float free_orbit_inertia = EDITOR_DEF("editors/3d/navigation_feel/orbit_inertia", 0.15);
+ float free_translation_inertia = EDITOR_DEF("editors/3d/navigation_feel/translation_inertia", 0.15);
//when being manipulated, move more quickly
- float manip_orbit_inertia = EDITOR_DEF("editors/3d/manipulation_orbit_inertia", 0.075);
- float manip_translation_inertia = EDITOR_DEF("editors/3d/manipulation_translation_inertia", 0.075);
+ float manip_orbit_inertia = EDITOR_DEF("editors/3d/navigation_feel/manipulation_orbit_inertia", 0.1);
+ float manip_translation_inertia = EDITOR_DEF("editors/3d/navigation_feel/manipulation_translation_inertia", 0.1);
+
+ float zoom_inertia = EDITOR_DEF("editors/3d/navigation_feel/zoom_inertia", 0.1);
//determine if being manipulated
bool manipulated = (Input::get_singleton()->get_mouse_button_mask() & (2 | 4)) || Input::get_singleton()->is_key_pressed(KEY_SHIFT) || Input::get_singleton()->is_key_pressed(KEY_ALT) || Input::get_singleton()->is_key_pressed(KEY_CONTROL);
@@ -96,7 +98,7 @@ void SpatialEditorViewport::_update_camera(float p_interp_delta) {
camera_cursor.y_rot = Math::lerp(old_camera_cursor.y_rot, cursor.y_rot, MIN(1.f, p_interp_delta * (1 / orbit_inertia)));
camera_cursor.pos = old_camera_cursor.pos.linear_interpolate(cursor.pos, MIN(1.f, p_interp_delta * (1 / translation_inertia)));
- camera_cursor.distance = Math::lerp(old_camera_cursor.distance, cursor.distance, MIN(1.f, p_interp_delta * (1 / translation_inertia)));
+ camera_cursor.distance = Math::lerp(old_camera_cursor.distance, cursor.distance, MIN(1.f, p_interp_delta * (1 / zoom_inertia)));
if (p_interp_delta == 0 || is_freelook_active()) {
camera_cursor = cursor;
@@ -465,7 +467,6 @@ void SpatialEditorViewport::_select_region() {
Vector<Plane> frustum;
Vector3 cam_pos = _get_camera_position();
- Set<Ref<SpatialEditorGizmo> > found_gizmos;
for (int i = 0; i < 4; i++) {
@@ -485,6 +486,9 @@ void SpatialEditorViewport::_select_region() {
frustum.push_back(far);
Vector<ObjectID> instances = VisualServer::get_singleton()->instances_cull_convex(frustum, get_tree()->get_root()->get_world()->get_scenario());
+ Vector<Spatial *> selected;
+
+ Node *edited_scene = get_tree()->get_edited_scene_root();
for (int i = 0; i < instances.size(); i++) {
@@ -497,11 +501,14 @@ void SpatialEditorViewport::_select_region() {
if (!seg.is_valid())
continue;
- if (found_gizmos.has(seg))
- continue;
+ Spatial *root_sp = sp;
+ while (root_sp && root_sp != edited_scene && root_sp->get_owner() != edited_scene && !edited_scene->is_editable_instance(root_sp->get_owner())) {
+ root_sp = Object::cast_to<Spatial>(root_sp->get_owner());
+ }
- if (seg->intersect_frustum(camera, frustum))
- _select(sp, true, false);
+ if (selected.find(root_sp) == -1)
+ if (seg->intersect_frustum(camera, frustum))
+ _select(root_sp, true, false);
}
}
@@ -797,20 +804,20 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
Ref<InputEventMouseButton> b = p_event;
if (b.is_valid()) {
-
+ float zoom_factor = 1 + (ZOOM_MULTIPLIER - 1) * b->get_factor();
switch (b->get_button_index()) {
case BUTTON_WHEEL_UP: {
- scale_cursor_distance(is_freelook_active() ? ZOOM_MULTIPLIER : 1.0 / ZOOM_MULTIPLIER);
+ scale_cursor_distance(is_freelook_active() ? zoom_factor : 1.0 / zoom_factor);
} break;
case BUTTON_WHEEL_DOWN: {
- scale_cursor_distance(is_freelook_active() ? 1.0 / ZOOM_MULTIPLIER : ZOOM_MULTIPLIER);
+ scale_cursor_distance(is_freelook_active() ? 1.0 / zoom_factor : zoom_factor);
} break;
case BUTTON_RIGHT: {
- NavigationScheme nav_scheme = (NavigationScheme)EditorSettings::get_singleton()->get("editors/3d/navigation_scheme").operator int();
+ NavigationScheme nav_scheme = (NavigationScheme)EditorSettings::get_singleton()->get("editors/3d/navigation/navigation_scheme").operator int();
if (b->is_pressed() && _edit.gizmo.is_valid()) {
//restore
@@ -856,7 +863,7 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
if (b->is_pressed()) {
int mod = _get_key_modifier(b);
- if (mod == _get_key_modifier_setting("editors/3d/freelook_activation_modifier")) {
+ if (mod == _get_key_modifier_setting("editors/3d/freelook/freelook_activation_modifier")) {
freelook_active = true;
}
} else {
@@ -908,7 +915,7 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
if (b->is_pressed()) {
- NavigationScheme nav_scheme = (NavigationScheme)EditorSettings::get_singleton()->get("editors/3d/navigation_scheme").operator int();
+ NavigationScheme nav_scheme = (NavigationScheme)EditorSettings::get_singleton()->get("editors/3d/navigation/navigation_scheme").operator int();
if ((nav_scheme == NAVIGATION_MAYA || nav_scheme == NAVIGATION_MODO) && b->get_alt()) {
break;
}
@@ -1117,7 +1124,7 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
_gizmo_select(_edit.mouse_pos, true);
}
- NavigationScheme nav_scheme = (NavigationScheme)EditorSettings::get_singleton()->get("editors/3d/navigation_scheme").operator int();
+ NavigationScheme nav_scheme = (NavigationScheme)EditorSettings::get_singleton()->get("editors/3d/navigation/navigation_scheme").operator int();
NavigationMode nav_mode = NAVIGATION_NONE;
if (_edit.gizmo.is_valid()) {
@@ -1440,11 +1447,11 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
int mod = _get_key_modifier(m);
- if (mod == _get_key_modifier_setting("editors/3d/pan_modifier"))
+ if (mod == _get_key_modifier_setting("editors/3d/navigation/pan_modifier"))
nav_mode = NAVIGATION_PAN;
- else if (mod == _get_key_modifier_setting("editors/3d/zoom_modifier"))
+ else if (mod == _get_key_modifier_setting("editors/3d/navigation/zoom_modifier"))
nav_mode = NAVIGATION_ZOOM;
- else if (mod == _get_key_modifier_setting("editors/3d/orbit_modifier"))
+ else if (mod == _get_key_modifier_setting("editors/3d/navigation/orbit_modifier"))
nav_mode = NAVIGATION_ORBIT;
} else if (nav_scheme == NAVIGATION_MAYA) {
@@ -1452,16 +1459,16 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
nav_mode = NAVIGATION_PAN;
}
- } else if (EditorSettings::get_singleton()->get("editors/3d/emulate_3_button_mouse")) {
+ } else if (EditorSettings::get_singleton()->get("editors/3d/navigation/emulate_3_button_mouse")) {
// Handle trackpad (no external mouse) use case
int mod = _get_key_modifier(m);
if (mod) {
- if (mod == _get_key_modifier_setting("editors/3d/pan_modifier"))
+ if (mod == _get_key_modifier_setting("editors/3d/navigation/pan_modifier"))
nav_mode = NAVIGATION_PAN;
- else if (mod == _get_key_modifier_setting("editors/3d/zoom_modifier"))
+ else if (mod == _get_key_modifier_setting("editors/3d/navigation/zoom_modifier"))
nav_mode = NAVIGATION_ZOOM;
- else if (mod == _get_key_modifier_setting("editors/3d/orbit_modifier"))
+ else if (mod == _get_key_modifier_setting("editors/3d/navigation/orbit_modifier"))
nav_mode = NAVIGATION_ORBIT;
}
}
@@ -1494,7 +1501,7 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
if (nav_scheme == NAVIGATION_MAYA && m->get_shift())
zoom_speed *= zoom_speed_modifier;
- NavigationZoomStyle zoom_style = (NavigationZoomStyle)EditorSettings::get_singleton()->get("editors/3d/zoom_style").operator int();
+ NavigationZoomStyle zoom_style = (NavigationZoomStyle)EditorSettings::get_singleton()->get("editors/3d/navigation/zoom_style").operator int();
if (zoom_style == NAVIGATION_ZOOM_HORIZONTAL) {
if (m->get_relative().x > 0)
scale_cursor_distance(1 - m->get_relative().x * zoom_speed);
@@ -1512,7 +1519,7 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
case NAVIGATION_ORBIT: {
Point2i relative = _get_warped_mouse_motion(m);
- real_t degrees_per_pixel = EditorSettings::get_singleton()->get("editors/3d/orbit_sensitivity");
+ real_t degrees_per_pixel = EditorSettings::get_singleton()->get("editors/3d/navigation_feel/orbit_sensitivity");
real_t radians_per_pixel = Math::deg2rad(degrees_per_pixel);
cursor.x_rot += relative.y * radians_per_pixel;
@@ -1531,7 +1538,7 @@ void SpatialEditorViewport::_sinput(const Ref<InputEvent> &p_event) {
if (!orthogonal) {
Point2i relative = _get_warped_mouse_motion(m);
- real_t degrees_per_pixel = EditorSettings::get_singleton()->get("editors/3d/orbit_sensitivity");
+ real_t degrees_per_pixel = EditorSettings::get_singleton()->get("editors/3d/navigation_feel/orbit_sensitivity");
real_t radians_per_pixel = Math::deg2rad(degrees_per_pixel);
cursor.x_rot += relative.y * radians_per_pixel;
@@ -1668,7 +1675,7 @@ void SpatialEditorViewport::scale_cursor_distance(real_t scale) {
Point2i SpatialEditorViewport::_get_warped_mouse_motion(const Ref<InputEventMouseMotion> &p_ev_mouse_motion) const {
Point2i relative;
- if (bool(EDITOR_DEF("editors/3d/warped_mouse_panning", false))) {
+ if (bool(EDITOR_DEF("editors/3d/navigation/warped_mouse_panning", false))) {
relative = Input::get_singleton()->warp_mouse_motion(p_ev_mouse_motion, surface->get_global_rect());
} else {
relative = p_ev_mouse_motion->get_relative();
@@ -1722,10 +1729,10 @@ void SpatialEditorViewport::_update_freelook(real_t delta) {
speed_modifier = true;
}
- real_t inertia = EDITOR_DEF("editors/3d/freelook_inertia", 0.2);
+ real_t inertia = EDITOR_DEF("editors/3d/freelook/freelook_inertia", 0.1);
inertia = MAX(0, inertia);
- const real_t base_speed = EDITOR_DEF("editors/3d/freelook_base_speed", 0.5);
- const real_t modifier_speed_factor = EDITOR_DEF("editors/3d/freelook_modifier_speed_factor", 5);
+ const real_t base_speed = EDITOR_DEF("editors/3d/freelook/freelook_base_speed", 0.5);
+ const real_t modifier_speed_factor = EDITOR_DEF("editors/3d/freelook/freelook_modifier_speed_factor", 3);
real_t speed = base_speed * cursor.distance;
if (speed_modifier)
diff --git a/editor/spatial_editor_gizmos.cpp b/editor/spatial_editor_gizmos.cpp
index 9c7ea506aa..450c9f4b3c 100644
--- a/editor/spatial_editor_gizmos.cpp
+++ b/editor/spatial_editor_gizmos.cpp
@@ -211,9 +211,10 @@ void EditorSpatialGizmo::add_unscaled_billboard(const Ref<Material> &p_material,
instances.push_back(ins);
}
-void EditorSpatialGizmo::add_collision_triangles(const Ref<TriangleMesh> &p_tmesh) {
+void EditorSpatialGizmo::add_collision_triangles(const Ref<TriangleMesh> &p_tmesh, const Rect3 &p_bounds) {
collision_mesh = p_tmesh;
+ collision_mesh_bounds = p_bounds;
}
void EditorSpatialGizmo::add_collision_segments(const Vector<Vector3> &p_lines) {
@@ -359,6 +360,29 @@ bool EditorSpatialGizmo::intersect_frustum(const Camera *p_camera, const Vector<
return false;
}
+ if (collision_mesh_bounds.size != Vector3(0.0, 0.0, 0.0)) {
+ Transform t = spatial_node->get_global_transform();
+ const Plane *p = p_frustum.ptr();
+ int fc = p_frustum.size();
+
+ Vector3 mins = t.xform(collision_mesh_bounds.get_position());
+ Vector3 max = t.xform(collision_mesh_bounds.get_position() + collision_mesh_bounds.get_size());
+
+ bool any_out = false;
+
+ for (int j = 0; j < fc; j++) {
+
+ if (p[j].distance_to(mins) > 0 || p[j].distance_to(max) > 0) {
+
+ any_out = true;
+ break;
+ }
+ }
+
+ if (!any_out)
+ return true;
+ }
+
return false;
}
@@ -637,7 +661,7 @@ void EditorSpatialGizmo::_bind_methods() {
ClassDB::bind_method(D_METHOD("add_lines", "lines", "material", "billboard"), &EditorSpatialGizmo::add_lines, DEFVAL(false));
ClassDB::bind_method(D_METHOD("add_mesh", "mesh", "billboard", "skeleton"), &EditorSpatialGizmo::add_mesh, DEFVAL(false), DEFVAL(RID()));
ClassDB::bind_method(D_METHOD("add_collision_segments", "segments"), &EditorSpatialGizmo::add_collision_segments);
- ClassDB::bind_method(D_METHOD("add_collision_triangles", "triangles"), &EditorSpatialGizmo::add_collision_triangles);
+ ClassDB::bind_method(D_METHOD("add_collision_triangles", "triangles", "bounds"), &EditorSpatialGizmo::add_collision_triangles);
ClassDB::bind_method(D_METHOD("add_unscaled_billboard", "material", "default_scale"), &EditorSpatialGizmo::add_unscaled_billboard, DEFVAL(1));
ClassDB::bind_method(D_METHOD("add_handles", "handles", "billboard", "secondary"), &EditorSpatialGizmo::add_handles, DEFVAL(false), DEFVAL(false));
ClassDB::bind_method(D_METHOD("set_spatial_node", "node"), &EditorSpatialGizmo::_set_spatial_node);
@@ -1249,8 +1273,10 @@ void MeshInstanceSpatialGizmo::redraw() {
return; //none
Ref<TriangleMesh> tm = m->generate_triangle_mesh();
- if (tm.is_valid())
- add_collision_triangles(tm);
+ if (tm.is_valid()) {
+ Rect3 aabb;
+ add_collision_triangles(tm, aabb);
+ }
}
MeshInstanceSpatialGizmo::MeshInstanceSpatialGizmo(MeshInstance *p_mesh) {
diff --git a/editor/spatial_editor_gizmos.h b/editor/spatial_editor_gizmos.h
index d63a804055..afe64c723c 100644
--- a/editor/spatial_editor_gizmos.h
+++ b/editor/spatial_editor_gizmos.h
@@ -78,6 +78,7 @@ class EditorSpatialGizmo : public SpatialEditorGizmo {
Vector<Vector3> collision_segments;
Ref<TriangleMesh> collision_mesh;
+ Rect3 collision_mesh_bounds;
struct Handle {
Vector3 pos;
@@ -99,7 +100,7 @@ protected:
void add_lines(const Vector<Vector3> &p_lines, const Ref<Material> &p_material, bool p_billboard = false);
void add_mesh(const Ref<ArrayMesh> &p_mesh, bool p_billboard = false, const RID &p_skeleton = RID());
void add_collision_segments(const Vector<Vector3> &p_lines);
- void add_collision_triangles(const Ref<TriangleMesh> &p_tmesh);
+ void add_collision_triangles(const Ref<TriangleMesh> &p_tmesh, const Rect3 &p_bounds = Rect3());
void add_unscaled_billboard(const Ref<Material> &p_material, float p_scale = 1);
void add_handles(const Vector<Vector3> &p_handles, bool p_billboard = false, bool p_secondary = false);
void add_solid_box(Ref<Material> &p_material, Vector3 size);
diff --git a/main/main.cpp b/main/main.cpp
index 04375666a9..1f7418ba2a 100644
--- a/main/main.cpp
+++ b/main/main.cpp
@@ -990,8 +990,10 @@ Error Main::setup2(Thread::ID p_main_tid_override) {
#endif
}
+#ifdef TOOLS_ENABLED
Ref<Image> icon = memnew(Image(app_icon_png));
OS::get_singleton()->set_icon(icon);
+#endif
}
MAIN_PRINT("Main: DCC");
@@ -1082,6 +1084,7 @@ bool Main::start() {
ERR_FAIL_COND_V(!_start_success, false);
+ bool hasicon = false;
bool editor = false;
String doc_tool;
List<String> removal_docs;
@@ -1519,8 +1522,10 @@ bool Main::start() {
if (iconpath != "") {
Ref<Image> icon;
icon.instance();
- if (icon->load(iconpath) == OK)
+ if (icon->load(iconpath) == OK) {
OS::get_singleton()->set_icon(icon);
+ hasicon = true;
+ }
}
}
}
@@ -1537,6 +1542,11 @@ bool Main::start() {
#endif
}
+ if (!hasicon) {
+ Ref<Image> icon = memnew(Image(app_icon_png));
+ OS::get_singleton()->set_icon(icon);
+ }
+
OS::get_singleton()->set_main_loop(main_loop);
return true;
diff --git a/platform/haiku/detect.py b/platform/haiku/detect.py
index c0e003a3d2..61ee32d2dd 100644
--- a/platform/haiku/detect.py
+++ b/platform/haiku/detect.py
@@ -21,7 +21,7 @@ def can_build():
def get_opts():
return [
- ('debug_release', 'Add debug symbols to release version', 'no')
+ ('debug_symbols', 'Add debug symbols to release version (yes/no/full)', 'yes')
]
@@ -36,16 +36,21 @@ def configure(env):
## Build type
if (env["target"] == "release"):
- if (env["debug_release"] == "yes"):
+ env.Prepend(CCFLAGS=['-O3', '-ffast-math'])
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
env.Prepend(CCFLAGS=['-g2'])
- else:
- env.Prepend(CCFLAGS=['-O3', '-ffast-math'])
elif (env["target"] == "release_debug"):
env.Prepend(CCFLAGS=['-O2', '-ffast-math', '-DDEBUG_ENABLED'])
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
+ env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "debug"):
- env.Prepend(CCFLAGS=['-g2', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
+ env.Prepend(CCFLAGS=['-g3', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
## Architecture
diff --git a/platform/osx/SCsub b/platform/osx/SCsub
index 5b2de54535..27bffbe80e 100644
--- a/platform/osx/SCsub
+++ b/platform/osx/SCsub
@@ -1,7 +1,11 @@
#!/usr/bin/env python
+import os
Import('env')
+def make_debug(target, source, env):
+ os.system('dsymutil %s -o %s.dSYM' % (target[0], target[0]))
+
files = [
'crash_handler_osx.mm',
'os_osx.mm',
@@ -13,8 +17,7 @@ files = [
'power_osx.cpp',
]
-prog = env.Program('#bin/godot', files)
-if (env['target'] == "debug" or env['target'] == "release_debug"):
- # Build the .dSYM file for atos
- action = "dsymutil " + File(prog)[0].path + " -o " + File(prog)[0].path + ".dSYM"
- env.AddPostAction(prog, action)
+binary = env.Program('#bin/godot', files)
+if env["debug_symbols"] == "full" or env["debug_symbols"] == "yes":
+ env.AddPostAction(binary, make_debug)
+
diff --git a/platform/osx/detect.py b/platform/osx/detect.py
index d3ebdfe992..24302b5ff9 100644
--- a/platform/osx/detect.py
+++ b/platform/osx/detect.py
@@ -22,6 +22,7 @@ def get_opts():
return [
('osxcross_sdk', 'OSXCross SDK version', 'darwin14'),
+ ('debug_symbols', 'Add debug symbols to release version (yes/no/full)', 'yes'),
]
@@ -36,10 +37,18 @@ def configure(env):
## Build type
if (env["target"] == "release"):
- env.Prepend(CCFLAGS=['-O2', '-ffast-math', '-fomit-frame-pointer', '-ftree-vectorize', '-msse2'])
+ env.Prepend(CCFLAGS=['-O3', '-ffast-math', '-fomit-frame-pointer', '-ftree-vectorize', '-msse2'])
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
+ env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "release_debug"):
env.Prepend(CCFLAGS=['-O2', '-DDEBUG_ENABLED'])
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
+ env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "debug"):
env.Prepend(CCFLAGS=['-g3', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
diff --git a/platform/windows/SCsub b/platform/windows/SCsub
index b56a5c6a80..fd041e096e 100644
--- a/platform/windows/SCsub
+++ b/platform/windows/SCsub
@@ -1,7 +1,12 @@
#!/usr/bin/env python
+import os
Import('env')
+def make_debug_mingw(target, source, env):
+ os.system('objcopy --only-keep-debug %s %s.debug' % (target[0], target[0]))
+ os.system('strip --strip-debug --strip-unneeded %s' % (target[0]))
+ os.system('objcopy --add-gnu-debuglink=%s.debug %s' % (target[0], target[0]))
common_win = [
"context_gl_win.cpp",
@@ -22,10 +27,14 @@ obj = env.RES(restarget, 'godot_res.rc')
common_win.append(obj)
-env.Program('#bin/godot', ['godot_win.cpp'] + common_win, PROGSUFFIX=env["PROGSUFFIX"])
+binary = env.Program('#bin/godot', ['godot_win.cpp'] + common_win, PROGSUFFIX=env["PROGSUFFIX"])
# Microsoft Visual Studio Project Generation
if (env['vsproj']) == "yes":
env.vs_srcs = env.vs_srcs + ["platform/windows/godot_win.cpp"]
for x in common_win:
env.vs_srcs = env.vs_srcs + ["platform/windows/" + str(x)]
+
+if not os.getenv("VCINSTALLDIR"):
+ if env["debug_symbols"] == "full" or env["debug_symbols"] == "yes":
+ env.AddPostAction(binary, make_debug_mingw)
diff --git a/platform/windows/detect.py b/platform/windows/detect.py
index 5bd9a78f49..65eb51a2f3 100644
--- a/platform/windows/detect.py
+++ b/platform/windows/detect.py
@@ -64,6 +64,7 @@ def get_opts():
return [
('mingw_prefix_32', 'MinGW prefix (Win32)', mingw32),
('mingw_prefix_64', 'MinGW prefix (Win64)', mingw64),
+ ('debug_symbols', 'Add debug symbols to release version (yes/no/full)', 'yes')
]
@@ -213,11 +214,20 @@ def configure(env):
env.Append(LINKFLAGS=['-Wl,--subsystem,windows'])
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
+ env.Prepend(CCFLAGS=['-g2'])
+
elif (env["target"] == "release_debug"):
env.Append(CCFLAGS=['-O2', '-DDEBUG_ENABLED'])
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
+ env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "debug"):
- env.Append(CCFLAGS=['-g', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
+ env.Append(CCFLAGS=['-g3', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
## Compiler configuration
diff --git a/platform/x11/SCsub b/platform/x11/SCsub
index 62717f3221..aabc49149f 100644
--- a/platform/x11/SCsub
+++ b/platform/x11/SCsub
@@ -1,7 +1,12 @@
#!/usr/bin/env python
+import os
Import('env')
+def make_debug(target, source, env):
+ os.system('objcopy --only-keep-debug %s %s.debug' % (target[0], target[0]))
+ os.system('strip --strip-debug --strip-unneeded %s' % (target[0]))
+ os.system('objcopy --add-gnu-debuglink=%s.debug %s' % (target[0], target[0]))
common_x11 = [
"context_gl_x11.cpp",
@@ -12,4 +17,6 @@ common_x11 = [
"power_x11.cpp",
]
-env.Program('#bin/godot', ['godot_x11.cpp'] + common_x11)
+binary = env.Program('#bin/godot', ['godot_x11.cpp'] + common_x11)
+if env["debug_symbols"] == "full" or env["debug_symbols"] == "yes":
+ env.AddPostAction(binary, make_debug)
diff --git a/platform/x11/detect.py b/platform/x11/detect.py
index d61175da60..efd388e44f 100644
--- a/platform/x11/detect.py
+++ b/platform/x11/detect.py
@@ -44,7 +44,6 @@ def can_build():
return True
-
def get_opts():
return [
@@ -55,7 +54,7 @@ def get_opts():
('use_lto', 'Use link time optimization', 'no'),
('pulseaudio', 'Detect & use pulseaudio', 'yes'),
('udev', 'Use udev for gamepad connection callbacks', 'no'),
- ('debug_release', 'Add debug symbols to release version', 'no'),
+ ('debug_symbols', 'Add debug symbols to release version (yes/no/full)', 'yes')
]
@@ -77,16 +76,20 @@ def configure(env):
# -O3 -ffast-math is identical to -Ofast. We need to split it out so we can selectively disable
# -ffast-math in code for which it generates wrong results.
env.Prepend(CCFLAGS=['-O3', '-ffast-math'])
- if (env["debug_release"] == "yes"):
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "release_debug"):
env.Prepend(CCFLAGS=['-O2', '-ffast-math', '-DDEBUG_ENABLED'])
- if (env["debug_release"] == "yes"):
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "debug"):
- env.Prepend(CCFLAGS=['-g2', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
+ env.Prepend(CCFLAGS=['-g3', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
env.Append(LINKFLAGS=['-rdynamic'])
## Architecture
diff --git a/platform/x11/os_x11.cpp b/platform/x11/os_x11.cpp
index c0299f1c26..599c0d2278 100644
--- a/platform/x11/os_x11.cpp
+++ b/platform/x11/os_x11.cpp
@@ -708,6 +708,16 @@ void OS_X11::set_wm_fullscreen(bool p_enabled) {
XSetWMNormalHints(x11_display, x11_window, xsh);
XFree(xsh);
}
+
+ if (!p_enabled && !get_borderless_window()) {
+ // put decorations back if the window wasn't suppoesed to be borderless
+ Hints hints;
+ Atom property;
+ hints.flags = 2;
+ hints.decorations = 1;
+ property = XInternAtom(x11_display, "_MOTIF_WM_HINTS", True);
+ XChangeProperty(x11_display, x11_window, property, property, 32, PropModeReplace, (unsigned char *)&hints, 5);
+ }
}
int OS_X11::get_screen_count() const {
diff --git a/scene/resources/dynamic_font.cpp b/scene/resources/dynamic_font.cpp
index b2d87c8f35..1ee76a4216 100644
--- a/scene/resources/dynamic_font.cpp
+++ b/scene/resources/dynamic_font.cpp
@@ -560,8 +560,23 @@ void DynamicFontAtSize::_update_char(CharType p_char) {
int ofs = ((i + tex_y + rect_margin) * tex.texture_size + j + tex_x + rect_margin) * 2;
ERR_FAIL_COND(ofs >= tex.imgdata.size());
- wr[ofs + 0] = 255; //grayscale as 1
- wr[ofs + 1] = slot->bitmap.buffer[i * slot->bitmap.width + j];
+ switch (slot->bitmap.pixel_mode) {
+ case FT_PIXEL_MODE_MONO: {
+ int byte = i * slot->bitmap.pitch + (j >> 3);
+ int bit = 1 << (7 - (j % 8));
+ wr[ofs + 0] = 255; //grayscale as 1
+ wr[ofs + 1] = slot->bitmap.buffer[byte] & bit ? 255 : 0;
+ } break;
+ case FT_PIXEL_MODE_GRAY:
+ wr[ofs + 0] = 255; //grayscale as 1
+ wr[ofs + 1] = slot->bitmap.buffer[i * slot->bitmap.pitch + j];
+ break;
+ // TODO: FT_PIXEL_MODE_LCD, FT_PIXEL_MODE_BGRA
+ default:
+ ERR_EXPLAIN("Font uses unsupported pixel format: " + itos(slot->bitmap.pixel_mode));
+ ERR_FAIL();
+ break;
+ }
}
}
}