summaryrefslogtreecommitdiff
path: root/servers
diff options
context:
space:
mode:
Diffstat (limited to 'servers')
-rw-r--r--servers/physics/area_pair_sw.cpp10
-rw-r--r--servers/physics/body_pair_sw.cpp2
-rw-r--r--servers/physics/collision_object_sw.cpp1
-rw-r--r--servers/physics/collision_object_sw.h8
-rw-r--r--servers/physics/joints/hinge_joint_sw.cpp1
-rw-r--r--servers/physics/physics_server_sw.cpp77
-rw-r--r--servers/physics/physics_server_sw.h6
-rw-r--r--servers/physics/space_sw.cpp4
-rw-r--r--servers/physics/space_sw.h16
-rw-r--r--servers/physics/step_sw.cpp38
-rw-r--r--servers/physics_2d/body_2d_sw.cpp17
-rw-r--r--servers/physics_2d/body_2d_sw.h12
-rw-r--r--servers/physics_2d/physics_2d_server_sw.cpp54
-rw-r--r--servers/physics_2d/physics_2d_server_sw.h3
-rw-r--r--servers/physics_2d/physics_2d_server_wrap_mt.h1
-rw-r--r--servers/physics_2d/space_2d_sw.cpp5
-rw-r--r--servers/physics_2d/space_2d_sw.h17
-rw-r--r--servers/physics_2d/step_2d_sw.cpp40
-rw-r--r--servers/physics_2d_server.cpp4
-rw-r--r--servers/physics_2d_server.h9
-rw-r--r--servers/physics_server.cpp8
-rw-r--r--servers/physics_server.h6
-rw-r--r--servers/server_wrap_mt_common.h61
-rw-r--r--servers/visual/rasterizer.h8
-rw-r--r--servers/visual/rasterizer_dummy.cpp3
-rw-r--r--servers/visual/rasterizer_dummy.h4
-rw-r--r--servers/visual/visual_server_raster.cpp46
-rw-r--r--servers/visual/visual_server_raster.h14
-rw-r--r--servers/visual/visual_server_wrap_mt.h6
-rw-r--r--servers/visual_server.cpp10
-rw-r--r--servers/visual_server.h8
31 files changed, 463 insertions, 36 deletions
diff --git a/servers/physics/area_pair_sw.cpp b/servers/physics/area_pair_sw.cpp
index c6bf6114a0..24f3b75ca5 100644
--- a/servers/physics/area_pair_sw.cpp
+++ b/servers/physics/area_pair_sw.cpp
@@ -32,6 +32,11 @@
bool AreaPairSW::setup(float p_step) {
+ if (!area->test_collision_mask(body)) {
+ colliding = false;
+ return false;
+ }
+
bool result = CollisionSolverSW::solve_static(body->get_shape(body_shape),body->get_transform() * body->get_shape_transform(body_shape),area->get_shape(area_shape),area->get_transform() * area->get_shape_transform(area_shape),NULL,this);
if (result!=colliding) {
@@ -100,6 +105,11 @@ AreaPairSW::~AreaPairSW() {
bool Area2PairSW::setup(float p_step) {
+ if (!area_a->test_collision_mask(area_b)) {
+ colliding = false;
+ return false;
+ }
+
// bool result = area_a->test_collision_mask(area_b) && CollisionSolverSW::solve(area_a->get_shape(shape_a),area_a->get_transform() * area_a->get_shape_transform(shape_a),Vector2(),area_b->get_shape(shape_b),area_b->get_transform() * area_b->get_shape_transform(shape_b),Vector2(),NULL,this);
bool result = CollisionSolverSW::solve_static(area_a->get_shape(shape_a),area_a->get_transform() * area_a->get_shape_transform(shape_a),area_b->get_shape(shape_b),area_b->get_transform() * area_b->get_shape_transform(shape_b),NULL,this);
diff --git a/servers/physics/body_pair_sw.cpp b/servers/physics/body_pair_sw.cpp
index a971cdaad8..40e906c36c 100644
--- a/servers/physics/body_pair_sw.cpp
+++ b/servers/physics/body_pair_sw.cpp
@@ -221,7 +221,7 @@ bool BodyPairSW::_test_ccd(float p_step,BodySW *p_A, int p_shape_A,const Transfo
bool BodyPairSW::setup(float p_step) {
//cannot collide
- if ((A->get_layer_mask()&B->get_layer_mask())==0 || A->has_exception(B->get_self()) || B->has_exception(A->get_self()) || (A->get_mode()<=PhysicsServer::BODY_MODE_KINEMATIC && B->get_mode()<=PhysicsServer::BODY_MODE_KINEMATIC && A->get_max_contacts_reported()==0 && B->get_max_contacts_reported()==0)) {
+ if (!A->test_collision_mask(B) || A->has_exception(B->get_self()) || B->has_exception(A->get_self()) || (A->get_mode()<=PhysicsServer::BODY_MODE_KINEMATIC && B->get_mode()<=PhysicsServer::BODY_MODE_KINEMATIC && A->get_max_contacts_reported()==0 && B->get_max_contacts_reported()==0)) {
collided=false;
return false;
}
diff --git a/servers/physics/collision_object_sw.cpp b/servers/physics/collision_object_sw.cpp
index 55c8c1b955..f2864ee95e 100644
--- a/servers/physics/collision_object_sw.cpp
+++ b/servers/physics/collision_object_sw.cpp
@@ -217,5 +217,6 @@ CollisionObjectSW::CollisionObjectSW(Type p_type) {
space=NULL;
instance_id=0;
layer_mask=1;
+ collision_mask=1;
ray_pickable=true;
}
diff --git a/servers/physics/collision_object_sw.h b/servers/physics/collision_object_sw.h
index 592c84e667..bc71c2709b 100644
--- a/servers/physics/collision_object_sw.h
+++ b/servers/physics/collision_object_sw.h
@@ -53,6 +53,7 @@ private:
RID self;
ObjectID instance_id;
uint32_t layer_mask;
+ uint32_t collision_mask;
struct Shape {
@@ -136,6 +137,13 @@ public:
_FORCE_INLINE_ void set_layer_mask(uint32_t p_mask) { layer_mask=p_mask; }
_FORCE_INLINE_ uint32_t get_layer_mask() const { return layer_mask; }
+ _FORCE_INLINE_ void set_collision_mask(uint32_t p_mask) { collision_mask=p_mask; }
+ _FORCE_INLINE_ uint32_t get_collision_mask() const { return collision_mask; }
+
+ _FORCE_INLINE_ bool test_collision_mask(CollisionObjectSW* p_other) const {
+ return layer_mask&p_other->collision_mask || p_other->layer_mask&collision_mask;
+ }
+
void remove_shape(ShapeSW *p_shape);
void remove_shape(int p_index);
diff --git a/servers/physics/joints/hinge_joint_sw.cpp b/servers/physics/joints/hinge_joint_sw.cpp
index feaf00290d..37b73f64c7 100644
--- a/servers/physics/joints/hinge_joint_sw.cpp
+++ b/servers/physics/joints/hinge_joint_sw.cpp
@@ -420,7 +420,6 @@ float HingeJointSW::get_param(PhysicsServer::HingeJointParam p_param) const{
void HingeJointSW::set_flag(PhysicsServer::HingeJointFlag p_flag, bool p_value){
- print_line(p_flag+": "+itos(p_value));
switch (p_flag) {
case PhysicsServer::HINGE_JOINT_FLAG_USE_LIMIT: m_useLimit=p_value; break;
case PhysicsServer::HINGE_JOINT_FLAG_ENABLE_MOTOR: m_enableAngularMotor=p_value; break;
diff --git a/servers/physics/physics_server_sw.cpp b/servers/physics/physics_server_sw.cpp
index 5eb14d80dc..6c098a6df2 100644
--- a/servers/physics/physics_server_sw.cpp
+++ b/servers/physics/physics_server_sw.cpp
@@ -34,7 +34,8 @@
#include "joints/slider_joint_sw.h"
#include "joints/cone_twist_joint_sw.h"
#include "joints/generic_6dof_joint_sw.h"
-
+#include "script_language.h"
+#include "os/os.h"
RID PhysicsServerSW::shape_create(ShapeType p_shape) {
@@ -418,6 +419,22 @@ Transform PhysicsServerSW::area_get_transform(RID p_area) const {
return area->get_transform();
};
+void PhysicsServerSW::area_set_layer_mask(RID p_area,uint32_t p_mask) {
+
+ AreaSW *area = area_owner.get(p_area);
+ ERR_FAIL_COND(!area);
+
+ area->set_layer_mask(p_mask);
+}
+
+void PhysicsServerSW::area_set_collision_mask(RID p_area,uint32_t p_mask) {
+
+ AreaSW *area = area_owner.get(p_area);
+ ERR_FAIL_COND(!area);
+
+ area->set_collision_mask(p_mask);
+}
+
void PhysicsServerSW::area_set_monitorable(RID p_area,bool p_monitorable) {
AreaSW *area = area_owner.get(p_area);
@@ -657,6 +674,25 @@ uint32_t PhysicsServerSW::body_get_layer_mask(RID p_body, uint32_t p_mask) const
}
+void PhysicsServerSW::body_set_collision_mask(RID p_body, uint32_t p_mask) {
+
+ BodySW *body = body_owner.get(p_body);
+ ERR_FAIL_COND(!body);
+
+ body->set_collision_mask(p_mask);
+ body->wakeup();
+
+}
+
+uint32_t PhysicsServerSW::body_get_collision_mask(RID p_body, uint32_t p_mask) const{
+
+ const BodySW *body = body_owner.get(p_body);
+ ERR_FAIL_COND_V(!body,0);
+
+ return body->get_collision_mask();
+
+}
+
void PhysicsServerSW::body_attach_object_instance_ID(RID p_body,uint32_t p_ID) {
@@ -1474,12 +1510,51 @@ void PhysicsServerSW::flush_queries() {
return;
doing_sync=true;
+
+ uint64_t time_beg = OS::get_singleton()->get_ticks_usec();
+
for( Set<const SpaceSW*>::Element *E=active_spaces.front();E;E=E->next()) {
SpaceSW *space=(SpaceSW *)E->get();
space->call_queries();
}
+
+ if (ScriptDebugger::get_singleton() && ScriptDebugger::get_singleton()->is_profiling()) {
+
+ uint64_t total_time[SpaceSW::ELAPSED_TIME_MAX];
+ static const char* time_name[SpaceSW::ELAPSED_TIME_MAX]={
+ "integrate_forces",
+ "generate_islands",
+ "setup_constraints",
+ "solve_constraints",
+ "integrate_velocities"
+ };
+
+ for(int i=0;i<SpaceSW::ELAPSED_TIME_MAX;i++) {
+ total_time[i]=0;
+ }
+
+ for( Set<const SpaceSW*>::Element *E=active_spaces.front();E;E=E->next()) {
+
+ for(int i=0;i<SpaceSW::ELAPSED_TIME_MAX;i++) {
+ total_time[i]+=E->get()->get_elapsed_time(SpaceSW::ElapsedTime(i));
+ }
+
+ }
+
+ Array values;
+ values.resize(SpaceSW::ELAPSED_TIME_MAX*2);
+ for(int i=0;i<SpaceSW::ELAPSED_TIME_MAX;i++) {
+ values[i*2+0]=time_name[i];
+ values[i*2+1]=USEC_TO_SEC(total_time[i]);
+ }
+ values.push_back("flush_queries");
+ values.push_back(USEC_TO_SEC(OS::get_singleton()->get_ticks_usec()-time_beg));
+
+ ScriptDebugger::get_singleton()->add_profiling_frame_data("physics",values);
+
+ }
};
diff --git a/servers/physics/physics_server_sw.h b/servers/physics/physics_server_sw.h
index 2aadac2216..59eeeb42a7 100644
--- a/servers/physics/physics_server_sw.h
+++ b/servers/physics/physics_server_sw.h
@@ -131,6 +131,9 @@ public:
virtual void area_set_ray_pickable(RID p_area,bool p_enable);
virtual bool area_is_ray_pickable(RID p_area) const;
+ virtual void area_set_collision_mask(RID p_area,uint32_t p_mask);
+ virtual void area_set_layer_mask(RID p_area,uint32_t p_mask);
+
virtual void area_set_monitorable(RID p_area,bool p_monitorable);
virtual void area_set_monitor_callback(RID p_area,Object *p_receiver,const StringName& p_method);
@@ -171,6 +174,9 @@ public:
virtual void body_set_layer_mask(RID p_body, uint32_t p_mask);
virtual uint32_t body_get_layer_mask(RID p_body, uint32_t p_mask) const;
+ virtual void body_set_collision_mask(RID p_body, uint32_t p_mask);
+ virtual uint32_t body_get_collision_mask(RID p_body, uint32_t p_mask) const;
+
virtual void body_set_user_flags(RID p_body, uint32_t p_flags);
virtual uint32_t body_get_user_flags(RID p_body, uint32_t p_flags) const;
diff --git a/servers/physics/space_sw.cpp b/servers/physics/space_sw.cpp
index 4cf7729b09..1e6f42aa02 100644
--- a/servers/physics/space_sw.cpp
+++ b/servers/physics/space_sw.cpp
@@ -736,6 +736,10 @@ SpaceSW::SpaceSW() {
direct_access = memnew( PhysicsDirectSpaceStateSW );
direct_access->space=this;
+
+ for(int i=0;i<ELAPSED_TIME_MAX;i++)
+ elapsed_time[i]=0;
+
}
SpaceSW::~SpaceSW() {
diff --git a/servers/physics/space_sw.h b/servers/physics/space_sw.h
index 6300c206d8..3fdef7e62b 100644
--- a/servers/physics/space_sw.h
+++ b/servers/physics/space_sw.h
@@ -59,6 +59,20 @@ public:
class SpaceSW {
+public:
+
+ enum ElapsedTime {
+ ELAPSED_TIME_INTEGRATE_FORCES,
+ ELAPSED_TIME_GENERATE_ISLANDS,
+ ELAPSED_TIME_SETUP_CONSTRAINTS,
+ ELAPSED_TIME_SOLVE_CONSTRAINTS,
+ ELAPSED_TIME_INTEGRATE_VELOCITIES,
+ ELAPSED_TIME_MAX
+
+ };
+private:
+
+ uint64_t elapsed_time[ELAPSED_TIME_MAX];
PhysicsDirectSpaceStateSW *direct_access;
RID self;
@@ -178,6 +192,8 @@ public:
void set_static_global_body(RID p_body) { static_global_body=p_body; }
RID get_static_global_body() { return static_global_body; }
+ void set_elapsed_time(ElapsedTime p_time,uint64_t p_msec) { elapsed_time[p_time]=p_msec; }
+ uint64_t get_elapsed_time(ElapsedTime p_time) const { return elapsed_time[p_time]; }
SpaceSW();
~SpaceSW();
diff --git a/servers/physics/step_sw.cpp b/servers/physics/step_sw.cpp
index f10dadf81a..5b7ebce817 100644
--- a/servers/physics/step_sw.cpp
+++ b/servers/physics/step_sw.cpp
@@ -29,6 +29,8 @@
#include "step_sw.h"
#include "joints_sw.h"
+#include "os/os.h"
+
void StepSW::_populate_island(BodySW* p_body,BodySW** p_island,ConstraintSW **p_constraint_island) {
p_body->set_island_step(_step);
@@ -152,6 +154,10 @@ void StepSW::step(SpaceSW* p_space,float p_delta,int p_iterations) {
const SelfList<BodySW>::List * body_list = &p_space->get_active_body_list();
/* INTEGRATE FORCES */
+
+ uint64_t profile_begtime = OS::get_singleton()->get_ticks_usec();
+ uint64_t profile_endtime=0;
+
int active_count=0;
const SelfList<BodySW>*b = body_list->first();
@@ -165,6 +171,12 @@ void StepSW::step(SpaceSW* p_space,float p_delta,int p_iterations) {
p_space->set_active_objects(active_count);
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(SpaceSW::ELAPSED_TIME_INTEGRATE_FORCES,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
/* GENERATE CONSTRAINT ISLANDS */
BodySW *island_list=NULL;
@@ -214,6 +226,13 @@ void StepSW::step(SpaceSW* p_space,float p_delta,int p_iterations) {
p_space->area_remove_from_moved_list((SelfList<AreaSW>*)aml.first()); //faster to remove here
}
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(SpaceSW::ELAPSED_TIME_GENERATE_ISLANDS,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
+
// print_line("island count: "+itos(island_count)+" active count: "+itos(active_count));
/* SETUP CONSTRAINT ISLANDS */
@@ -226,6 +245,12 @@ void StepSW::step(SpaceSW* p_space,float p_delta,int p_iterations) {
}
}
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(SpaceSW::ELAPSED_TIME_SETUP_CONSTRAINTS,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
/* SOLVE CONSTRAINT ISLANDS */
{
@@ -237,6 +262,13 @@ void StepSW::step(SpaceSW* p_space,float p_delta,int p_iterations) {
}
}
+
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(SpaceSW::ELAPSED_TIME_SOLVE_CONSTRAINTS,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
/* INTEGRATE VELOCITIES */
b = body_list->first();
@@ -257,6 +289,12 @@ void StepSW::step(SpaceSW* p_space,float p_delta,int p_iterations) {
}
}
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(SpaceSW::ELAPSED_TIME_INTEGRATE_VELOCITIES,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
p_space->update();
p_space->unlock();
_step++;
diff --git a/servers/physics_2d/body_2d_sw.cpp b/servers/physics_2d/body_2d_sw.cpp
index ab1c7ef66f..12ac0bd1ca 100644
--- a/servers/physics_2d/body_2d_sw.cpp
+++ b/servers/physics_2d/body_2d_sw.cpp
@@ -33,7 +33,7 @@
void Body2DSW::_update_inertia() {
- if (get_space() && !inertia_update_list.in_list())
+ if (!user_inertia && get_space() && !inertia_update_list.in_list())
get_space()->body_add_to_inertia_update_list(&inertia_update_list);
}
@@ -48,6 +48,8 @@ void Body2DSW::update_inertias() {
case Physics2DServer::BODY_MODE_RIGID: {
+ if(user_inertia) break;
+
//update tensor for allshapes, not the best way but should be somehow OK. (inspired from bullet)
float total_area=0;
@@ -157,6 +159,15 @@ void Body2DSW::set_param(Physics2DServer::BodyParameter p_param, float p_value)
_update_inertia();
} break;
+ case Physics2DServer::BODY_PARAM_INERTIA: {
+ if(p_value<=0) {
+ user_inertia = false;
+ _update_inertia();
+ } else {
+ user_inertia = true;
+ _inv_inertia = 1.0 / p_value;
+ }
+ } break;
case Physics2DServer::BODY_PARAM_GRAVITY_SCALE: {
gravity_scale=p_value;
} break;
@@ -186,6 +197,9 @@ float Body2DSW::get_param(Physics2DServer::BodyParameter p_param) const {
case Physics2DServer::BODY_PARAM_MASS: {
return mass;
} break;
+ case Physics2DServer::BODY_PARAM_INERTIA: {
+ return _inv_inertia==0 ? 0 : 1.0 / _inv_inertia;
+ } break;
case Physics2DServer::BODY_PARAM_GRAVITY_SCALE: {
return gravity_scale;
} break;
@@ -665,6 +679,7 @@ Body2DSW::Body2DSW() : CollisionObject2DSW(TYPE_BODY), active_list(this), inerti
angular_velocity=0;
biased_angular_velocity=0;
mass=1;
+ user_inertia=false;
_inv_inertia=0;
_inv_mass=1;
bounce=0;
diff --git a/servers/physics_2d/body_2d_sw.h b/servers/physics_2d/body_2d_sw.h
index b7f3ab01db..ed98017629 100644
--- a/servers/physics_2d/body_2d_sw.h
+++ b/servers/physics_2d/body_2d_sw.h
@@ -57,6 +57,7 @@ class Body2DSW : public CollisionObject2DSW {
real_t _inv_mass;
real_t _inv_inertia;
+ bool user_inertia;
Vector2 gravity;
real_t area_linear_damp;
@@ -204,10 +205,10 @@ public:
_FORCE_INLINE_ real_t get_biased_angular_velocity() const { return biased_angular_velocity; }
- _FORCE_INLINE_ void apply_impulse(const Vector2& p_pos, const Vector2& p_j) {
+ _FORCE_INLINE_ void apply_impulse(const Vector2& p_offset, const Vector2& p_impulse) {
- linear_velocity += p_j * _inv_mass;
- angular_velocity += _inv_inertia * p_pos.cross(p_j);
+ linear_velocity += p_impulse * _inv_mass;
+ angular_velocity += _inv_inertia * p_offset.cross(p_impulse);
}
_FORCE_INLINE_ void apply_bias_impulse(const Vector2& p_pos, const Vector2& p_j) {
@@ -243,6 +244,11 @@ public:
void set_applied_torque(real_t p_torque) { applied_torque=p_torque; }
real_t get_applied_torque() const { return applied_torque; }
+ _FORCE_INLINE_ void add_force(const Vector2& p_force, const Vector2& p_offset) {
+
+ applied_force += p_force;
+ applied_torque += p_offset.cross(p_force);
+ }
_FORCE_INLINE_ void set_continuous_collision_detection_mode(Physics2DServer::CCDMode p_mode) { continuous_cd_mode=p_mode; }
_FORCE_INLINE_ Physics2DServer::CCDMode get_continuous_collision_detection_mode() const { return continuous_cd_mode; }
diff --git a/servers/physics_2d/physics_2d_server_sw.cpp b/servers/physics_2d/physics_2d_server_sw.cpp
index c571331498..54cd929c2f 100644
--- a/servers/physics_2d/physics_2d_server_sw.cpp
+++ b/servers/physics_2d/physics_2d_server_sw.cpp
@@ -31,6 +31,9 @@
#include "broad_phase_2d_hash_grid.h"
#include "collision_solver_2d_sw.h"
#include "globals.h"
+#include "script_language.h"
+#include "os/os.h"
+
RID Physics2DServerSW::shape_create(ShapeType p_shape) {
Shape2DSW *shape=NULL;
@@ -860,6 +863,15 @@ void Physics2DServerSW::body_apply_impulse(RID p_body, const Vector2& p_pos, con
body->wakeup();
};
+void Physics2DServerSW::body_add_force(RID p_body, const Vector2& p_offset, const Vector2& p_force) {
+
+ Body2DSW *body = body_owner.get(p_body);
+ ERR_FAIL_COND(!body);
+
+ body->add_force(p_force,p_offset);
+ body->wakeup();
+};
+
void Physics2DServerSW::body_set_axis_velocity(RID p_body, const Vector2& p_axis_velocity) {
Body2DSW *body = body_owner.get(p_body);
@@ -1267,6 +1279,8 @@ void Physics2DServerSW::step(float p_step) {
active_objects+=E->get()->get_active_objects();
collision_pairs+=E->get()->get_collision_pairs();
}
+
+
};
void Physics2DServerSW::sync() {
@@ -1279,6 +1293,7 @@ void Physics2DServerSW::flush_queries() {
if (!active)
return;
+ uint64_t time_beg = OS::get_singleton()->get_ticks_usec();
for( Set<const Space2DSW*>::Element *E=active_spaces.front();E;E=E->next()) {
@@ -1286,7 +1301,44 @@ void Physics2DServerSW::flush_queries() {
space->call_queries();
}
-};
+
+ if (ScriptDebugger::get_singleton() && ScriptDebugger::get_singleton()->is_profiling()) {
+
+ uint64_t total_time[Space2DSW::ELAPSED_TIME_MAX];
+ static const char* time_name[Space2DSW::ELAPSED_TIME_MAX]={
+ "integrate_forces",
+ "generate_islands",
+ "setup_constraints",
+ "solve_constraints",
+ "integrate_velocities"
+ };
+
+ for(int i=0;i<Space2DSW::ELAPSED_TIME_MAX;i++) {
+ total_time[i]=0;
+ }
+
+ for( Set<const Space2DSW*>::Element *E=active_spaces.front();E;E=E->next()) {
+
+ for(int i=0;i<Space2DSW::ELAPSED_TIME_MAX;i++) {
+ total_time[i]+=E->get()->get_elapsed_time(Space2DSW::ElapsedTime(i));
+ }
+
+ }
+
+ Array values;
+ values.resize(Space2DSW::ELAPSED_TIME_MAX*2);
+ for(int i=0;i<Space2DSW::ELAPSED_TIME_MAX;i++) {
+ values[i*2+0]=time_name[i];
+ values[i*2+1]=USEC_TO_SEC(total_time[i]);
+ }
+ values.push_back("flush_queries");
+ values.push_back(USEC_TO_SEC(OS::get_singleton()->get_ticks_usec()-time_beg));
+
+ ScriptDebugger::get_singleton()->add_profiling_frame_data("physics_2d",values);
+
+ }
+
+}
void Physics2DServerSW::end_sync() {
doing_sync=false;
diff --git a/servers/physics_2d/physics_2d_server_sw.h b/servers/physics_2d/physics_2d_server_sw.h
index cd4dfc1a8b..d557688b91 100644
--- a/servers/physics_2d/physics_2d_server_sw.h
+++ b/servers/physics_2d/physics_2d_server_sw.h
@@ -55,6 +55,7 @@ friend class Physics2DDirectBodyStateSW;
bool using_threads;
+
Step2DSW *stepper;
Set<const Space2DSW*> active_spaces;
@@ -205,6 +206,8 @@ public:
virtual void body_set_applied_torque(RID p_body, float p_torque);
virtual float body_get_applied_torque(RID p_body) const;
+ virtual void body_add_force(RID p_body, const Vector2& p_offset, const Vector2& p_force);
+
virtual void body_apply_impulse(RID p_body, const Vector2& p_pos, const Vector2& p_impulse);
virtual void body_set_axis_velocity(RID p_body, const Vector2& p_axis_velocity);
diff --git a/servers/physics_2d/physics_2d_server_wrap_mt.h b/servers/physics_2d/physics_2d_server_wrap_mt.h
index 60f8a4c879..891c45addf 100644
--- a/servers/physics_2d/physics_2d_server_wrap_mt.h
+++ b/servers/physics_2d/physics_2d_server_wrap_mt.h
@@ -205,6 +205,7 @@ public:
FUNC2(body_set_applied_torque,RID,float);
FUNC1RC(float,body_get_applied_torque,RID);
+ FUNC3(body_add_force,RID,const Vector2&,const Vector2&);
FUNC3(body_apply_impulse,RID,const Vector2&,const Vector2&);
FUNC2(body_set_axis_velocity,RID,const Vector2&);
diff --git a/servers/physics_2d/space_2d_sw.cpp b/servers/physics_2d/space_2d_sw.cpp
index 027e218bfc..ddef5fc86b 100644
--- a/servers/physics_2d/space_2d_sw.cpp
+++ b/servers/physics_2d/space_2d_sw.cpp
@@ -198,7 +198,7 @@ int Physics2DDirectSpaceStateSW::intersect_shape(const RID& p_shape, const Matri
Rect2 aabb = p_xform.xform(shape->get_aabb());
aabb=aabb.grow(p_margin);
- int amount = space->broadphase->cull_aabb(aabb,space->intersection_query_results,Space2DSW::INTERSECTION_QUERY_MAX,space->intersection_query_subindex_results);
+ int amount = space->broadphase->cull_aabb(aabb,space->intersection_query_results,p_result_max,space->intersection_query_subindex_results);
bool collided=false;
int cc=0;
@@ -1325,7 +1325,8 @@ Space2DSW::Space2DSW() {
direct_access->space=this;
-
+ for(int i=0;i<ELAPSED_TIME_MAX;i++)
+ elapsed_time[i]=0;
}
diff --git a/servers/physics_2d/space_2d_sw.h b/servers/physics_2d/space_2d_sw.h
index 5f35f224b2..f8e1f32838 100644
--- a/servers/physics_2d/space_2d_sw.h
+++ b/servers/physics_2d/space_2d_sw.h
@@ -60,6 +60,20 @@ public:
class Space2DSW {
+public:
+
+ enum ElapsedTime {
+ ELAPSED_TIME_INTEGRATE_FORCES,
+ ELAPSED_TIME_GENERATE_ISLANDS,
+ ELAPSED_TIME_SETUP_CONSTRAINTS,
+ ELAPSED_TIME_SOLVE_CONSTRAINTS,
+ ELAPSED_TIME_INTEGRATE_VELOCITIES,
+ ELAPSED_TIME_MAX
+
+ };
+private:
+
+ uint64_t elapsed_time[ELAPSED_TIME_MAX];
Physics2DDirectSpaceStateSW *direct_access;
RID self;
@@ -182,6 +196,9 @@ public:
Physics2DDirectSpaceStateSW *get_direct_state();
+ void set_elapsed_time(ElapsedTime p_time,uint64_t p_msec) { elapsed_time[p_time]=p_msec; }
+ uint64_t get_elapsed_time(ElapsedTime p_time) const { return elapsed_time[p_time]; }
+
Space2DSW();
~Space2DSW();
};
diff --git a/servers/physics_2d/step_2d_sw.cpp b/servers/physics_2d/step_2d_sw.cpp
index 4f9d06ee96..4f86168c1e 100644
--- a/servers/physics_2d/step_2d_sw.cpp
+++ b/servers/physics_2d/step_2d_sw.cpp
@@ -27,7 +27,7 @@
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
/*************************************************************************/
#include "step_2d_sw.h"
-
+#include "os/os.h"
void Step2DSW::_populate_island(Body2DSW* p_body,Body2DSW** p_island,Constraint2DSW **p_constraint_island) {
@@ -142,6 +142,11 @@ void Step2DSW::step(Space2DSW* p_space,float p_delta,int p_iterations) {
const SelfList<Body2DSW>::List * body_list = &p_space->get_active_body_list();
/* INTEGRATE FORCES */
+
+ uint64_t profile_begtime = OS::get_singleton()->get_ticks_usec();
+ uint64_t profile_endtime=0;
+
+
int active_count=0;
const SelfList<Body2DSW>*b = body_list->first();
@@ -154,6 +159,13 @@ void Step2DSW::step(Space2DSW* p_space,float p_delta,int p_iterations) {
p_space->set_active_objects(active_count);
+
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(Space2DSW::ELAPSED_TIME_INTEGRATE_FORCES,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
/* GENERATE CONSTRAINT ISLANDS */
Body2DSW *island_list=NULL;
@@ -190,7 +202,6 @@ void Step2DSW::step(Space2DSW* p_space,float p_delta,int p_iterations) {
const SelfList<Area2DSW>::List &aml = p_space->get_moved_area_list();
-
while(aml.first()) {
for(const Set<Constraint2DSW*>::Element *E=aml.first()->self()->get_constraints().front();E;E=E->next()) {
@@ -206,6 +217,13 @@ void Step2DSW::step(Space2DSW* p_space,float p_delta,int p_iterations) {
}
// print_line("island count: "+itos(island_count)+" active count: "+itos(active_count));
+
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(Space2DSW::ELAPSED_TIME_GENERATE_ISLANDS,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
/* SETUP CONSTRAINT ISLANDS */
{
@@ -248,6 +266,12 @@ void Step2DSW::step(Space2DSW* p_space,float p_delta,int p_iterations) {
}
}
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(Space2DSW::ELAPSED_TIME_SETUP_CONSTRAINTS,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
/* SOLVE CONSTRAINT ISLANDS */
{
@@ -259,6 +283,12 @@ void Step2DSW::step(Space2DSW* p_space,float p_delta,int p_iterations) {
}
}
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(Space2DSW::ELAPSED_TIME_SOLVE_CONSTRAINTS,profile_endtime-profile_begtime);
+ profile_begtime=profile_endtime;
+ }
+
/* INTEGRATE VELOCITIES */
b = body_list->first();
@@ -280,6 +310,12 @@ void Step2DSW::step(Space2DSW* p_space,float p_delta,int p_iterations) {
}
}
+ { //profile
+ profile_endtime=OS::get_singleton()->get_ticks_usec();
+ p_space->set_elapsed_time(Space2DSW::ELAPSED_TIME_INTEGRATE_VELOCITIES,profile_endtime-profile_begtime);
+ //profile_begtime=profile_endtime;
+ }
+
p_space->update();
p_space->unlock();
_step++;
diff --git a/servers/physics_2d_server.cpp b/servers/physics_2d_server.cpp
index 2d267a5749..411b99ebc8 100644
--- a/servers/physics_2d_server.cpp
+++ b/servers/physics_2d_server.cpp
@@ -597,6 +597,7 @@ void Physics2DServer::_bind_methods() {
ObjectTypeDB::bind_method(_MD("body_get_state","body","state"),&Physics2DServer::body_get_state);
ObjectTypeDB::bind_method(_MD("body_apply_impulse","body","pos","impulse"),&Physics2DServer::body_apply_impulse);
+ ObjectTypeDB::bind_method(_MD("body_add_force","body","offset","force"),&Physics2DServer::body_add_force);
ObjectTypeDB::bind_method(_MD("body_set_axis_velocity","body","axis_velocity"),&Physics2DServer::body_set_axis_velocity);
ObjectTypeDB::bind_method(_MD("body_add_collision_exception","body","excepted_body"),&Physics2DServer::body_add_collision_exception);
@@ -629,7 +630,7 @@ void Physics2DServer::_bind_methods() {
ObjectTypeDB::bind_method(_MD("groove_joint_create","groove1_a","groove2_a","anchor_b","body_a","body_b"),&Physics2DServer::groove_joint_create,DEFVAL(RID()),DEFVAL(RID()));
ObjectTypeDB::bind_method(_MD("damped_spring_joint_create","anchor_a","anchor_b","body_a","body_b"),&Physics2DServer::damped_spring_joint_create,DEFVAL(RID()));
- ObjectTypeDB::bind_method(_MD("damped_string_joint_set_param","joint","param","value"),&Physics2DServer::damped_string_joint_set_param,DEFVAL(RID()));
+ ObjectTypeDB::bind_method(_MD("damped_string_joint_set_param","joint","param","value"),&Physics2DServer::damped_string_joint_set_param);
ObjectTypeDB::bind_method(_MD("damped_string_joint_get_param","joint","param"),&Physics2DServer::damped_string_joint_get_param);
ObjectTypeDB::bind_method(_MD("joint_get_type","joint"),&Physics2DServer::joint_get_type);
@@ -677,6 +678,7 @@ void Physics2DServer::_bind_methods() {
BIND_CONSTANT( BODY_PARAM_BOUNCE );
BIND_CONSTANT( BODY_PARAM_FRICTION );
BIND_CONSTANT( BODY_PARAM_MASS );
+ BIND_CONSTANT( BODY_PARAM_INERTIA );
BIND_CONSTANT( BODY_PARAM_GRAVITY_SCALE );
BIND_CONSTANT( BODY_PARAM_LINEAR_DAMP);
BIND_CONSTANT( BODY_PARAM_ANGULAR_DAMP);
diff --git a/servers/physics_2d_server.h b/servers/physics_2d_server.h
index 25875f16d3..53c5a9ecc0 100644
--- a/servers/physics_2d_server.h
+++ b/servers/physics_2d_server.h
@@ -421,6 +421,7 @@ public:
BODY_PARAM_BOUNCE,
BODY_PARAM_FRICTION,
BODY_PARAM_MASS, ///< unused for static, always infinite
+ BODY_PARAM_INERTIA, // read-only: computed from mass & shapes
BODY_PARAM_GRAVITY_SCALE,
BODY_PARAM_LINEAR_DAMP,
BODY_PARAM_ANGULAR_DAMP,
@@ -450,7 +451,9 @@ public:
virtual void body_set_applied_torque(RID p_body, float p_torque)=0;
virtual float body_get_applied_torque(RID p_body) const=0;
- virtual void body_apply_impulse(RID p_body, const Vector2& p_pos, const Vector2& p_impulse)=0;
+ virtual void body_add_force(RID p_body, const Vector2& p_offset, const Vector2& p_force)=0;
+
+ virtual void body_apply_impulse(RID p_body, const Vector2& p_offset, const Vector2& p_impulse)=0;
virtual void body_set_axis_velocity(RID p_body, const Vector2& p_axis_velocity)=0;
//fix
@@ -559,7 +562,9 @@ public:
INFO_ACTIVE_OBJECTS,
INFO_COLLISION_PAIRS,
- INFO_ISLAND_COUNT
+ INFO_ISLAND_COUNT,
+ INFO_STEP_TIME,
+ INFO_BROAD_PHASE_TIME
};
virtual int get_process_info(ProcessInfo p_info)=0;
diff --git a/servers/physics_server.cpp b/servers/physics_server.cpp
index 89fcffe7ed..685477ed79 100644
--- a/servers/physics_server.cpp
+++ b/servers/physics_server.cpp
@@ -457,6 +457,8 @@ void PhysicsServer::_bind_methods() {
ObjectTypeDB::bind_method(_MD("area_remove_shape","area","shape_idx"),&PhysicsServer::area_remove_shape);
ObjectTypeDB::bind_method(_MD("area_clear_shapes","area"),&PhysicsServer::area_clear_shapes);
+ ObjectTypeDB::bind_method(_MD("area_set_layer_mask","area","mask"),&PhysicsServer::area_set_layer_mask);
+ ObjectTypeDB::bind_method(_MD("area_set_collision_mask","area","mask"),&PhysicsServer::area_set_collision_mask);
ObjectTypeDB::bind_method(_MD("area_set_param","area","param","value"),&PhysicsServer::area_set_param);
ObjectTypeDB::bind_method(_MD("area_set_transform","area","transform"),&PhysicsServer::area_set_transform);
@@ -480,6 +482,12 @@ void PhysicsServer::_bind_methods() {
ObjectTypeDB::bind_method(_MD("body_set_mode","body","mode"),&PhysicsServer::body_set_mode);
ObjectTypeDB::bind_method(_MD("body_get_mode","body"),&PhysicsServer::body_get_mode);
+ ObjectTypeDB::bind_method(_MD("body_set_layer_mask","body","mask"),&PhysicsServer::body_set_layer_mask);
+ ObjectTypeDB::bind_method(_MD("body_get_layer_mask","body"),&PhysicsServer::body_get_layer_mask);
+
+ ObjectTypeDB::bind_method(_MD("body_set_collision_mask","body","mask"),&PhysicsServer::body_set_collision_mask);
+ ObjectTypeDB::bind_method(_MD("body_get_collision_mask","body"),&PhysicsServer::body_get_collision_mask);
+
ObjectTypeDB::bind_method(_MD("body_add_shape","body","shape","transform"),&PhysicsServer::body_add_shape,DEFVAL(Transform()));
ObjectTypeDB::bind_method(_MD("body_set_shape","body","shape_idx","shape"),&PhysicsServer::body_set_shape);
ObjectTypeDB::bind_method(_MD("body_set_shape_transform","body","shape_idx","transform"),&PhysicsServer::body_set_shape_transform);
diff --git a/servers/physics_server.h b/servers/physics_server.h
index 9b00825d92..5221b38ccb 100644
--- a/servers/physics_server.h
+++ b/servers/physics_server.h
@@ -346,6 +346,9 @@ public:
virtual Variant area_get_param(RID p_parea,AreaParameter p_param) const=0;
virtual Transform area_get_transform(RID p_area) const=0;
+ virtual void area_set_collision_mask(RID p_area,uint32_t p_mask)=0;
+ virtual void area_set_layer_mask(RID p_area,uint32_t p_mask)=0;
+
virtual void area_set_monitorable(RID p_area,bool p_monitorable)=0;
virtual void area_set_monitor_callback(RID p_area,Object *p_receiver,const StringName& p_method)=0;
@@ -397,6 +400,9 @@ public:
virtual void body_set_layer_mask(RID p_body, uint32_t p_mask)=0;
virtual uint32_t body_get_layer_mask(RID p_body, uint32_t p_mask) const=0;
+ virtual void body_set_collision_mask(RID p_body, uint32_t p_mask)=0;
+ virtual uint32_t body_get_collision_mask(RID p_body, uint32_t p_mask) const=0;
+
virtual void body_set_user_flags(RID p_body, uint32_t p_flags)=0;
virtual uint32_t body_get_user_flags(RID p_body, uint32_t p_flags) const=0;
diff --git a/servers/server_wrap_mt_common.h b/servers/server_wrap_mt_common.h
index cbb75129d0..149e9ec4f9 100644
--- a/servers/server_wrap_mt_common.h
+++ b/servers/server_wrap_mt_common.h
@@ -698,3 +698,64 @@
}\
}
+#define FUNC8R(m_r,m_type,m_arg1, m_arg2, m_arg3, m_arg4, m_arg5, m_arg6, m_arg7, m_arg8)\
+ virtual m_r m_type(m_arg1 p1, m_arg2 p2, m_arg3 p3, m_arg4 p4, m_arg5 p5, m_arg6 p6, m_arg7 p7, m_arg8 p8) { \
+ if (Thread::get_caller_ID()!=server_thread) {\
+ m_r ret;\
+ command_queue.push_and_ret( server_name, &ServerName::m_type,p1, p2, p3, p4, p5, p6, p7, p8, &ret);\
+ SYNC_DEBUG\
+ return ret;\
+ } else {\
+ return server_name->m_type(p1, p2, p3, p4, p5, p6, p7, p8);\
+ }\
+ }
+
+#define FUNC8RC(m_r,m_type,m_arg1, m_arg2, m_arg3, m_arg4, m_arg5, m_arg6, m_arg7, m_arg8)\
+ virtual m_r m_type(m_arg1 p1, m_arg2 p2, m_arg3 p3, m_arg4 p4, m_arg5 p5, m_arg6 p6, m_arg7 p7, m_arg8 p8) const { \
+ if (Thread::get_caller_ID()!=server_thread) {\
+ m_r ret;\
+ command_queue.push_and_ret( server_name, &ServerName::m_type,p1, p2, p3, p4, p5, p6, p7, p8, &ret);\
+ SYNC_DEBUG\
+ return ret;\
+ } else {\
+ return server_name->m_type(p1, p2, p3, p4, p5, p6, p7, p8);\
+ }\
+ }
+
+
+#define FUNC8S(m_type,m_arg1, m_arg2, m_arg3, m_arg4, m_arg5, m_arg6, m_arg7, m_arg8)\
+ virtual void m_type(m_arg1 p1, m_arg2 p2, m_arg3 p3, m_arg4 p4, m_arg5 p5, m_arg6 p6, m_arg7 p7, m_arg8 p8) { \
+ if (Thread::get_caller_ID()!=server_thread) {\
+ command_queue.push_and_sync( server_name, &ServerName::m_type,p1, p2, p3, p4, p5, p6, p7, p8);\
+ } else {\
+ server_name->m_type(p1, p2, p3, p4, p5, p6, p7, p8);\
+ }\
+ }
+
+#define FUNC8SC(m_type,m_arg1, m_arg2, m_arg3, m_arg4, m_arg5, m_arg6, m_arg7, m_arg8)\
+ virtual void m_type(m_arg1 p1, m_arg2 p2, m_arg3 p3, m_arg4 p4, m_arg5 p5, m_arg6 p6, m_arg7 p7, m_arg8 p8) const { \
+ if (Thread::get_caller_ID()!=server_thread) {\
+ command_queue.push_and_sync( server_name, &ServerName::m_type,p1, p2, p3, p4, p5, p6, p7, p8);\
+ } else {\
+ server_name->m_type(p1, p2, p3, p4, p5, p6, p7, p8);\
+ }\
+ }
+
+
+#define FUNC8(m_type,m_arg1, m_arg2, m_arg3, m_arg4, m_arg5, m_arg6, m_arg7, m_arg8)\
+ virtual void m_type(m_arg1 p1, m_arg2 p2, m_arg3 p3, m_arg4 p4, m_arg5 p5, m_arg6 p6, m_arg7 p7, m_arg8 p8) { \
+ if (Thread::get_caller_ID()!=server_thread) {\
+ command_queue.push( server_name, &ServerName::m_type,p1, p2, p3, p4, p5, p6, p7, p8);\
+ } else {\
+ server_name->m_type(p1, p2, p3, p4, p5, p6, p7, p8);\
+ }\
+ }
+
+#define FUNC8C(m_type,m_arg1, m_arg2, m_arg3, m_arg4, m_arg5, m_arg6, m_arg7, m_arg8)\
+ virtual void m_type(m_arg1 p1, m_arg2 p2, m_arg3 p3, m_arg4 p4, m_arg5 p5, m_arg6 p6, m_arg7 p7, m_arg8 p8) const { \
+ if (Thread::get_caller_ID()!=server_thread) {\
+ command_queue.push( server_name, &ServerName::m_type,p1, p2, p3, p4, p5, p6, p7, p8);\
+ } else {\
+ server_name->m_type(p1, p2, p3, p4, p5, p6, p7, p8);\
+ }\
+ }
diff --git a/servers/visual/rasterizer.h b/servers/visual/rasterizer.h
index e2de20785a..50ec6792cc 100644
--- a/servers/visual/rasterizer.h
+++ b/servers/visual/rasterizer.h
@@ -196,6 +196,8 @@ public:
virtual String texture_get_path(RID p_texture) const=0;
virtual void texture_debug_usage(List<VS::TextureInfo> *r_info)=0;
+ virtual void texture_set_shrink_all_x2_on_set_data(bool p_enable)=0;
+
/* SHADER API */
virtual RID shader_create(VS::ShaderMode p_mode=VS::SHADER_MATERIAL)=0;
@@ -540,6 +542,7 @@ public:
RID skeleton;
RID material_override;
RID sampled_light;
+ Vector<RID> materials;
Vector<RID> light_instances;
Vector<float> morph_values;
BakedLightData *baked_light;
@@ -699,6 +702,7 @@ public:
struct CommandStyle : public Command {
Rect2 rect;
+ Rect2 source;
RID texture;
float margin[4];
bool draw_center;
@@ -941,12 +945,12 @@ public:
virtual void canvas_disable_blending()=0;
virtual void canvas_set_opacity(float p_opacity)=0;
virtual void canvas_set_blend_mode(VS::MaterialBlendMode p_mode)=0;
- virtual void canvas_begin_rect(const Matrix32& p_transform)=0;;
+ virtual void canvas_begin_rect(const Matrix32& p_transform)=0;
virtual void canvas_set_clip(bool p_clip, const Rect2& p_rect)=0;
virtual void canvas_end_rect()=0;
virtual void canvas_draw_line(const Point2& p_from, const Point2& p_to,const Color& p_color,float p_width)=0;
virtual void canvas_draw_rect(const Rect2& p_rect, int p_flags, const Rect2& p_source,RID p_texture,const Color& p_modulate)=0;
- virtual void canvas_draw_style_box(const Rect2& p_rect, RID p_texture,const float *p_margins, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1))=0;
+ virtual void canvas_draw_style_box(const Rect2& p_rect, const Rect2& p_src_region, RID p_texture,const float *p_margins, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1))=0;
virtual void canvas_draw_primitive(const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs, RID p_texture,float p_width)=0;
virtual void canvas_draw_polygon(int p_vertex_count, const int* p_indices, const Vector2* p_vertices, const Vector2* p_uvs, const Color* p_colors,const RID& p_texture,bool p_singlecolor)=0;
virtual void canvas_set_transform(const Matrix32& p_transform)=0;
diff --git a/servers/visual/rasterizer_dummy.cpp b/servers/visual/rasterizer_dummy.cpp
index 3b12b503dd..0e71d224d5 100644
--- a/servers/visual/rasterizer_dummy.cpp
+++ b/servers/visual/rasterizer_dummy.cpp
@@ -1627,7 +1627,7 @@ void RasterizerDummy::canvas_draw_rect(const Rect2& p_rect, int p_flags, const R
}
-void RasterizerDummy::canvas_draw_style_box(const Rect2& p_rect, RID p_texture,const float *p_margin, bool p_draw_center,const Color& p_modulate) {
+void RasterizerDummy::canvas_draw_style_box(const Rect2& p_rect, const Rect2& p_src_region, RID p_texture,const float *p_margin, bool p_draw_center,const Color& p_modulate) {
}
@@ -1959,4 +1959,3 @@ RasterizerDummy::RasterizerDummy() {
RasterizerDummy::~RasterizerDummy() {
};
-
diff --git a/servers/visual/rasterizer_dummy.h b/servers/visual/rasterizer_dummy.h
index efa843839a..ac320e55f9 100644
--- a/servers/visual/rasterizer_dummy.h
+++ b/servers/visual/rasterizer_dummy.h
@@ -415,6 +415,8 @@ public:
virtual String texture_get_path(RID p_texture) const { return String(); }
virtual void texture_debug_usage(List<VS::TextureInfo> *r_info) {}
+ virtual void texture_set_shrink_all_x2_on_set_data(bool p_enable) {}
+
/* SHADER API */
virtual RID shader_create(VS::ShaderMode p_mode=VS::SHADER_MATERIAL);
@@ -706,7 +708,7 @@ public:
virtual void canvas_end_rect();
virtual void canvas_draw_line(const Point2& p_from, const Point2& p_to,const Color& p_color,float p_width);
virtual void canvas_draw_rect(const Rect2& p_rect, int p_flags, const Rect2& p_source,RID p_texture,const Color& p_modulate);
- virtual void canvas_draw_style_box(const Rect2& p_rect, RID p_texture,const float *p_margins, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1));
+ virtual void canvas_draw_style_box(const Rect2& p_rect, const Rect2& p_src_region, RID p_texture,const float *p_margins, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1));
virtual void canvas_draw_primitive(const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs, RID p_texture,float p_width);
virtual void canvas_draw_polygon(int p_vertex_count, const int* p_indices, const Vector2* p_vertices, const Vector2* p_uvs, const Color* p_colors,const RID& p_texture,bool p_singlecolor);
virtual void canvas_set_transform(const Matrix32& p_transform);
diff --git a/servers/visual/visual_server_raster.cpp b/servers/visual/visual_server_raster.cpp
index 1db7971d3b..532247d94c 100644
--- a/servers/visual/visual_server_raster.cpp
+++ b/servers/visual/visual_server_raster.cpp
@@ -127,6 +127,11 @@ void VisualServerRaster::texture_debug_usage(List<TextureInfo> *r_info){
rasterizer->texture_debug_usage(r_info);
}
+void VisualServerRaster::texture_set_shrink_all_x2_on_set_data(bool p_enable) {
+
+ rasterizer->texture_set_shrink_all_x2_on_set_data(p_enable);
+}
+
/* SHADER API */
RID VisualServerRaster::shader_create(ShaderMode p_mode) {
@@ -393,7 +398,7 @@ void VisualServerRaster::mesh_add_custom_surface(RID p_mesh,const Variant& p_dat
void VisualServerRaster::mesh_add_surface(RID p_mesh,PrimitiveType p_primitive,const Array& p_arrays,const Array& p_blend_shapes,bool p_alpha_sort) {
VS_CHANGED;
- _dependency_queue_update(p_mesh,true);
+ _dependency_queue_update(p_mesh,true,true);
rasterizer->mesh_add_surface(p_mesh,p_primitive,p_arrays,p_blend_shapes,p_alpha_sort);
}
@@ -447,6 +452,7 @@ VisualServer::PrimitiveType VisualServerRaster::mesh_surface_get_primitive_type(
void VisualServerRaster::mesh_remove_surface(RID p_mesh,int p_surface){
rasterizer->mesh_remove_surface(p_mesh,p_surface);
+ _dependency_queue_update(p_mesh,true,true);
}
int VisualServerRaster::mesh_get_surface_count(RID p_mesh) const{
@@ -475,6 +481,8 @@ void VisualServerRaster::mesh_clear(RID p_mesh) {
while(rasterizer->mesh_get_surface_count(p_mesh)) {
rasterizer->mesh_remove_surface(p_mesh,0);
}
+
+ _dependency_queue_update(p_mesh,true,true);
}
@@ -2033,7 +2041,7 @@ Variant VisualServerRaster::environment_fx_get_param(RID p_env,EnvironmentFxPara
/* SCENARIO API */
-void VisualServerRaster::_dependency_queue_update(RID p_rid,bool p_update_aabb) {
+void VisualServerRaster::_dependency_queue_update(RID p_rid,bool p_update_aabb,bool p_update_materials) {
Map< RID, Set<RID> >::Element * E = instance_dependency_map.find( p_rid );
@@ -2046,17 +2054,19 @@ void VisualServerRaster::_dependency_queue_update(RID p_rid,bool p_update_aabb)
while(I) {
Instance *ins = instance_owner.get( I->get() );
- _instance_queue_update( ins , p_update_aabb );
+ _instance_queue_update( ins , p_update_aabb, p_update_materials );
I = I->next();
}
}
-void VisualServerRaster::_instance_queue_update(Instance *p_instance,bool p_update_aabb) {
+void VisualServerRaster::_instance_queue_update(Instance *p_instance,bool p_update_aabb,bool p_update_materials) {
if (p_update_aabb)
p_instance->update_aabb=true;
+ if (p_update_materials)
+ p_instance->update_materials=true;
if (p_instance->update)
return;
@@ -2268,6 +2278,7 @@ void VisualServerRaster::instance_set_base(RID p_instance, RID p_base) {
}
instance->data.morph_values.clear();
+ instance->data.materials.clear();
}
@@ -2281,6 +2292,7 @@ void VisualServerRaster::instance_set_base(RID p_instance, RID p_base) {
if (rasterizer->is_mesh(p_base)) {
instance->base_type=INSTANCE_MESH;
instance->data.morph_values.resize( rasterizer->mesh_get_morph_target_count(p_base));
+ instance->data.materials.resize( rasterizer->mesh_get_surface_count(p_base));
} else if (rasterizer->is_multimesh(p_base)) {
instance->base_type=INSTANCE_MULTIMESH;
} else if (rasterizer->is_immediate(p_base)) {
@@ -2505,6 +2517,16 @@ float VisualServerRaster::instance_get_morph_target_weight(RID p_instance,int p_
return instance->data.morph_values[p_shape];
}
+void VisualServerRaster::instance_set_surface_material(RID p_instance,int p_surface, RID p_material) {
+
+ VS_CHANGED;
+ Instance *instance = instance_owner.get( p_instance );
+ ERR_FAIL_COND( !instance);
+ ERR_FAIL_INDEX( p_surface, instance->data.materials.size() );
+ instance->data.materials[p_surface]=p_material;
+}
+
+
void VisualServerRaster::instance_set_transform(RID p_instance, const Transform& p_transform) {
VS_CHANGED;
Instance *instance = instance_owner.get( p_instance );
@@ -3041,6 +3063,7 @@ void VisualServerRaster::_update_instance(Instance *p_instance) {
}
+
if (p_instance->aabb.has_no_surface())
return;
@@ -3296,10 +3319,17 @@ void VisualServerRaster::_update_instances() {
if (instance->update_aabb)
_update_instance_aabb(instance);
+ if (instance->update_materials) {
+ if (instance->base_type==INSTANCE_MESH) {
+ instance->data.materials.resize(rasterizer->mesh_get_surface_count(instance->base_rid));
+ }
+ }
+
_update_instance(instance);
instance->update=false;
instance->update_aabb=false;
+ instance->update_materials=false;
instance->update_next=0;
}
}
@@ -3656,8 +3686,11 @@ void VisualServerRaster::canvas_item_add_texture_rect(RID p_item, const Rect2& p
rect->modulate=p_modulate;
rect->rect=p_rect;
rect->flags=0;
- if (p_tile)
+ if (p_tile) {
rect->flags|=Rasterizer::CANVAS_RECT_TILE;
+ rect->flags|=Rasterizer::CANVAS_RECT_REGION;
+ rect->source=Rect2(0,0,p_rect.size.width,p_rect.size.height);
+ }
if (p_rect.size.x<0) {
@@ -3712,7 +3745,7 @@ void VisualServerRaster::canvas_item_add_texture_rect_region(RID p_item, const R
}
-void VisualServerRaster::canvas_item_add_style_box(RID p_item, const Rect2& p_rect, RID p_texture,const Vector2& p_topleft, const Vector2& p_bottomright, bool p_draw_center,const Color& p_modulate) {
+void VisualServerRaster::canvas_item_add_style_box(RID p_item, const Rect2& p_rect, const Rect2& p_source, RID p_texture, const Vector2& p_topleft, const Vector2& p_bottomright, bool p_draw_center,const Color& p_modulate) {
VS_CHANGED;
CanvasItem *canvas_item = canvas_item_owner.get( p_item );
@@ -3722,6 +3755,7 @@ void VisualServerRaster::canvas_item_add_style_box(RID p_item, const Rect2& p_re
ERR_FAIL_COND(!style);
style->texture=p_texture;
style->rect=p_rect;
+ style->source=p_source;
style->draw_center=p_draw_center;
style->color=p_modulate;
style->margin[MARGIN_LEFT]=p_topleft.x;
diff --git a/servers/visual/visual_server_raster.h b/servers/visual/visual_server_raster.h
index 2b72b0b900..dcaac6e8d2 100644
--- a/servers/visual/visual_server_raster.h
+++ b/servers/visual/visual_server_raster.h
@@ -160,6 +160,7 @@ class VisualServerRaster : public VisualServer {
Scenario *scenario;
bool update;
bool update_aabb;
+ bool update_materials;
Instance *update_next;
InstanceType base_type;
@@ -317,6 +318,8 @@ class VisualServerRaster : public VisualServer {
draw_range_end=0;
extra_margin=0;
visible_in_all_rooms=false;
+ update_aabb=false;
+ update_materials=false;
baked_light=NULL;
baked_light_info=NULL;
@@ -583,8 +586,8 @@ class VisualServerRaster : public VisualServer {
void _portal_disconnect(Instance *p_portal,bool p_cleanup=false);
void _portal_attempt_connect(Instance *p_portal);
- void _dependency_queue_update(RID p_rid,bool p_update_aabb=false);
- _FORCE_INLINE_ void _instance_queue_update(Instance *p_instance,bool p_update_aabb=false);
+ void _dependency_queue_update(RID p_rid, bool p_update_aabb=false, bool p_update_materials=false);
+ _FORCE_INLINE_ void _instance_queue_update(Instance *p_instance,bool p_update_aabb=false,bool p_update_materials=false);
void _update_instances();
void _update_instance_aabb(Instance *p_instance);
void _update_instance(Instance *p_instance);
@@ -673,6 +676,8 @@ public:
virtual void texture_debug_usage(List<TextureInfo> *r_info);
+ virtual void texture_set_shrink_all_x2_on_set_data(bool p_enable);
+
/* SHADER API */
@@ -1081,6 +1086,9 @@ public:
virtual void instance_set_morph_target_weight(RID p_instance,int p_shape, float p_weight);
virtual float instance_get_morph_target_weight(RID p_instance,int p_shape) const;
+ virtual void instance_set_surface_material(RID p_instance,int p_surface, RID p_material);
+
+
virtual void instance_set_transform(RID p_instance, const Transform& p_transform);
virtual Transform instance_get_transform(RID p_instance) const;
@@ -1163,7 +1171,7 @@ public:
virtual void canvas_item_add_circle(RID p_item, const Point2& p_pos, float p_radius,const Color& p_color);
virtual void canvas_item_add_texture_rect(RID p_item, const Rect2& p_rect, RID p_texture,bool p_tile=false,const Color& p_modulate=Color(1,1,1),bool p_transpose=false);
virtual void canvas_item_add_texture_rect_region(RID p_item, const Rect2& p_rect, RID p_texture,const Rect2& p_src_rect,const Color& p_modulate=Color(1,1,1),bool p_transpose=false);
- virtual void canvas_item_add_style_box(RID p_item, const Rect2& p_rect, RID p_texture,const Vector2& p_topleft, const Vector2& p_bottomright, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1));
+ virtual void canvas_item_add_style_box(RID p_item, const Rect2& p_rect, const Rect2& p_source, RID p_texture,const Vector2& p_topleft, const Vector2& p_bottomright, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1));
virtual void canvas_item_add_primitive(RID p_item, const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs, RID p_texture,float p_width=1.0);
virtual void canvas_item_add_polygon(RID p_item, const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs=Vector<Point2>(), RID p_texture=RID());
virtual void canvas_item_add_triangle_array(RID p_item, const Vector<int>& p_indices, const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs=Vector<Point2>(), RID p_texture=RID(), int p_count=-1);
diff --git a/servers/visual/visual_server_wrap_mt.h b/servers/visual/visual_server_wrap_mt.h
index b6018f1c25..a97b232c03 100644
--- a/servers/visual/visual_server_wrap_mt.h
+++ b/servers/visual/visual_server_wrap_mt.h
@@ -101,6 +101,8 @@ public:
FUNC2(texture_set_path,RID,const String&);
FUNC1RC(String,texture_get_path,RID);
+ FUNC1(texture_set_shrink_all_x2_on_set_data,bool);
+
virtual void texture_debug_usage(List<TextureInfo> *r_info) {
//pass directly, should lock the server anyway
visual_server->texture_debug_usage(r_info);
@@ -523,6 +525,8 @@ public:
FUNC3(instance_set_morph_target_weight,RID,int, float);
FUNC2RC(float,instance_get_morph_target_weight,RID,int);
+ FUNC3(instance_set_surface_material,RID,int, RID);
+
FUNC2(instance_set_transform,RID, const Transform&);
FUNC1RC(Transform,instance_get_transform,RID);
@@ -603,7 +607,7 @@ public:
FUNC4(canvas_item_add_circle,RID, const Point2& , float ,const Color& );
FUNC6(canvas_item_add_texture_rect,RID, const Rect2& , RID ,bool ,const Color&,bool );
FUNC6(canvas_item_add_texture_rect_region,RID, const Rect2& , RID ,const Rect2& ,const Color&,bool );
- FUNC7(canvas_item_add_style_box,RID, const Rect2& , RID ,const Vector2& ,const Vector2&, bool ,const Color& );
+ FUNC8(canvas_item_add_style_box,RID, const Rect2& , const Rect2&, RID ,const Vector2& ,const Vector2&, bool ,const Color& );
FUNC6(canvas_item_add_primitive,RID, const Vector<Point2>& , const Vector<Color>& ,const Vector<Point2>& , RID ,float );
FUNC5(canvas_item_add_polygon,RID, const Vector<Point2>& , const Vector<Color>& ,const Vector<Point2>& , RID );
FUNC7(canvas_item_add_triangle_array,RID, const Vector<int>& , const Vector<Point2>& , const Vector<Color>& ,const Vector<Point2>& , RID , int );
diff --git a/servers/visual_server.cpp b/servers/visual_server.cpp
index 17d5b16b9f..570a5a6ee4 100644
--- a/servers/visual_server.cpp
+++ b/servers/visual_server.cpp
@@ -355,8 +355,12 @@ void VisualServer::_bind_methods() {
ObjectTypeDB::bind_method(_MD("texture_get_flags"),&VisualServer::texture_get_flags );
ObjectTypeDB::bind_method(_MD("texture_get_width"),&VisualServer::texture_get_width );
ObjectTypeDB::bind_method(_MD("texture_get_height"),&VisualServer::texture_get_height );
+
+ ObjectTypeDB::bind_method(_MD("texture_set_shrink_all_x2_on_set_data","shrink"),&VisualServer::texture_set_shrink_all_x2_on_set_data );
+
#ifndef _3D_DISABLED
+
ObjectTypeDB::bind_method(_MD("shader_create","mode"),&VisualServer::shader_create,DEFVAL(SHADER_MATERIAL));
ObjectTypeDB::bind_method(_MD("shader_set_mode","shader","mode"),&VisualServer::shader_set_mode);
@@ -701,10 +705,10 @@ void VisualServer::_bind_methods() {
}
-void VisualServer::_canvas_item_add_style_box(RID p_item, const Rect2& p_rect, RID p_texture,const Vector<float>& p_margins, const Color& p_modulate) {
+void VisualServer::_canvas_item_add_style_box(RID p_item, const Rect2& p_rect, const Rect2& p_source, RID p_texture,const Vector<float>& p_margins, const Color& p_modulate) {
ERR_FAIL_COND(p_margins.size()!=4);
- canvas_item_add_style_box(p_item, p_rect, p_texture,Vector2(p_margins[0],p_margins[1]),Vector2(p_margins[2],p_margins[3]),true,p_modulate);
+ canvas_item_add_style_box(p_item,p_rect,p_source,p_texture,Vector2(p_margins[0],p_margins[1]),Vector2(p_margins[2],p_margins[3]),true,p_modulate);
}
void VisualServer::_camera_set_orthogonal(RID p_camera,float p_size,float p_z_near,float p_z_far) {
@@ -818,5 +822,3 @@ VisualServer::~VisualServer() {
singleton=NULL;
}
-
-
diff --git a/servers/visual_server.h b/servers/visual_server.h
index c70a72ef2a..f330a6faee 100644
--- a/servers/visual_server.h
+++ b/servers/visual_server.h
@@ -52,7 +52,7 @@ class VisualServer : public Object {
void _camera_set_orthogonal(RID p_camera,float p_size,float p_z_near,float p_z_far);
void _viewport_set_rect(RID p_viewport,const Rect2& p_rect);
Rect2 _viewport_get_rect(RID p_viewport) const;
- void _canvas_item_add_style_box(RID p_item, const Rect2& p_rect, RID p_texture,const Vector<float>& p_margins, const Color& p_modulate=Color(1,1,1));
+ void _canvas_item_add_style_box(RID p_item, const Rect2& p_rect, const Rect2& p_source, RID p_texture,const Vector<float>& p_margins, const Color& p_modulate=Color(1,1,1));
protected:
RID _make_test_cube();
void _free_internal_rids();
@@ -138,6 +138,8 @@ public:
virtual void texture_set_path(RID p_texture,const String& p_path)=0;
virtual String texture_get_path(RID p_texture) const=0;
+ virtual void texture_set_shrink_all_x2_on_set_data(bool p_enable)=0;
+
struct TextureInfo {
RID texture;
Size2 size;
@@ -917,6 +919,8 @@ public:
virtual void instance_set_morph_target_weight(RID p_instance,int p_shape, float p_weight)=0;
virtual float instance_get_morph_target_weight(RID p_instance,int p_shape) const=0;
+ virtual void instance_set_surface_material(RID p_instance,int p_surface, RID p_material)=0;
+
virtual void instance_attach_skeleton(RID p_instance,RID p_skeleton)=0;
virtual RID instance_get_skeleton(RID p_instance) const=0;
@@ -1021,7 +1025,7 @@ public:
virtual void canvas_item_add_circle(RID p_item, const Point2& p_pos, float p_radius,const Color& p_color)=0;
virtual void canvas_item_add_texture_rect(RID p_item, const Rect2& p_rect, RID p_texture,bool p_tile=false,const Color& p_modulate=Color(1,1,1),bool p_transpose=false)=0;
virtual void canvas_item_add_texture_rect_region(RID p_item, const Rect2& p_rect, RID p_texture,const Rect2& p_src_rect,const Color& p_modulate=Color(1,1,1),bool p_transpose=false)=0;
- virtual void canvas_item_add_style_box(RID p_item, const Rect2& p_rect, RID p_texture,const Vector2& p_topleft, const Vector2& p_bottomright, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1))=0;
+ virtual void canvas_item_add_style_box(RID p_item, const Rect2& p_rect, const Rect2& p_source, RID p_texture,const Vector2& p_topleft, const Vector2& p_bottomright, bool p_draw_center=true,const Color& p_modulate=Color(1,1,1))=0;
virtual void canvas_item_add_primitive(RID p_item, const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs, RID p_texture,float p_width=1.0)=0;
virtual void canvas_item_add_polygon(RID p_item, const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs=Vector<Point2>(), RID p_texture=RID())=0;
virtual void canvas_item_add_triangle_array(RID p_item, const Vector<int>& p_indices, const Vector<Point2>& p_points, const Vector<Color>& p_colors,const Vector<Point2>& p_uvs=Vector<Point2>(), RID p_texture=RID(), int p_count=-1)=0;