diff --git a/drivers/gles3/shader_compiler_gles3.cpp b/drivers/gles3/shader_compiler_gles3.cpp index 4f741c6b7ae..b1f7b4c9bda 100644 --- a/drivers/gles3/shader_compiler_gles3.cpp +++ b/drivers/gles3/shader_compiler_gles3.cpp @@ -747,6 +747,7 @@ ShaderCompilerGLES3::ShaderCompilerGLES3() { actions[VS::SHADER_SPATIAL].renames["INSTANCE_CUSTOM"] = "instance_custom"; actions[VS::SHADER_SPATIAL].renames["SCREEN_UV"] = "screen_uv"; actions[VS::SHADER_SPATIAL].renames["SCREEN_TEXTURE"] = "screen_texture"; + actions[VS::SHADER_SPATIAL].renames["DEPTH_TEXTURE"] = "depth_buffer"; actions[VS::SHADER_SPATIAL].renames["SIDE"] = "side"; actions[VS::SHADER_SPATIAL].usage_defines["TANGENT"] = "#define ENABLE_TANGENT_INTERP\n"; diff --git a/editor/import/editor_import_collada.cpp b/editor/import/editor_import_collada.cpp index 907c7b045c2..e0a2ea624e2 100644 --- a/editor/import/editor_import_collada.cpp +++ b/editor/import/editor_import_collada.cpp @@ -72,7 +72,7 @@ struct ColladaImport { Map node_map; //map from collada node to engine node Map node_name_map; //map from collada node to engine node - Map > mesh_cache; + Map > mesh_cache; Map > curve_cache; Map > material_cache; Map skeleton_map; @@ -88,7 +88,7 @@ struct ColladaImport { Error _create_scene(Collada::Node *p_node, Spatial *p_parent); Error _create_resources(Collada::Node *p_node); Error _create_material(const String &p_material); - Error _create_mesh_surfaces(bool p_optimize, Ref &p_mesh, const Map &p_material_map, const Collada::MeshData &meshdata, const Transform &p_local_xform, const Vector &bone_remap, const Collada::SkinControllerData *p_skin_data, const Collada::MorphControllerData *p_morph_data, Vector > p_morph_meshes = Vector >(), bool p_for_morph = false, bool p_use_mesh_material = false); + Error _create_mesh_surfaces(bool p_optimize, Ref &p_mesh, const Map &p_material_map, const Collada::MeshData &meshdata, const Transform &p_local_xform, const Vector &bone_remap, const Collada::SkinControllerData *p_skin_data, const Collada::MorphControllerData *p_morph_data, Vector > p_morph_meshes = Vector >(), bool p_for_morph = false, bool p_use_mesh_material = false); Error load(const String &p_path, int p_flags, bool p_force_make_tangents = false); void _fix_param_animation_tracks(); void create_animation(int p_clip, bool p_make_tracks_in_all_bones, bool p_import_value_tracks); @@ -591,7 +591,7 @@ static void _generate_tangents_and_binormals(const PoolVector &p_indices, c } } -Error ColladaImport::_create_mesh_surfaces(bool p_optimize, Ref &p_mesh, const Map &p_material_map, const Collada::MeshData &meshdata, const Transform &p_local_xform, const Vector &bone_remap, const Collada::SkinControllerData *skin_controller, const Collada::MorphControllerData *p_morph_data, Vector > p_morph_meshes, bool p_for_morph, bool p_use_mesh_material) { +Error ColladaImport::_create_mesh_surfaces(bool p_optimize, Ref &p_mesh, const Map &p_material_map, const Collada::MeshData &meshdata, const Transform &p_local_xform, const Vector &bone_remap, const Collada::SkinControllerData *skin_controller, const Collada::MorphControllerData *p_morph_data, Vector > p_morph_meshes, bool p_for_morph, bool p_use_mesh_material) { bool local_xform_mirror = p_local_xform.basis.determinant() < 0; @@ -1530,7 +1530,7 @@ Error ColladaImport::_create_resources(Collada::Node *p_node) { String meshid; Transform apply_xform; Vector bone_remap; - Vector > morphs; + Vector > morphs; print_line("mesh: " + String(mi->get_name())); @@ -1621,9 +1621,9 @@ Error ColladaImport::_create_resources(Collada::Node *p_node) { String meshid = names[i]; if (collada.state.mesh_data_map.has(meshid)) { - Ref mesh = Ref(memnew(Mesh)); + Ref mesh = Ref(memnew(ArrayMesh)); const Collada::MeshData &meshdata = collada.state.mesh_data_map[meshid]; - Error err = _create_mesh_surfaces(false, mesh, ng->material_map, meshdata, apply_xform, bone_remap, skin, NULL, Vector >(), true); + Error err = _create_mesh_surfaces(false, mesh, ng->material_map, meshdata, apply_xform, bone_remap, skin, NULL, Vector >(), true); ERR_FAIL_COND_V(err, err); morphs.push_back(mesh); @@ -1648,7 +1648,7 @@ Error ColladaImport::_create_resources(Collada::Node *p_node) { meshid = ng->source; } - Ref mesh; + Ref mesh; if (mesh_cache.has(meshid)) { mesh = mesh_cache[meshid]; } else { @@ -1656,7 +1656,7 @@ Error ColladaImport::_create_resources(Collada::Node *p_node) { //bleh, must ignore invalid ERR_FAIL_COND_V(!collada.state.mesh_data_map.has(meshid), ERR_INVALID_DATA); - mesh = Ref(memnew(Mesh)); + mesh = Ref(memnew(ArrayMesh)); const Collada::MeshData &meshdata = collada.state.mesh_data_map[meshid]; mesh->set_name(meshdata.name); Error err = _create_mesh_surfaces(morphs.size() == 0, mesh, ng->material_map, meshdata, apply_xform, bone_remap, skin, morph, morphs, false, use_mesh_builtin_materials); diff --git a/editor/import/resource_importer_obj.cpp b/editor/import/resource_importer_obj.cpp index 21c2ae6eb3c..8d0f3267f7a 100644 --- a/editor/import/resource_importer_obj.cpp +++ b/editor/import/resource_importer_obj.cpp @@ -89,7 +89,7 @@ Error ResourceImporterOBJ::import(const String &p_source_file, const String &p_s FileAccessRef f = FileAccess::open(p_source_file, FileAccess::READ); ERR_FAIL_COND_V(!f, ERR_CANT_OPEN); - Ref mesh = Ref(memnew(Mesh)); + Ref mesh = Ref(memnew(ArrayMesh)); Map > name_map; bool generate_normals = p_options["generate/normals"]; diff --git a/editor/import/resource_importer_scene.cpp b/editor/import/resource_importer_scene.cpp index 755f4eb219d..d2d2d45a478 100644 --- a/editor/import/resource_importer_scene.cpp +++ b/editor/import/resource_importer_scene.cpp @@ -137,7 +137,7 @@ static String _fixstr(const String &p_what, const String &p_str) { return p_what; } -Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map, Ref > &collision_map) { +Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map, Ref > &collision_map) { // children first.. for (int i = 0; i < p_node->get_child_count(); i++) { @@ -175,7 +175,7 @@ Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map mi->set_flag(GeometryInstance::FLAG_BILLBOARD, true); if (mi->get_mesh().is_valid()) { - Ref m = mi->get_mesh(); + Ref m = mi->get_mesh(); for (int i = 0; i < m->get_surface_count(); i++) { Ref fm = m->surface_get_material(i); @@ -194,7 +194,7 @@ Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map MeshInstance *mi = p_node->cast_to(); - Ref m = mi->get_mesh(); + Ref m = mi->get_mesh(); if (m.is_valid()) { @@ -275,7 +275,7 @@ Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map if (mi->get_mesh().is_valid()) { - Ref m = mi->get_mesh(); + Ref m = mi->get_mesh(); for (int i = 0; i < m->get_surface_count(); i++) { Ref fm = m->surface_get_material(i); @@ -325,7 +325,7 @@ Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map /*if (mi->get_mesh().is_valid()) { - Ref m = mi->get_mesh(); + Ref m = mi->get_mesh(); for(int i=0;iget_surface_count();i++) { Ref fm = m->surface_get_material(i); @@ -477,7 +477,7 @@ Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map MeshInstance *mi = p_node->cast_to(); - Ref mesh = mi->get_mesh(); + Ref mesh = mi->get_mesh(); ERR_FAIL_COND_V(mesh.is_null(), NULL); NavigationMeshInstance *nmi = memnew(NavigationMeshInstance); @@ -655,7 +655,7 @@ Node *ResourceImporterScene::_fix_node(Node *p_node, Node *p_root, Map MeshInstance *mi = p_node->cast_to(); - Ref mesh = mi->get_mesh(); + Ref mesh = mi->get_mesh(); if (!mesh.is_null()) { if (_teststr(mesh->get_name(), "col")) { @@ -972,7 +972,7 @@ static String _make_extname(const String &p_str) { return ext_name; } -void ResourceImporterScene::_make_external_resources(Node *p_node, const String &p_base_path, bool p_make_materials, bool p_make_meshes, Map, Ref > &p_materials, Map, Ref > &p_meshes) { +void ResourceImporterScene::_make_external_resources(Node *p_node, const String &p_base_path, bool p_make_materials, bool p_make_meshes, Map, Ref > &p_materials, Map, Ref > &p_meshes) { List pi; @@ -1005,7 +1005,7 @@ void ResourceImporterScene::_make_external_resources(Node *p_node, const String } } else { - Ref mesh = p_node->get(E->get().name); + Ref mesh = p_node->get(E->get().name); if (mesh.is_valid()) { @@ -1018,7 +1018,7 @@ void ResourceImporterScene::_make_external_resources(Node *p_node, const String String ext_name = p_base_path + "." + _make_extname(mesh->get_name()) + ".msh"; if (FileAccess::exists(ext_name)) { //if exists, use it - Ref existing = ResourceLoader::load(ext_name); + Ref existing = ResourceLoader::load(ext_name); p_meshes[mesh] = existing; } else { @@ -1059,7 +1059,7 @@ void ResourceImporterScene::_make_external_resources(Node *p_node, const String } if (!p_make_meshes) { - p_meshes[mesh] = Ref(); //save it anyway, so it won't be checked again + p_meshes[mesh] = Ref(); //save it anyway, so it won't be checked again } } } @@ -1192,7 +1192,7 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p float anim_optimizer_angerr = p_options["animation/optimizer/max_angular_error"]; float anim_optimizer_maxang = p_options["animation/optimizer/max_angle"]; - Map, Ref > collision_map; + Map, Ref > collision_map; scene = _fix_node(scene, scene, collision_map); @@ -1230,7 +1230,7 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p if (external_materials || external_meshes) { Map, Ref > mat_map; - Map, Ref > mesh_map; + Map, Ref > mesh_map; _make_external_resources(scene, p_source_file.get_basename(), external_materials, external_meshes, mat_map, mesh_map); } diff --git a/editor/import/resource_importer_scene.h b/editor/import/resource_importer_scene.h index 9f7b1a84e64..ede3028b297 100644 --- a/editor/import/resource_importer_scene.h +++ b/editor/import/resource_importer_scene.h @@ -32,6 +32,7 @@ #include "io/resource_import.h" #include "scene/resources/animation.h" +#include "scene/resources/mesh.h" #include "scene/resources/shape.h" class Material; @@ -100,9 +101,9 @@ public: virtual void get_import_options(List *r_options, int p_preset = 0) const; virtual bool get_option_visibility(const String &p_option, const Map &p_options) const; - void _make_external_resources(Node *p_node, const String &p_base_path, bool p_make_materials, bool p_make_meshes, Map, Ref > &p_materials, Map, Ref > &p_meshes); + void _make_external_resources(Node *p_node, const String &p_base_path, bool p_make_materials, bool p_make_meshes, Map, Ref > &p_materials, Map, Ref > &p_meshes); - Node *_fix_node(Node *p_node, Node *p_root, Map, Ref > &collision_map); + Node *_fix_node(Node *p_node, Node *p_root, Map, Ref > &collision_map); void _create_clips(Node *scene, const Array &p_clips, bool p_bake_all); void _filter_anim_tracks(Ref anim, Set &keep); diff --git a/editor/plugins/spatial_editor_plugin.cpp b/editor/plugins/spatial_editor_plugin.cpp index 3536ecd0942..61f6880433c 100644 --- a/editor/plugins/spatial_editor_plugin.cpp +++ b/editor/plugins/spatial_editor_plugin.cpp @@ -3055,8 +3055,8 @@ void SpatialEditor::_init_indicators() { for (int i = 0; i < 3; i++) { - move_gizmo[i] = Ref(memnew(Mesh)); - rotate_gizmo[i] = Ref(memnew(Mesh)); + move_gizmo[i] = Ref(memnew(ArrayMesh)); + rotate_gizmo[i] = Ref(memnew(ArrayMesh)); Ref mat = memnew(SpatialMaterial); mat->set_flag(SpatialMaterial::FLAG_UNSHADED, true); diff --git a/editor/plugins/spatial_editor_plugin.h b/editor/plugins/spatial_editor_plugin.h index 88245ad0dc5..394002db3b5 100644 --- a/editor/plugins/spatial_editor_plugin.h +++ b/editor/plugins/spatial_editor_plugin.h @@ -330,13 +330,13 @@ private: bool grid_enable[3]; //should be always visible if true bool grid_enabled; - Ref move_gizmo[3], rotate_gizmo[3]; + Ref move_gizmo[3], rotate_gizmo[3]; Ref gizmo_color[3]; Ref gizmo_hl; int over_gizmo_handle; - Ref selection_box; + Ref selection_box; RID indicators; RID indicators_instance; RID cursor_mesh; @@ -472,8 +472,8 @@ public: float get_rotate_snap() const { return snap_rotate->get_text().to_double(); } float get_scale_snap() const { return snap_scale->get_text().to_double(); } - Ref get_move_gizmo(int idx) const { return move_gizmo[idx]; } - Ref get_rotate_gizmo(int idx) const { return rotate_gizmo[idx]; } + Ref get_move_gizmo(int idx) const { return move_gizmo[idx]; } + Ref get_rotate_gizmo(int idx) const { return rotate_gizmo[idx]; } void update_transform_gizmo(); diff --git a/editor/spatial_editor_gizmos.cpp b/editor/spatial_editor_gizmos.cpp index 4781bb6a3bc..149b06e50a6 100644 --- a/editor/spatial_editor_gizmos.cpp +++ b/editor/spatial_editor_gizmos.cpp @@ -79,7 +79,7 @@ void EditorSpatialGizmo::Instance::create_instance(Spatial *p_base) { VS::get_singleton()->instance_set_layer_mask(instance, 1 << SpatialEditorViewport::GIZMO_EDIT_LAYER); //gizmos are 26 } -void EditorSpatialGizmo::add_mesh(const Ref &p_mesh, bool p_billboard, const RID &p_skeleton) { +void EditorSpatialGizmo::add_mesh(const Ref &p_mesh, bool p_billboard, const RID &p_skeleton) { ERR_FAIL_COND(!spatial_node); Instance ins; @@ -100,7 +100,7 @@ void EditorSpatialGizmo::add_lines(const Vector &p_lines, const Ref mesh = memnew(Mesh); + Ref mesh = memnew(ArrayMesh); Array a; a.resize(Mesh::ARRAY_MAX); @@ -162,7 +162,7 @@ void EditorSpatialGizmo::add_unscaled_billboard(const Ref &p_material, uv.push_back(Vector2(0, 1)); uv.push_back(Vector2(1, 1)); - Ref mesh = memnew(Mesh); + Ref mesh = memnew(ArrayMesh); Array a; a.resize(Mesh::ARRAY_MAX); a[Mesh::ARRAY_VERTEX] = vs; @@ -219,7 +219,7 @@ void EditorSpatialGizmo::add_handles(const Vector &p_handles, bool p_bi ERR_FAIL_COND(!spatial_node); Instance ins; - Ref mesh = memnew(Mesh); + Ref mesh = memnew(ArrayMesh); #if 1 Array a; @@ -1029,7 +1029,7 @@ CameraSpatialGizmo::CameraSpatialGizmo(Camera *p_camera) { void MeshInstanceSpatialGizmo::redraw() { - Ref m = mesh->get_mesh(); + Ref m = mesh->get_mesh(); if (!m.is_valid()) return; //none @@ -1248,7 +1248,7 @@ void SkeletonSpatialGizmo::redraw() { */ } - Ref m = surface_tool->commit(); + Ref m = surface_tool->commit(); add_mesh(m, false, skel->get_skeleton()); } @@ -2511,7 +2511,7 @@ void NavigationMeshSpatialGizmo::redraw() { if (lines.size()) add_lines(lines, navmesh->is_enabled() ? SpatialEditorGizmos::singleton->navmesh_edge_material : SpatialEditorGizmos::singleton->navmesh_edge_material_disabled); add_collision_triangles(tmesh); - Ref m = memnew(Mesh); + Ref m = memnew(ArrayMesh); Array a; a.resize(Mesh::ARRAY_MAX); a[0] = tmeshfaces; @@ -3213,7 +3213,7 @@ SpatialEditorGizmos::SpatialEditorGizmos() { //position 3D Shared mesh - pos3d_mesh = Ref(memnew(Mesh)); + pos3d_mesh = Ref(memnew(ArrayMesh)); { PoolVector cursor_points; @@ -3246,7 +3246,7 @@ SpatialEditorGizmos::SpatialEditorGizmos() { pos3d_mesh->surface_set_material(0, mat); } - listener_line_mesh = Ref(memnew(Mesh)); + listener_line_mesh = Ref(memnew(ArrayMesh)); { PoolVector cursor_points; diff --git a/editor/spatial_editor_gizmos.h b/editor/spatial_editor_gizmos.h index 095586ab915..6a77e914259 100644 --- a/editor/spatial_editor_gizmos.h +++ b/editor/spatial_editor_gizmos.h @@ -59,7 +59,7 @@ class EditorSpatialGizmo : public SpatialEditorGizmo { struct Instance { RID instance; - Ref mesh; + Ref mesh; RID skeleton; bool billboard; bool unscaled; @@ -97,7 +97,7 @@ class EditorSpatialGizmo : public SpatialEditorGizmo { protected: void add_lines(const Vector &p_lines, const Ref &p_material, bool p_billboard = false); - void add_mesh(const Ref &p_mesh, bool p_billboard = false, const RID &p_skeleton = RID()); + void add_mesh(const Ref &p_mesh, bool p_billboard = false, const RID &p_skeleton = RID()); void add_collision_segments(const Vector &p_lines); void add_collision_triangles(const Ref &p_tmesh); void add_unscaled_billboard(const Ref &p_material, float p_scale = 1); @@ -454,8 +454,8 @@ public: Ref shape_material; Ref handle_t; - Ref pos3d_mesh; - Ref listener_line_mesh; + Ref pos3d_mesh; + Ref listener_line_mesh; static SpatialEditorGizmos *singleton; Ref test_cube_tm; diff --git a/scene/3d/gi_probe.cpp b/scene/3d/gi_probe.cpp index 2acbed3b4ea..ec3e0592498 100644 --- a/scene/3d/gi_probe.cpp +++ b/scene/3d/gi_probe.cpp @@ -973,7 +973,7 @@ GIProbe::Baker::MaterialCache GIProbe::_get_material_cache(Ref p_mater return mc; } -void GIProbe::_plot_mesh(const Transform &p_xform, Ref &p_mesh, Baker *p_baker, const Vector > &p_materials, const Ref &p_override_material) { +void GIProbe::_plot_mesh(const Transform &p_xform, Ref &p_mesh, Baker *p_baker, const Vector > &p_materials, const Ref &p_override_material) { for (int i = 0; i < p_mesh->get_surface_count(); i++) { @@ -1067,7 +1067,7 @@ void GIProbe::_find_meshes(Node *p_at_node, Baker *p_baker) { MeshInstance *mi = p_at_node->cast_to(); if (mi && mi->get_flag(GeometryInstance::FLAG_USE_BAKED_LIGHT)) { - Ref mesh = mi->get_mesh(); + Ref mesh = mi->get_mesh(); if (mesh.is_valid()) { Rect3 aabb = mesh->get_aabb(); @@ -1094,7 +1094,7 @@ void GIProbe::_find_meshes(Node *p_at_node, Baker *p_baker) { for (int i = 0; i < meshes.size(); i += 2) { Transform mxf = meshes[i]; - Ref mesh = meshes[i + 1]; + Ref mesh = meshes[i + 1]; if (!mesh.is_valid()) continue; @@ -1317,7 +1317,7 @@ void GIProbe::_create_debug_mesh(Baker *p_baker) { print_line("leaf voxels: " + itos(p_baker->leaf_voxel_count)); mm->set_instance_count(p_baker->leaf_voxel_count); - Ref mesh; + Ref mesh; mesh.instance(); { diff --git a/scene/3d/gi_probe.h b/scene/3d/gi_probe.h index 3b05d9952bc..b5ee86455ee 100644 --- a/scene/3d/gi_probe.h +++ b/scene/3d/gi_probe.h @@ -145,7 +145,7 @@ private: struct PlotMesh { Ref override_material; Vector > instance_materials; - Ref mesh; + Ref mesh; Transform local_xform; }; @@ -173,7 +173,7 @@ private: Vector _get_bake_texture(Ref p_image, const Color &p_color); Baker::MaterialCache _get_material_cache(Ref p_material, Baker *p_baker); void _plot_face(int p_idx, int p_level, int p_x, int p_y, int p_z, const Vector3 *p_vtx, const Vector2 *p_uv, const Baker::MaterialCache &p_material, const Rect3 &p_aabb, Baker *p_baker); - void _plot_mesh(const Transform &p_xform, Ref &p_mesh, Baker *p_baker, const Vector > &p_materials, const Ref &p_override_material); + void _plot_mesh(const Transform &p_xform, Ref &p_mesh, Baker *p_baker, const Vector > &p_materials, const Ref &p_override_material); void _find_meshes(Node *p_at_node, Baker *p_baker); void _fixup_plot(int p_idx, int p_level, int p_x, int p_y, int p_z, Baker *p_baker); diff --git a/scene/3d/listener.cpp b/scene/3d/listener.cpp index 148afbffa29..c7d3bac2f80 100644 --- a/scene/3d/listener.cpp +++ b/scene/3d/listener.cpp @@ -152,7 +152,7 @@ bool Listener::_can_gizmo_scale() const { } RES Listener::_get_gizmo_geometry() const { - Ref mesh = memnew(Mesh); + Ref mesh = memnew(ArrayMesh); return mesh; } diff --git a/scene/3d/navigation_mesh.cpp b/scene/3d/navigation_mesh.cpp index 13fd852fe7d..82f6f665db3 100644 --- a/scene/3d/navigation_mesh.cpp +++ b/scene/3d/navigation_mesh.cpp @@ -187,7 +187,7 @@ Ref NavigationMesh::get_debug_mesh() { } } - debug_mesh = Ref(memnew(Mesh)); + debug_mesh = Ref(memnew(ArrayMesh)); Array arr; arr.resize(Mesh::ARRAY_MAX); diff --git a/scene/3d/navigation_mesh.h b/scene/3d/navigation_mesh.h index c8f6d936aa6..e5a3dc7b430 100644 --- a/scene/3d/navigation_mesh.h +++ b/scene/3d/navigation_mesh.h @@ -44,7 +44,7 @@ class NavigationMesh : public Resource { Vector indices; }; Vector polygons; - Ref debug_mesh; + Ref debug_mesh; struct _EdgeKey { diff --git a/scene/3d/ray_cast.cpp b/scene/3d/ray_cast.cpp index d24aa6ae2a2..345afd3edfe 100644 --- a/scene/3d/ray_cast.cpp +++ b/scene/3d/ray_cast.cpp @@ -266,7 +266,7 @@ void RayCast::_create_debug_shape() { line_material->set_albedo(Color(1.0, 0.8, 0.6)); } - Ref mesh = memnew(Mesh); + Ref mesh = memnew(ArrayMesh); MeshInstance *mi = memnew(MeshInstance); mi->set_mesh(mesh); @@ -287,7 +287,7 @@ void RayCast::_update_debug_shape() { if (!mi->get_mesh().is_valid()) return; - Ref mesh = mi->get_mesh(); + Ref mesh = mi->get_mesh(); if (mesh->get_surface_count() > 0) mesh->surface_remove(0); diff --git a/scene/main/scene_main_loop.cpp b/scene/main/scene_main_loop.cpp index 96a35198406..f7a255cd336 100644 --- a/scene/main/scene_main_loop.cpp +++ b/scene/main/scene_main_loop.cpp @@ -839,12 +839,12 @@ Ref SceneTree::get_debug_collision_material() { return collision_material; } -Ref SceneTree::get_debug_contact_mesh() { +Ref SceneTree::get_debug_contact_mesh() { if (debug_contact_mesh.is_valid()) return debug_contact_mesh; - debug_contact_mesh = Ref(memnew(Mesh)); + debug_contact_mesh = Ref(memnew(ArrayMesh)); Ref mat = memnew(SpatialMaterial); /*mat->set_flag(Material::FLAG_UNSHADED,true); diff --git a/scene/main/scene_main_loop.h b/scene/main/scene_main_loop.h index 5d42c66652b..2ea79bf945b 100644 --- a/scene/main/scene_main_loop.h +++ b/scene/main/scene_main_loop.h @@ -33,6 +33,7 @@ #include "io/networked_multiplayer_peer.h" #include "os/main_loop.h" #include "os/thread_safe.h" +#include "scene/resources/mesh.h" #include "scene/resources/world.h" #include "scene/resources/world_2d.h" #include "self_list.h" @@ -169,7 +170,7 @@ private: Color debug_collision_contact_color; Color debug_navigation_color; Color debug_navigation_disabled_color; - Ref debug_contact_mesh; + Ref debug_contact_mesh; Ref navigation_material; Ref navigation_disabled_material; Ref collision_material; @@ -406,7 +407,7 @@ public: Ref get_debug_navigation_material(); Ref get_debug_navigation_disabled_material(); Ref get_debug_collision_material(); - Ref get_debug_contact_mesh(); + Ref get_debug_contact_mesh(); int get_collision_debug_contact_count() { return collision_debug_contacts; } diff --git a/scene/register_scene_types.cpp b/scene/register_scene_types.cpp index 0a3f64eacd7..9f078072d78 100644 --- a/scene/register_scene_types.cpp +++ b/scene/register_scene_types.cpp @@ -523,11 +523,12 @@ void register_scene_types() { ClassDB::register_virtual_class(); #ifndef _3D_DISABLED - ClassDB::register_class(); - ClassDB::register_class(); + ClassDB::register_virtual_class(); + ClassDB::register_class(); ClassDB::register_virtual_class(); ClassDB::register_class(); ClassDB::add_compatibility_class("FixedSpatialMaterial", "SpatialMaterial"); + ClassDB::add_compatibility_class("Mesh", "ArrayMesh"); SceneTree::add_idle_callback(SpatialMaterial::flush_changes); SpatialMaterial::init_shaders(); diff --git a/scene/resources/mesh.cpp b/scene/resources/mesh.cpp index 4846d84b33c..e2ede41290a 100644 --- a/scene/resources/mesh.cpp +++ b/scene/resources/mesh.cpp @@ -32,6 +32,390 @@ #include "scene/resources/convex_polygon_shape.h" #include "surface_tool.h" +void Mesh::_clear_triangle_mesh() { + + triangle_mesh.unref(); + ; +} + +Ref Mesh::generate_triangle_mesh() const { + + if (triangle_mesh.is_valid()) + return triangle_mesh; + + int facecount = 0; + + for (int i = 0; i < get_surface_count(); i++) { + + if (surface_get_primitive_type(i) != PRIMITIVE_TRIANGLES) + continue; + + if (surface_get_format(i) & ARRAY_FORMAT_INDEX) { + + facecount += surface_get_array_index_len(i); + } else { + + facecount += surface_get_array_len(i); + } + } + + if (facecount == 0 || (facecount % 3) != 0) + return triangle_mesh; + + PoolVector faces; + faces.resize(facecount); + PoolVector::Write facesw = faces.write(); + + int widx = 0; + + for (int i = 0; i < get_surface_count(); i++) { + + if (surface_get_primitive_type(i) != PRIMITIVE_TRIANGLES) + continue; + + Array a = surface_get_arrays(i); + + int vc = surface_get_array_len(i); + PoolVector vertices = a[ARRAY_VERTEX]; + PoolVector::Read vr = vertices.read(); + + if (surface_get_format(i) & ARRAY_FORMAT_INDEX) { + + int ic = surface_get_array_index_len(i); + PoolVector indices = a[ARRAY_INDEX]; + PoolVector::Read ir = indices.read(); + + for (int i = 0; i < ic; i++) { + int index = ir[i]; + facesw[widx++] = vr[index]; + } + + } else { + + for (int i = 0; i < vc; i++) + facesw[widx++] = vr[i]; + } + } + + facesw = PoolVector::Write(); + + triangle_mesh = Ref(memnew(TriangleMesh)); + triangle_mesh->create(faces); + + return triangle_mesh; +} + +PoolVector Mesh::get_faces() const { + + Ref tm = generate_triangle_mesh(); + if (tm.is_valid()) + return tm->get_faces(); + return PoolVector(); + /* + for (int i=0;imesh_surface_get_primitive_type( mesh, i ) != VisualServer::PRIMITIVE_TRIANGLES ) + continue; + + PoolVector indices; + PoolVector vertices; + + vertices=VisualServer::get_singleton()->mesh_surface_get_array(mesh, i,VisualServer::ARRAY_VERTEX); + + int len=VisualServer::get_singleton()->mesh_surface_get_array_index_len(mesh, i); + bool has_indices; + + if (len>0) { + + indices=VisualServer::get_singleton()->mesh_surface_get_array(mesh, i,VisualServer::ARRAY_INDEX); + has_indices=true; + + } else { + + len=vertices.size(); + has_indices=false; + } + + if (len<=0) + continue; + + PoolVector::Read indicesr = indices.read(); + const int *indicesptr = indicesr.ptr(); + + PoolVector::Read verticesr = vertices.read(); + const Vector3 *verticesptr = verticesr.ptr(); + + int old_faces=faces.size(); + int new_faces=old_faces+(len/3); + + faces.resize(new_faces); + + PoolVector::Write facesw = faces.write(); + Face3 *facesptr=facesw.ptr(); + + + for (int i=0;i Mesh::create_convex_shape() const { + + PoolVector vertices; + + for (int i = 0; i < get_surface_count(); i++) { + + Array a = surface_get_arrays(i); + PoolVector v = a[ARRAY_VERTEX]; + vertices.append_array(v); + } + + Ref shape = memnew(ConvexPolygonShape); + shape->set_points(vertices); + return shape; +} + +Ref Mesh::create_trimesh_shape() const { + + PoolVector faces = get_faces(); + if (faces.size() == 0) + return Ref(); + + PoolVector face_points; + face_points.resize(faces.size() * 3); + + for (int i = 0; i < face_points.size(); i++) { + + Face3 f = faces.get(i / 3); + face_points.set(i, f.vertex[i % 3]); + } + + Ref shape = memnew(ConcavePolygonShape); + shape->set_faces(face_points); + return shape; +} + +Ref Mesh::create_outline(float p_margin) const { + + Array arrays; + int index_accum = 0; + for (int i = 0; i < get_surface_count(); i++) { + + if (surface_get_primitive_type(i) != PRIMITIVE_TRIANGLES) + continue; + + Array a = surface_get_arrays(i); + int vcount = 0; + + if (i == 0) { + arrays = a; + PoolVector v = a[ARRAY_VERTEX]; + index_accum += v.size(); + } else { + + for (int j = 0; j < arrays.size(); j++) { + + if (arrays[j].get_type() == Variant::NIL || a[j].get_type() == Variant::NIL) { + //mismatch, do not use + arrays[j] = Variant(); + continue; + } + + switch (j) { + + case ARRAY_VERTEX: + case ARRAY_NORMAL: { + + PoolVector dst = arrays[j]; + PoolVector src = a[j]; + if (j == ARRAY_VERTEX) + vcount = src.size(); + if (dst.size() == 0 || src.size() == 0) { + arrays[j] = Variant(); + continue; + } + dst.append_array(src); + arrays[j] = dst; + } break; + case ARRAY_TANGENT: + case ARRAY_BONES: + case ARRAY_WEIGHTS: { + + PoolVector dst = arrays[j]; + PoolVector src = a[j]; + if (dst.size() == 0 || src.size() == 0) { + arrays[j] = Variant(); + continue; + } + dst.append_array(src); + arrays[j] = dst; + + } break; + case ARRAY_COLOR: { + PoolVector dst = arrays[j]; + PoolVector src = a[j]; + if (dst.size() == 0 || src.size() == 0) { + arrays[j] = Variant(); + continue; + } + dst.append_array(src); + arrays[j] = dst; + + } break; + case ARRAY_TEX_UV: + case ARRAY_TEX_UV2: { + PoolVector dst = arrays[j]; + PoolVector src = a[j]; + if (dst.size() == 0 || src.size() == 0) { + arrays[j] = Variant(); + continue; + } + dst.append_array(src); + arrays[j] = dst; + + } break; + case ARRAY_INDEX: { + PoolVector dst = arrays[j]; + PoolVector src = a[j]; + if (dst.size() == 0 || src.size() == 0) { + arrays[j] = Variant(); + continue; + } + { + int ss = src.size(); + PoolVector::Write w = src.write(); + for (int k = 0; k < ss; k++) { + w[k] += index_accum; + } + } + dst.append_array(src); + arrays[j] = dst; + index_accum += vcount; + + } break; + } + } + } + } + + { + PoolVector::Write ir; + PoolVector indices = arrays[ARRAY_INDEX]; + bool has_indices = false; + PoolVector vertices = arrays[ARRAY_VERTEX]; + int vc = vertices.size(); + ERR_FAIL_COND_V(!vc, Ref()); + PoolVector::Write r = vertices.write(); + + if (indices.size()) { + vc = indices.size(); + ir = indices.write(); + has_indices = true; + } + + Map normal_accum; + + //fill normals with triangle normals + for (int i = 0; i < vc; i += 3) { + + Vector3 t[3]; + + if (has_indices) { + t[0] = r[ir[i + 0]]; + t[1] = r[ir[i + 1]]; + t[2] = r[ir[i + 2]]; + } else { + t[0] = r[i + 0]; + t[1] = r[i + 1]; + t[2] = r[i + 2]; + } + + Vector3 n = Plane(t[0], t[1], t[2]).normal; + + for (int j = 0; j < 3; j++) { + + Map::Element *E = normal_accum.find(t[j]); + if (!E) { + normal_accum[t[j]] = n; + } else { + float d = n.dot(E->get()); + if (d < 1.0) + E->get() += n * (1.0 - d); + //E->get()+=n; + } + } + } + + //normalize + + for (Map::Element *E = normal_accum.front(); E; E = E->next()) { + E->get().normalize(); + } + + //displace normals + int vc2 = vertices.size(); + + for (int i = 0; i < vc2; i++) { + + Vector3 t = r[i]; + + Map::Element *E = normal_accum.find(t); + ERR_CONTINUE(!E); + + t += E->get() * p_margin; + r[i] = t; + } + + r = PoolVector::Write(); + arrays[ARRAY_VERTEX] = vertices; + + if (!has_indices) { + + PoolVector new_indices; + new_indices.resize(vertices.size()); + PoolVector::Write iw = new_indices.write(); + + for (int j = 0; j < vc2; j += 3) { + + iw[j] = j; + iw[j + 1] = j + 2; + iw[j + 2] = j + 1; + } + + iw = PoolVector::Write(); + arrays[ARRAY_INDEX] = new_indices; + + } else { + + for (int j = 0; j < vc; j += 3) { + + SWAP(ir[j + 1], ir[j + 2]); + } + ir = PoolVector::Write(); + arrays[ARRAY_INDEX] = indices; + } + } + + Ref newmesh = memnew(ArrayMesh); + newmesh->add_surface_from_arrays(PRIMITIVE_TRIANGLES, arrays); + return newmesh; +} + +Mesh::Mesh() { +} + static const char *_array_name[] = { "vertex_array", "normal_array", @@ -45,34 +429,34 @@ static const char *_array_name[] = { NULL }; -static const Mesh::ArrayType _array_types[] = { +static const ArrayMesh::ArrayType _array_types[] = { - Mesh::ARRAY_VERTEX, - Mesh::ARRAY_NORMAL, - Mesh::ARRAY_TANGENT, - Mesh::ARRAY_COLOR, - Mesh::ARRAY_TEX_UV, - Mesh::ARRAY_TEX_UV2, - Mesh::ARRAY_BONES, - Mesh::ARRAY_WEIGHTS, - Mesh::ARRAY_INDEX + ArrayMesh::ARRAY_VERTEX, + ArrayMesh::ARRAY_NORMAL, + ArrayMesh::ARRAY_TANGENT, + ArrayMesh::ARRAY_COLOR, + ArrayMesh::ARRAY_TEX_UV, + ArrayMesh::ARRAY_TEX_UV2, + ArrayMesh::ARRAY_BONES, + ArrayMesh::ARRAY_WEIGHTS, + ArrayMesh::ARRAY_INDEX }; /* compatibility */ static const int _format_translate[] = { - Mesh::ARRAY_FORMAT_VERTEX, - Mesh::ARRAY_FORMAT_NORMAL, - Mesh::ARRAY_FORMAT_TANGENT, - Mesh::ARRAY_FORMAT_COLOR, - Mesh::ARRAY_FORMAT_TEX_UV, - Mesh::ARRAY_FORMAT_TEX_UV2, - Mesh::ARRAY_FORMAT_BONES, - Mesh::ARRAY_FORMAT_WEIGHTS, - Mesh::ARRAY_FORMAT_INDEX, + ArrayMesh::ARRAY_FORMAT_VERTEX, + ArrayMesh::ARRAY_FORMAT_NORMAL, + ArrayMesh::ARRAY_FORMAT_TANGENT, + ArrayMesh::ARRAY_FORMAT_COLOR, + ArrayMesh::ARRAY_FORMAT_TEX_UV, + ArrayMesh::ARRAY_FORMAT_TEX_UV2, + ArrayMesh::ARRAY_FORMAT_BONES, + ArrayMesh::ARRAY_FORMAT_WEIGHTS, + ArrayMesh::ARRAY_FORMAT_INDEX, }; -bool Mesh::_set(const StringName &p_name, const Variant &p_value) { +bool ArrayMesh::_set(const StringName &p_name, const Variant &p_value) { String sname = p_name; @@ -191,7 +575,7 @@ bool Mesh::_set(const StringName &p_name, const Variant &p_value) { return false; } -bool Mesh::_get(const StringName &p_name, Variant &r_ret) const { +bool ArrayMesh::_get(const StringName &p_name, Variant &r_ret) const { if (_is_generated()) return false; @@ -270,7 +654,7 @@ bool Mesh::_get(const StringName &p_name, Variant &r_ret) const { return true; } -void Mesh::_get_property_list(List *p_list) const { +void ArrayMesh::_get_property_list(List *p_list) const { if (_is_generated()) return; @@ -290,7 +674,7 @@ void Mesh::_get_property_list(List *p_list) const { p_list->push_back(PropertyInfo(Variant::RECT3, "custom_aabb/custom_aabb")); } -void Mesh::_recompute_aabb() { +void ArrayMesh::_recompute_aabb() { // regenerate AABB aabb = Rect3(); @@ -304,7 +688,7 @@ void Mesh::_recompute_aabb() { } } -void Mesh::add_surface(uint32_t p_format, PrimitiveType p_primitive, const PoolVector &p_array, int p_vertex_count, const PoolVector &p_index_array, int p_index_count, const Rect3 &p_aabb, const Vector > &p_blend_shapes, const Vector &p_bone_aabbs) { +void ArrayMesh::add_surface(uint32_t p_format, PrimitiveType p_primitive, const PoolVector &p_array, int p_vertex_count, const PoolVector &p_index_array, int p_index_count, const Rect3 &p_aabb, const Vector > &p_blend_shapes, const Vector &p_bone_aabbs) { Surface s; s.aabb = p_aabb; @@ -313,7 +697,7 @@ void Mesh::add_surface(uint32_t p_format, PrimitiveType p_primitive, const PoolV VisualServer::get_singleton()->mesh_add_surface(mesh, p_format, (VS::PrimitiveType)p_primitive, p_array, p_vertex_count, p_index_array, p_index_count, p_aabb, p_blend_shapes, p_bone_aabbs); } -void Mesh::add_surface_from_arrays(PrimitiveType p_primitive, const Array &p_arrays, const Array &p_blend_shapes, uint32_t p_flags) { +void ArrayMesh::add_surface_from_arrays(PrimitiveType p_primitive, const Array &p_arrays, const Array &p_blend_shapes, uint32_t p_flags) { ERR_FAIL_COND(p_arrays.size() != ARRAY_MAX); @@ -345,28 +729,28 @@ void Mesh::add_surface_from_arrays(PrimitiveType p_primitive, const Array &p_arr _recompute_aabb(); } - triangle_mesh = Ref(); + _clear_triangle_mesh(); _change_notify(); emit_changed(); } -Array Mesh::surface_get_arrays(int p_surface) const { +Array ArrayMesh::surface_get_arrays(int p_surface) const { ERR_FAIL_INDEX_V(p_surface, surfaces.size(), Array()); return VisualServer::get_singleton()->mesh_surface_get_arrays(mesh, p_surface); } -Array Mesh::surface_get_blend_shape_arrays(int p_surface) const { +Array ArrayMesh::surface_get_blend_shape_arrays(int p_surface) const { ERR_FAIL_INDEX_V(p_surface, surfaces.size(), Array()); return Array(); } -int Mesh::get_surface_count() const { +int ArrayMesh::get_surface_count() const { return surfaces.size(); } -void Mesh::add_blend_shape(const StringName &p_name) { +void ArrayMesh::add_blend_shape(const StringName &p_name) { if (surfaces.size()) { ERR_EXPLAIN("Can't add a shape key count if surfaces are already created."); @@ -389,15 +773,15 @@ void Mesh::add_blend_shape(const StringName &p_name) { VS::get_singleton()->mesh_set_blend_shape_count(mesh, blend_shapes.size()); } -int Mesh::get_blend_shape_count() const { +int ArrayMesh::get_blend_shape_count() const { return blend_shapes.size(); } -StringName Mesh::get_blend_shape_name(int p_index) const { +StringName ArrayMesh::get_blend_shape_name(int p_index) const { ERR_FAIL_INDEX_V(p_index, blend_shapes.size(), StringName()); return blend_shapes[p_index]; } -void Mesh::clear_blend_shapes() { +void ArrayMesh::clear_blend_shapes() { if (surfaces.size()) { ERR_EXPLAIN("Can't set shape key count if surfaces are already created."); @@ -407,54 +791,54 @@ void Mesh::clear_blend_shapes() { blend_shapes.clear(); } -void Mesh::set_blend_shape_mode(BlendShapeMode p_mode) { +void ArrayMesh::set_blend_shape_mode(BlendShapeMode p_mode) { blend_shape_mode = p_mode; VS::get_singleton()->mesh_set_blend_shape_mode(mesh, (VS::BlendShapeMode)p_mode); } -Mesh::BlendShapeMode Mesh::get_blend_shape_mode() const { +ArrayMesh::BlendShapeMode ArrayMesh::get_blend_shape_mode() const { return blend_shape_mode; } -void Mesh::surface_remove(int p_idx) { +void ArrayMesh::surface_remove(int p_idx) { ERR_FAIL_INDEX(p_idx, surfaces.size()); VisualServer::get_singleton()->mesh_remove_surface(mesh, p_idx); surfaces.remove(p_idx); - triangle_mesh = Ref(); + _clear_triangle_mesh(); _recompute_aabb(); _change_notify(); emit_changed(); } -int Mesh::surface_get_array_len(int p_idx) const { +int ArrayMesh::surface_get_array_len(int p_idx) const { ERR_FAIL_INDEX_V(p_idx, surfaces.size(), -1); return VisualServer::get_singleton()->mesh_surface_get_array_len(mesh, p_idx); } -int Mesh::surface_get_array_index_len(int p_idx) const { +int ArrayMesh::surface_get_array_index_len(int p_idx) const { ERR_FAIL_INDEX_V(p_idx, surfaces.size(), -1); return VisualServer::get_singleton()->mesh_surface_get_array_index_len(mesh, p_idx); } -uint32_t Mesh::surface_get_format(int p_idx) const { +uint32_t ArrayMesh::surface_get_format(int p_idx) const { ERR_FAIL_INDEX_V(p_idx, surfaces.size(), 0); return VisualServer::get_singleton()->mesh_surface_get_format(mesh, p_idx); } -Mesh::PrimitiveType Mesh::surface_get_primitive_type(int p_idx) const { +ArrayMesh::PrimitiveType ArrayMesh::surface_get_primitive_type(int p_idx) const { ERR_FAIL_INDEX_V(p_idx, surfaces.size(), PRIMITIVE_LINES); return (PrimitiveType)VisualServer::get_singleton()->mesh_surface_get_primitive_type(mesh, p_idx); } -void Mesh::surface_set_material(int p_idx, const Ref &p_material) { +void ArrayMesh::surface_set_material(int p_idx, const Ref &p_material) { ERR_FAIL_INDEX(p_idx, surfaces.size()); if (surfaces[p_idx].material == p_material) @@ -465,33 +849,33 @@ void Mesh::surface_set_material(int p_idx, const Ref &p_material) { _change_notify("material"); } -void Mesh::surface_set_name(int p_idx, const String &p_name) { +void ArrayMesh::surface_set_name(int p_idx, const String &p_name) { ERR_FAIL_INDEX(p_idx, surfaces.size()); surfaces[p_idx].name = p_name; } -String Mesh::surface_get_name(int p_idx) const { +String ArrayMesh::surface_get_name(int p_idx) const { ERR_FAIL_INDEX_V(p_idx, surfaces.size(), String()); return surfaces[p_idx].name; } -void Mesh::surface_set_custom_aabb(int p_idx, const Rect3 &p_aabb) { +void ArrayMesh::surface_set_custom_aabb(int p_idx, const Rect3 &p_aabb) { ERR_FAIL_INDEX(p_idx, surfaces.size()); surfaces[p_idx].aabb = p_aabb; // set custom aabb too? } -Ref Mesh::surface_get_material(int p_idx) const { +Ref ArrayMesh::surface_get_material(int p_idx) const { ERR_FAIL_INDEX_V(p_idx, surfaces.size(), Ref()); return surfaces[p_idx].material; } -void Mesh::add_surface_from_mesh_data(const Geometry::MeshData &p_mesh_data) { +void ArrayMesh::add_surface_from_mesh_data(const Geometry::MeshData &p_mesh_data) { VisualServer::get_singleton()->mesh_add_surface_from_mesh_data(mesh, p_mesh_data); Rect3 aabb; @@ -510,7 +894,7 @@ void Mesh::add_surface_from_mesh_data(const Geometry::MeshData &p_mesh_data) { else aabb.merge_with(s.aabb); - triangle_mesh = Ref(); + _clear_triangle_mesh(); surfaces.push_back(s); _change_notify(); @@ -518,129 +902,27 @@ void Mesh::add_surface_from_mesh_data(const Geometry::MeshData &p_mesh_data) { emit_changed(); } -RID Mesh::get_rid() const { +RID ArrayMesh::get_rid() const { return mesh; } -Rect3 Mesh::get_aabb() const { +Rect3 ArrayMesh::get_aabb() const { return aabb; } -void Mesh::set_custom_aabb(const Rect3 &p_custom) { +void ArrayMesh::set_custom_aabb(const Rect3 &p_custom) { custom_aabb = p_custom; VS::get_singleton()->mesh_set_custom_aabb(mesh, custom_aabb); } -Rect3 Mesh::get_custom_aabb() const { +Rect3 ArrayMesh::get_custom_aabb() const { return custom_aabb; } -PoolVector Mesh::get_faces() const { - - Ref tm = generate_triangle_mesh(); - if (tm.is_valid()) - return tm->get_faces(); - return PoolVector(); - /* - for (int i=0;imesh_surface_get_primitive_type( mesh, i ) != VisualServer::PRIMITIVE_TRIANGLES ) - continue; - - PoolVector indices; - PoolVector vertices; - - vertices=VisualServer::get_singleton()->mesh_surface_get_array(mesh, i,VisualServer::ARRAY_VERTEX); - - int len=VisualServer::get_singleton()->mesh_surface_get_array_index_len(mesh, i); - bool has_indices; - - if (len>0) { - - indices=VisualServer::get_singleton()->mesh_surface_get_array(mesh, i,VisualServer::ARRAY_INDEX); - has_indices=true; - - } else { - - len=vertices.size(); - has_indices=false; - } - - if (len<=0) - continue; - - PoolVector::Read indicesr = indices.read(); - const int *indicesptr = indicesr.ptr(); - - PoolVector::Read verticesr = vertices.read(); - const Vector3 *verticesptr = verticesr.ptr(); - - int old_faces=faces.size(); - int new_faces=old_faces+(len/3); - - faces.resize(new_faces); - - PoolVector::Write facesw = faces.write(); - Face3 *facesptr=facesw.ptr(); - - - for (int i=0;i Mesh::create_convex_shape() const { - - PoolVector vertices; - - for (int i = 0; i < get_surface_count(); i++) { - - Array a = surface_get_arrays(i); - PoolVector v = a[ARRAY_VERTEX]; - vertices.append_array(v); - } - - Ref shape = memnew(ConvexPolygonShape); - shape->set_points(vertices); - return shape; -} - -Ref Mesh::create_trimesh_shape() const { - - PoolVector faces = get_faces(); - if (faces.size() == 0) - return Ref(); - - PoolVector face_points; - face_points.resize(faces.size() * 3); - - for (int i = 0; i < face_points.size(); i++) { - - Face3 f = faces.get(i / 3); - face_points.set(i, f.vertex[i % 3]); - } - - Ref shape = memnew(ConcavePolygonShape); - shape->set_faces(face_points); - return shape; -} - -void Mesh::center_geometry() { +void ArrayMesh::center_geometry() { /* Vector3 ofs = aabb.pos+aabb.size*0.5; @@ -668,13 +950,13 @@ void Mesh::center_geometry() { */ } -void Mesh::regen_normalmaps() { +void ArrayMesh::regen_normalmaps() { Vector > surfs; for (int i = 0; i < get_surface_count(); i++) { Ref st = memnew(SurfaceTool); - st->create_from(Ref(this), i); + st->create_from(Ref(this), i); surfs.push_back(st); } @@ -685,315 +967,42 @@ void Mesh::regen_normalmaps() { for (int i = 0; i < surfs.size(); i++) { surfs[i]->generate_tangents(); - surfs[i]->commit(Ref(this)); + surfs[i]->commit(Ref(this)); } } -Ref Mesh::generate_triangle_mesh() const { - - if (triangle_mesh.is_valid()) - return triangle_mesh; - - int facecount = 0; - - for (int i = 0; i < get_surface_count(); i++) { - - if (surface_get_primitive_type(i) != PRIMITIVE_TRIANGLES) - continue; - - if (surface_get_format(i) & ARRAY_FORMAT_INDEX) { - - facecount += surface_get_array_index_len(i); - } else { - - facecount += surface_get_array_len(i); - } - } - - if (facecount == 0 || (facecount % 3) != 0) - return triangle_mesh; - - PoolVector faces; - faces.resize(facecount); - PoolVector::Write facesw = faces.write(); - - int widx = 0; - - for (int i = 0; i < get_surface_count(); i++) { - - if (surface_get_primitive_type(i) != PRIMITIVE_TRIANGLES) - continue; - - Array a = surface_get_arrays(i); - - int vc = surface_get_array_len(i); - PoolVector vertices = a[ARRAY_VERTEX]; - PoolVector::Read vr = vertices.read(); - - if (surface_get_format(i) & ARRAY_FORMAT_INDEX) { - - int ic = surface_get_array_index_len(i); - PoolVector indices = a[ARRAY_INDEX]; - PoolVector::Read ir = indices.read(); - - for (int i = 0; i < ic; i++) { - int index = ir[i]; - facesw[widx++] = vr[index]; - } - - } else { - - for (int i = 0; i < vc; i++) - facesw[widx++] = vr[i]; - } - } - - facesw = PoolVector::Write(); - - triangle_mesh = Ref(memnew(TriangleMesh)); - triangle_mesh->create(faces); - - return triangle_mesh; -} - -Ref Mesh::create_outline(float p_margin) const { - - Array arrays; - int index_accum = 0; - for (int i = 0; i < get_surface_count(); i++) { - - if (surface_get_primitive_type(i) != PRIMITIVE_TRIANGLES) - continue; - - Array a = surface_get_arrays(i); - int vcount = 0; - - if (i == 0) { - arrays = a; - PoolVector v = a[ARRAY_VERTEX]; - index_accum += v.size(); - } else { - - for (int j = 0; j < arrays.size(); j++) { - - if (arrays[j].get_type() == Variant::NIL || a[j].get_type() == Variant::NIL) { - //mismatch, do not use - arrays[j] = Variant(); - continue; - } - - switch (j) { - - case ARRAY_VERTEX: - case ARRAY_NORMAL: { - - PoolVector dst = arrays[j]; - PoolVector src = a[j]; - if (j == ARRAY_VERTEX) - vcount = src.size(); - if (dst.size() == 0 || src.size() == 0) { - arrays[j] = Variant(); - continue; - } - dst.append_array(src); - arrays[j] = dst; - } break; - case ARRAY_TANGENT: - case ARRAY_BONES: - case ARRAY_WEIGHTS: { - - PoolVector dst = arrays[j]; - PoolVector src = a[j]; - if (dst.size() == 0 || src.size() == 0) { - arrays[j] = Variant(); - continue; - } - dst.append_array(src); - arrays[j] = dst; - - } break; - case ARRAY_COLOR: { - PoolVector dst = arrays[j]; - PoolVector src = a[j]; - if (dst.size() == 0 || src.size() == 0) { - arrays[j] = Variant(); - continue; - } - dst.append_array(src); - arrays[j] = dst; - - } break; - case ARRAY_TEX_UV: - case ARRAY_TEX_UV2: { - PoolVector dst = arrays[j]; - PoolVector src = a[j]; - if (dst.size() == 0 || src.size() == 0) { - arrays[j] = Variant(); - continue; - } - dst.append_array(src); - arrays[j] = dst; - - } break; - case ARRAY_INDEX: { - PoolVector dst = arrays[j]; - PoolVector src = a[j]; - if (dst.size() == 0 || src.size() == 0) { - arrays[j] = Variant(); - continue; - } - { - int ss = src.size(); - PoolVector::Write w = src.write(); - for (int k = 0; k < ss; k++) { - w[k] += index_accum; - } - } - dst.append_array(src); - arrays[j] = dst; - index_accum += vcount; - - } break; - } - } - } - } - - { - PoolVector::Write ir; - PoolVector indices = arrays[ARRAY_INDEX]; - bool has_indices = false; - PoolVector vertices = arrays[ARRAY_VERTEX]; - int vc = vertices.size(); - ERR_FAIL_COND_V(!vc, Ref()); - PoolVector::Write r = vertices.write(); - - if (indices.size()) { - vc = indices.size(); - ir = indices.write(); - has_indices = true; - } - - Map normal_accum; - - //fill normals with triangle normals - for (int i = 0; i < vc; i += 3) { - - Vector3 t[3]; - - if (has_indices) { - t[0] = r[ir[i + 0]]; - t[1] = r[ir[i + 1]]; - t[2] = r[ir[i + 2]]; - } else { - t[0] = r[i + 0]; - t[1] = r[i + 1]; - t[2] = r[i + 2]; - } - - Vector3 n = Plane(t[0], t[1], t[2]).normal; - - for (int j = 0; j < 3; j++) { - - Map::Element *E = normal_accum.find(t[j]); - if (!E) { - normal_accum[t[j]] = n; - } else { - float d = n.dot(E->get()); - if (d < 1.0) - E->get() += n * (1.0 - d); - //E->get()+=n; - } - } - } - - //normalize - - for (Map::Element *E = normal_accum.front(); E; E = E->next()) { - E->get().normalize(); - } - - //displace normals - int vc2 = vertices.size(); - - for (int i = 0; i < vc2; i++) { - - Vector3 t = r[i]; - - Map::Element *E = normal_accum.find(t); - ERR_CONTINUE(!E); - - t += E->get() * p_margin; - r[i] = t; - } - - r = PoolVector::Write(); - arrays[ARRAY_VERTEX] = vertices; - - if (!has_indices) { - - PoolVector new_indices; - new_indices.resize(vertices.size()); - PoolVector::Write iw = new_indices.write(); - - for (int j = 0; j < vc2; j += 3) { - - iw[j] = j; - iw[j + 1] = j + 2; - iw[j + 2] = j + 1; - } - - iw = PoolVector::Write(); - arrays[ARRAY_INDEX] = new_indices; - - } else { - - for (int j = 0; j < vc; j += 3) { - - SWAP(ir[j + 1], ir[j + 2]); - } - ir = PoolVector::Write(); - arrays[ARRAY_INDEX] = indices; - } - } - - Ref newmesh = memnew(Mesh); - newmesh->add_surface_from_arrays(PRIMITIVE_TRIANGLES, arrays); - return newmesh; -} - -void Mesh::_bind_methods() { - - ClassDB::bind_method(D_METHOD("add_blend_shape", "name"), &Mesh::add_blend_shape); - ClassDB::bind_method(D_METHOD("get_blend_shape_count"), &Mesh::get_blend_shape_count); - ClassDB::bind_method(D_METHOD("get_blend_shape_name", "index"), &Mesh::get_blend_shape_name); - ClassDB::bind_method(D_METHOD("clear_blend_shapes"), &Mesh::clear_blend_shapes); - ClassDB::bind_method(D_METHOD("set_blend_shape_mode", "mode"), &Mesh::set_blend_shape_mode); - ClassDB::bind_method(D_METHOD("get_blend_shape_mode"), &Mesh::get_blend_shape_mode); - - ClassDB::bind_method(D_METHOD("add_surface_from_arrays", "primitive", "arrays", "blend_shapes", "compress_flags"), &Mesh::add_surface_from_arrays, DEFVAL(Array()), DEFVAL(ARRAY_COMPRESS_DEFAULT)); - ClassDB::bind_method(D_METHOD("get_surface_count"), &Mesh::get_surface_count); - ClassDB::bind_method(D_METHOD("surface_remove", "surf_idx"), &Mesh::surface_remove); - ClassDB::bind_method(D_METHOD("surface_get_array_len", "surf_idx"), &Mesh::surface_get_array_len); - ClassDB::bind_method(D_METHOD("surface_get_array_index_len", "surf_idx"), &Mesh::surface_get_array_index_len); - ClassDB::bind_method(D_METHOD("surface_get_format", "surf_idx"), &Mesh::surface_get_format); - ClassDB::bind_method(D_METHOD("surface_get_primitive_type", "surf_idx"), &Mesh::surface_get_primitive_type); - ClassDB::bind_method(D_METHOD("surface_set_material", "surf_idx", "material:Material"), &Mesh::surface_set_material); - ClassDB::bind_method(D_METHOD("surface_get_material:Material", "surf_idx"), &Mesh::surface_get_material); - ClassDB::bind_method(D_METHOD("surface_set_name", "surf_idx", "name"), &Mesh::surface_set_name); - ClassDB::bind_method(D_METHOD("surface_get_name", "surf_idx"), &Mesh::surface_get_name); - ClassDB::bind_method(D_METHOD("create_trimesh_shape:Shape"), &Mesh::create_trimesh_shape); - ClassDB::bind_method(D_METHOD("create_convex_shape:Shape"), &Mesh::create_convex_shape); - ClassDB::bind_method(D_METHOD("create_outline:Mesh", "margin"), &Mesh::create_outline); - ClassDB::bind_method(D_METHOD("center_geometry"), &Mesh::center_geometry); +void ArrayMesh::_bind_methods() { + + ClassDB::bind_method(D_METHOD("add_blend_shape", "name"), &ArrayMesh::add_blend_shape); + ClassDB::bind_method(D_METHOD("get_blend_shape_count"), &ArrayMesh::get_blend_shape_count); + ClassDB::bind_method(D_METHOD("get_blend_shape_name", "index"), &ArrayMesh::get_blend_shape_name); + ClassDB::bind_method(D_METHOD("clear_blend_shapes"), &ArrayMesh::clear_blend_shapes); + ClassDB::bind_method(D_METHOD("set_blend_shape_mode", "mode"), &ArrayMesh::set_blend_shape_mode); + ClassDB::bind_method(D_METHOD("get_blend_shape_mode"), &ArrayMesh::get_blend_shape_mode); + + ClassDB::bind_method(D_METHOD("add_surface_from_arrays", "primitive", "arrays", "blend_shapes", "compress_flags"), &ArrayMesh::add_surface_from_arrays, DEFVAL(Array()), DEFVAL(ARRAY_COMPRESS_DEFAULT)); + ClassDB::bind_method(D_METHOD("get_surface_count"), &ArrayMesh::get_surface_count); + ClassDB::bind_method(D_METHOD("surface_remove", "surf_idx"), &ArrayMesh::surface_remove); + ClassDB::bind_method(D_METHOD("surface_get_array_len", "surf_idx"), &ArrayMesh::surface_get_array_len); + ClassDB::bind_method(D_METHOD("surface_get_array_index_len", "surf_idx"), &ArrayMesh::surface_get_array_index_len); + ClassDB::bind_method(D_METHOD("surface_get_format", "surf_idx"), &ArrayMesh::surface_get_format); + ClassDB::bind_method(D_METHOD("surface_get_primitive_type", "surf_idx"), &ArrayMesh::surface_get_primitive_type); + ClassDB::bind_method(D_METHOD("surface_set_material", "surf_idx", "material:Material"), &ArrayMesh::surface_set_material); + ClassDB::bind_method(D_METHOD("surface_get_material:Material", "surf_idx"), &ArrayMesh::surface_get_material); + ClassDB::bind_method(D_METHOD("surface_set_name", "surf_idx", "name"), &ArrayMesh::surface_set_name); + ClassDB::bind_method(D_METHOD("surface_get_name", "surf_idx"), &ArrayMesh::surface_get_name); + ClassDB::bind_method(D_METHOD("create_trimesh_shape:Shape"), &ArrayMesh::create_trimesh_shape); + ClassDB::bind_method(D_METHOD("create_convex_shape:Shape"), &ArrayMesh::create_convex_shape); + ClassDB::bind_method(D_METHOD("create_outline:ArrayMesh", "margin"), &ArrayMesh::create_outline); + ClassDB::bind_method(D_METHOD("center_geometry"), &ArrayMesh::center_geometry); ClassDB::set_method_flags(get_class_static(), _scs_create("center_geometry"), METHOD_FLAGS_DEFAULT | METHOD_FLAG_EDITOR); - ClassDB::bind_method(D_METHOD("regen_normalmaps"), &Mesh::regen_normalmaps); + ClassDB::bind_method(D_METHOD("regen_normalmaps"), &ArrayMesh::regen_normalmaps); ClassDB::set_method_flags(get_class_static(), _scs_create("regen_normalmaps"), METHOD_FLAGS_DEFAULT | METHOD_FLAG_EDITOR); - ClassDB::bind_method(D_METHOD("get_faces"), &Mesh::get_faces); - ClassDB::bind_method(D_METHOD("generate_triangle_mesh:TriangleMesh"), &Mesh::generate_triangle_mesh); + ClassDB::bind_method(D_METHOD("get_faces"), &ArrayMesh::get_faces); + ClassDB::bind_method(D_METHOD("generate_triangle_mesh:TriangleMesh"), &ArrayMesh::generate_triangle_mesh); - ClassDB::bind_method(D_METHOD("set_custom_aabb", "aabb"), &Mesh::set_custom_aabb); - ClassDB::bind_method(D_METHOD("get_custom_aabb"), &Mesh::get_custom_aabb); + ClassDB::bind_method(D_METHOD("set_custom_aabb", "aabb"), &ArrayMesh::set_custom_aabb); + ClassDB::bind_method(D_METHOD("get_custom_aabb"), &ArrayMesh::get_custom_aabb); BIND_CONSTANT(NO_INDEX_ARRAY); BIND_CONSTANT(ARRAY_WEIGHTS_SIZE); @@ -1027,19 +1036,19 @@ void Mesh::_bind_methods() { BIND_CONSTANT(PRIMITIVE_TRIANGLE_FAN); } -Mesh::Mesh() { +ArrayMesh::ArrayMesh() { mesh = VisualServer::get_singleton()->mesh_create(); blend_shape_mode = BLEND_SHAPE_MODE_RELATIVE; } -Mesh::~Mesh() { +ArrayMesh::~ArrayMesh() { VisualServer::get_singleton()->free(mesh); } //////////////////////// - +#if 0 void QuadMesh::_bind_methods() { ClassDB::bind_method(D_METHOD("set_material", "material:Material"), &QuadMesh::set_material); @@ -1105,3 +1114,4 @@ QuadMesh::QuadMesh() { add_surface_from_arrays(PRIMITIVE_TRIANGLE_FAN, arr); } +#endif diff --git a/scene/resources/mesh.h b/scene/resources/mesh.h index e441b4924a3..7804a84f811 100644 --- a/scene/resources/mesh.h +++ b/scene/resources/mesh.h @@ -38,10 +38,13 @@ /** @author Juan Linietsky */ -class Mesh : public Resource { +class Mesh : public Resource { GDCLASS(Mesh, Resource); - RES_BASE_EXTENSION("msh"); + + mutable Ref triangle_mesh; //cached +protected: + void _clear_triangle_mesh(); public: enum { @@ -111,6 +114,34 @@ public: BLEND_SHAPE_MODE_RELATIVE = VS::BLEND_SHAPE_MODE_RELATIVE, }; + virtual int get_surface_count() const = 0; + virtual int surface_get_array_len(int p_idx) const = 0; + virtual int surface_get_array_index_len(int p_idx) const = 0; + virtual Array surface_get_arrays(int p_surface) const = 0; + virtual uint32_t surface_get_format(int p_idx) const = 0; + virtual PrimitiveType surface_get_primitive_type(int p_idx) const = 0; + virtual Ref surface_get_material(int p_idx) const = 0; + virtual int get_blend_shape_count() const = 0; + virtual StringName get_blend_shape_name(int p_index) const = 0; + + PoolVector get_faces() const; + Ref generate_triangle_mesh() const; + + Ref create_trimesh_shape() const; + Ref create_convex_shape() const; + + Ref create_outline(float p_margin) const; + + virtual Rect3 get_aabb() const = 0; + + Mesh(); +}; + +class ArrayMesh : public Mesh { + + GDCLASS(ArrayMesh, Mesh); + RES_BASE_EXTENSION("msh"); + private: struct Surface { String name; @@ -124,8 +155,6 @@ private: Vector blend_shapes; Rect3 custom_aabb; - mutable Ref triangle_mesh; - void _recompute_aabb(); protected: @@ -177,21 +206,15 @@ public: Rect3 get_aabb() const; virtual RID get_rid() const; - Ref create_trimesh_shape() const; - Ref create_convex_shape() const; - - Ref create_outline(float p_margin) const; - void center_geometry(); void regen_normalmaps(); - PoolVector get_faces() const; - Ref generate_triangle_mesh() const; - Mesh(); + ArrayMesh(); - ~Mesh(); + ~ArrayMesh(); }; +#if 0 class QuadMesh : public Mesh { GDCLASS(QuadMesh, Mesh) @@ -206,6 +229,8 @@ public: QuadMesh(); }; +#endif + VARIANT_ENUM_CAST(Mesh::ArrayType); VARIANT_ENUM_CAST(Mesh::PrimitiveType); VARIANT_ENUM_CAST(Mesh::BlendShapeMode); diff --git a/scene/resources/mesh_data_tool.cpp b/scene/resources/mesh_data_tool.cpp index b6b47bf4438..dc3713fb57b 100644 --- a/scene/resources/mesh_data_tool.cpp +++ b/scene/resources/mesh_data_tool.cpp @@ -38,7 +38,7 @@ void MeshDataTool::clear() { format = 0; } -Error MeshDataTool::create_from_surface(const Ref &p_mesh, int p_surface) { +Error MeshDataTool::create_from_surface(const Ref &p_mesh, int p_surface) { ERR_FAIL_COND_V(p_mesh.is_null(), ERR_INVALID_PARAMETER); @@ -179,7 +179,7 @@ Error MeshDataTool::create_from_surface(const Ref &p_mesh, int p_surface) return OK; } -Error MeshDataTool::commit_to_surface(const Ref &p_mesh) { +Error MeshDataTool::commit_to_surface(const Ref &p_mesh) { ERR_FAIL_COND_V(p_mesh.is_null(), ERR_INVALID_PARAMETER); Array arr; @@ -309,7 +309,7 @@ Error MeshDataTool::commit_to_surface(const Ref &p_mesh) { if (w.size()) arr[Mesh::ARRAY_WEIGHTS] = w; - Ref ncmesh = p_mesh; + Ref ncmesh = p_mesh; int sc = ncmesh->get_surface_count(); ncmesh->add_surface_from_arrays(Mesh::PRIMITIVE_TRIANGLES, arr); ncmesh->surface_set_material(sc, material); diff --git a/scene/resources/mesh_data_tool.h b/scene/resources/mesh_data_tool.h index f6797d3e5ec..ad771edbd12 100644 --- a/scene/resources/mesh_data_tool.h +++ b/scene/resources/mesh_data_tool.h @@ -78,8 +78,8 @@ protected: public: void clear(); - Error create_from_surface(const Ref &p_mesh, int p_surface); - Error commit_to_surface(const Ref &p_mesh); + Error create_from_surface(const Ref &p_mesh, int p_surface); + Error commit_to_surface(const Ref &p_mesh); int get_format() const; diff --git a/scene/resources/shape.cpp b/scene/resources/shape.cpp index b449932b17d..77f2096d9b9 100644 --- a/scene/resources/shape.cpp +++ b/scene/resources/shape.cpp @@ -49,14 +49,14 @@ void Shape::add_vertices_to_array(PoolVector &array, const Transform &p } } -Ref Shape::get_debug_mesh() { +Ref Shape::get_debug_mesh() { if (debug_mesh_cache.is_valid()) return debug_mesh_cache; Vector lines = _gen_debug_mesh_lines(); - debug_mesh_cache = Ref(memnew(Mesh)); + debug_mesh_cache = Ref(memnew(ArrayMesh)); if (!lines.empty()) { //make mesh diff --git a/scene/resources/shape.h b/scene/resources/shape.h index 01b8db650e1..ea3ba9ab0a6 100644 --- a/scene/resources/shape.h +++ b/scene/resources/shape.h @@ -31,7 +31,7 @@ #define SHAPE_H #include "resource.h" -class Mesh; +class ArrayMesh; class Shape : public Resource { @@ -40,7 +40,7 @@ class Shape : public Resource { RES_BASE_EXTENSION("shp"); RID shape; - Ref debug_mesh_cache; + Ref debug_mesh_cache; protected: _FORCE_INLINE_ RID get_shape() const { return shape; } @@ -50,7 +50,7 @@ protected: public: virtual RID get_rid() const { return shape; } - Ref get_debug_mesh(); + Ref get_debug_mesh(); void add_vertices_to_array(PoolVector &array, const Transform &p_xform); diff --git a/scene/resources/surface_tool.cpp b/scene/resources/surface_tool.cpp index 4c36d79a7a5..60fb97c792f 100644 --- a/scene/resources/surface_tool.cpp +++ b/scene/resources/surface_tool.cpp @@ -224,13 +224,13 @@ void SurfaceTool::add_index(int p_index) { index_array.push_back(p_index); } -Ref SurfaceTool::commit(const Ref &p_existing) { +Ref SurfaceTool::commit(const Ref &p_existing) { - Ref mesh; + Ref mesh; if (p_existing.is_valid()) mesh = p_existing; else - mesh = Ref(memnew(Mesh)); + mesh.instance(); int varr_len = vertex_array.size(); diff --git a/scene/resources/surface_tool.h b/scene/resources/surface_tool.h index b143086e11e..753c3626b87 100644 --- a/scene/resources/surface_tool.h +++ b/scene/resources/surface_tool.h @@ -125,7 +125,7 @@ public: void create_from(const Ref &p_existing, int p_surface); void append_from(const Ref &p_existing, int p_surface, const Transform &p_xform); - Ref commit(const Ref &p_existing = Ref()); + Ref commit(const Ref &p_existing = Ref()); SurfaceTool(); }; diff --git a/servers/visual/shader_types.cpp b/servers/visual/shader_types.cpp index 44ec13af453..e0201420fea 100644 --- a/servers/visual/shader_types.cpp +++ b/servers/visual/shader_types.cpp @@ -105,6 +105,7 @@ ShaderTypes::ShaderTypes() { shader_modes[VS::SHADER_SPATIAL].functions["fragment"]["SPECIAL"] = ShaderLanguage::TYPE_FLOAT; shader_modes[VS::SHADER_SPATIAL].functions["fragment"]["DISCARD"] = ShaderLanguage::TYPE_BOOL; shader_modes[VS::SHADER_SPATIAL].functions["fragment"]["SCREEN_TEXTURE"] = ShaderLanguage::TYPE_SAMPLER2D; + shader_modes[VS::SHADER_SPATIAL].functions["fragment"]["DEPTH_TEXTURE"] = ShaderLanguage::TYPE_SAMPLER2D; shader_modes[VS::SHADER_SPATIAL].functions["fragment"]["SCREEN_UV"] = ShaderLanguage::TYPE_VEC2; shader_modes[VS::SHADER_SPATIAL].functions["fragment"]["POINT_COORD"] = ShaderLanguage::TYPE_VEC2; shader_modes[VS::SHADER_SPATIAL].functions["fragment"]["SIDE"] = ShaderLanguage::TYPE_FLOAT;