summaryrefslogtreecommitdiff
path: root/servers/visual
diff options
context:
space:
mode:
authorJuan Linietsky <reduzio@gmail.com>2016-11-24 20:46:55 -0300
committerJuan Linietsky <reduzio@gmail.com>2016-11-24 20:46:55 -0300
commita732708b9dad4ebc118a0ce854f950c6becb984c (patch)
tree4e740d30a2449e065462bc408e23536d5270ca0e /servers/visual
parent69c30709ec6908e0960707501cc7fea58eb64f01 (diff)
Blend shapes using transform feedback (GPU)
Diffstat (limited to 'servers/visual')
-rw-r--r--servers/visual/rasterizer.h3
-rw-r--r--servers/visual/visual_server_scene.cpp27
2 files changed, 26 insertions, 4 deletions
diff --git a/servers/visual/rasterizer.h b/servers/visual/rasterizer.h
index 5f536b8fd4..21cf391af5 100644
--- a/servers/visual/rasterizer.h
+++ b/servers/visual/rasterizer.h
@@ -380,7 +380,8 @@ public:
virtual void portal_set_disable_distance(RID p_portal, float p_distance)=0;
virtual void portal_set_disabled_color(RID p_portal, const Color& p_color)=0;
-
+ virtual void instance_add_skeleton(RID p_skeleton,RasterizerScene::InstanceBase *p_instance)=0;
+ virtual void instance_remove_skeleton(RID p_skeleton,RasterizerScene::InstanceBase *p_instance)=0;
virtual void instance_add_dependency(RID p_base,RasterizerScene::InstanceBase *p_instance)=0;
virtual void instance_remove_dependency(RID p_base,RasterizerScene::InstanceBase *p_instance)=0;
diff --git a/servers/visual/visual_server_scene.cpp b/servers/visual/visual_server_scene.cpp
index 2439eacd75..0f7dabcc12 100644
--- a/servers/visual/visual_server_scene.cpp
+++ b/servers/visual/visual_server_scene.cpp
@@ -738,13 +738,25 @@ void VisualServerScene::instance_attach_object_instance_ID(RID p_instance,Object
}
void VisualServerScene::instance_set_morph_target_weight(RID p_instance,int p_shape, float p_weight){
+ Instance *instance = instance_owner.get( p_instance );
+ ERR_FAIL_COND( !instance );
+
+ if (instance->update_item.in_list()) {
+ _update_dirty_instance(instance);
+ }
+
+ ERR_FAIL_INDEX(p_shape,instance->morph_values.size());
+ instance->morph_values[p_shape]=p_weight;
}
+
void VisualServerScene::instance_set_surface_material(RID p_instance,int p_surface, RID p_material){
Instance *instance = instance_owner.get( p_instance );
ERR_FAIL_COND( !instance );
- _update_dirty_instance(instance);
+ if (instance->update_item.in_list()) {
+ _update_dirty_instance(instance);
+ }
ERR_FAIL_INDEX(p_surface,instance->materials.size());
@@ -770,13 +782,13 @@ void VisualServerScene::instance_attach_skeleton(RID p_instance,RID p_skeleton){
return;
if (instance->skeleton.is_valid()) {
- VSG::storage->instance_remove_dependency(p_skeleton,instance);
+ VSG::storage->instance_remove_skeleton(p_skeleton,instance);
}
instance->skeleton=p_skeleton;
if (instance->skeleton.is_valid()) {
- VSG::storage->instance_add_dependency(p_skeleton,instance);
+ VSG::storage->instance_add_skeleton(p_skeleton,instance);
}
_instance_queue_update(instance,true);
@@ -2227,6 +2239,7 @@ void VisualServerScene::_update_dirty_instance(Instance *p_instance) {
if (p_instance->update_aabb)
_update_instance_aabb(p_instance);
+
if (p_instance->update_materials) {
if (p_instance->base_type==VS::INSTANCE_MESH) {
@@ -2239,6 +2252,14 @@ void VisualServerScene::_update_dirty_instance(Instance *p_instance) {
}
}
p_instance->materials.resize(new_mat_count);
+
+ int new_morph_count = VSG::storage->mesh_get_morph_target_count(p_instance->base);
+ if (new_morph_count!=p_instance->morph_values.size()) {
+ p_instance->morph_values.resize(new_morph_count);
+ for(int i=0;i<new_morph_count;i++) {
+ p_instance->morph_values[i]=0;
+ }
+ }
}
if ((1<<p_instance->base_type)&VS::INSTANCE_GEOMETRY_MASK) {