More Bug Fixes
-=-=-=-=-=-=- -Fixed a few bugs in Mixer, now playback of chiptunes works great :) -Changed how visibility AABB generation from skeletons work, it's fully automatic and real-time now, generated from current skeleton pose for the frame. -Fixed camera in 3D kinematic character demo.
This commit is contained in:
parent
76aaa96d0e
commit
990f6cf50e
18 changed files with 288 additions and 33 deletions
|
@ -45,13 +45,13 @@ func _fixed_process(dt):
|
||||||
var col = ds.intersect_ray(target,target,collision_exception)
|
var col = ds.intersect_ray(target,target,collision_exception)
|
||||||
var col_right = ds.intersect_ray(target,target+Matrix3(up,deg2rad(-autoturn_ray_aperture)).xform(delta),collision_exception)
|
var col_right = ds.intersect_ray(target,target+Matrix3(up,deg2rad(-autoturn_ray_aperture)).xform(delta),collision_exception)
|
||||||
|
|
||||||
if (col!=null):
|
if (!col.empty()):
|
||||||
#if main ray was occluded, get camera closer, this is the worst case scenario
|
#if main ray was occluded, get camera closer, this is the worst case scenario
|
||||||
delta = col.position - target
|
delta = col.position - target
|
||||||
elif (col_left!=null and col_right==null):
|
elif (!col_left.empty() and col_right.empty()):
|
||||||
#if only left ray is occluded, turn the camera around to the right
|
#if only left ray is occluded, turn the camera around to the right
|
||||||
delta = Matrix3(up,deg2rad(-dt*autoturn_speed)).xform(delta)
|
delta = Matrix3(up,deg2rad(-dt*autoturn_speed)).xform(delta)
|
||||||
elif (col_left==null and col_right!=null):
|
elif (col_left.empty() and !col_right.empty()):
|
||||||
#if only right ray is occluded, turn the camera around to the left
|
#if only right ray is occluded, turn the camera around to the left
|
||||||
delta = Matrix3(up,deg2rad(dt*autoturn_speed)).xform(delta)
|
delta = Matrix3(up,deg2rad(dt*autoturn_speed)).xform(delta)
|
||||||
else:
|
else:
|
||||||
|
|
|
@ -125,7 +125,7 @@ int64_t CPPlayer::get_channel_last_note_time_usec(int p_channel) const {
|
||||||
void CPPlayer::set_channel_global_volume(int p_channel,int p_volume) {
|
void CPPlayer::set_channel_global_volume(int p_channel,int p_volume) {
|
||||||
|
|
||||||
CP_FAIL_INDEX(p_channel,64);
|
CP_FAIL_INDEX(p_channel,64);
|
||||||
control.channel[p_channel].channel_global_volume=p_volume;
|
control.channel[p_channel].channel_global_volume=CLAMP(p_volume,0,255);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -146,6 +146,7 @@ void CPPlayer::Voice_Control::reset() {
|
||||||
|
|
||||||
void CPPlayer::Channel_Control::reset() {
|
void CPPlayer::Channel_Control::reset() {
|
||||||
|
|
||||||
|
int prev_gv =channel_global_volume;
|
||||||
cp_memzero(this,sizeof(*this));
|
cp_memzero(this,sizeof(*this));
|
||||||
|
|
||||||
slave_voice=NULL;
|
slave_voice=NULL;
|
||||||
|
@ -162,6 +163,7 @@ void CPPlayer::Channel_Control::reset() {
|
||||||
reserved=false;
|
reserved=false;
|
||||||
carry.maybe=false;
|
carry.maybe=false;
|
||||||
last_event_usecs=-1;
|
last_event_usecs=-1;
|
||||||
|
channel_global_volume=prev_gv;
|
||||||
}
|
}
|
||||||
|
|
||||||
void CPPlayer::Voice_Control::update_info_from_master_channel() {
|
void CPPlayer::Voice_Control::update_info_from_master_channel() {
|
||||||
|
@ -316,6 +318,15 @@ void CPPlayer::update_mixer() {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*printf("fadeout %i\n",(int)v.fadeout_volume);
|
||||||
|
printf("channel %i\n",(int)v.channel_volume);
|
||||||
|
printf("output %i\n",(int)v.output_volume);
|
||||||
|
printf("env %i\n",(int)tmp_volenv_value);
|
||||||
|
printf("cgb %i\n",(int)v.master_channel->channel_global_volume);
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
int cv=v.master_channel->channel_global_volume;
|
||||||
|
|
||||||
tmpvol=(uint64_t)v.fadeout_volume; /* max 1024 - 10 bits */
|
tmpvol=(uint64_t)v.fadeout_volume; /* max 1024 - 10 bits */
|
||||||
tmpvol*=(uint64_t)v.channel_volume; /* * max 64 - 6 bits */
|
tmpvol*=(uint64_t)v.channel_volume; /* * max 64 - 6 bits */
|
||||||
|
@ -341,6 +352,7 @@ void CPPlayer::update_mixer() {
|
||||||
|
|
||||||
v.total_volume=tmpvol;
|
v.total_volume=tmpvol;
|
||||||
|
|
||||||
|
|
||||||
if ((v.master_channel!=NULL) && song->is_channel_mute( v.master_channel_index ) && !v.master_channel->reserved) {
|
if ((v.master_channel!=NULL) && song->is_channel_mute( v.master_channel_index ) && !v.master_channel->reserved) {
|
||||||
|
|
||||||
mixer->set_voice_volume(i,0);
|
mixer->set_voice_volume(i,0);
|
||||||
|
@ -518,7 +530,7 @@ void CPPlayer::update_mixer() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
switch(song->get_reverb_mode()) {
|
switch(song->get_reverb_mode()) {
|
||||||
|
|
||||||
case CPSong::REVERB_MODE_ROOM: {
|
case CPSong::REVERB_MODE_ROOM: {
|
||||||
|
@ -569,6 +581,8 @@ void CPPlayer::update_mixer() {
|
||||||
}
|
}
|
||||||
|
|
||||||
mixer->set_chorus_params(song->get_chorus_delay_ms(),song->get_chorus_separation_ms(),song->get_chorus_depth_ms10(),song->get_chorus_speed_hz10() );
|
mixer->set_chorus_params(song->get_chorus_delay_ms(),song->get_chorus_separation_ms(),song->get_chorus_depth_ms10(),song->get_chorus_speed_hz10() );
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -372,6 +372,7 @@ void CPMixerImpl::set_voice_panning(int p_voice_index,int p_pan) {
|
||||||
|
|
||||||
void CPMixerImpl::set_voice_volume(int p_voice_index,int p_vol) {
|
void CPMixerImpl::set_voice_volume(int p_voice_index,int p_vol) {
|
||||||
|
|
||||||
|
|
||||||
Voice &v=voices[p_voice_index];
|
Voice &v=voices[p_voice_index];
|
||||||
ERR_FAIL_COND(v.channel==AudioMixer::INVALID_CHANNEL);
|
ERR_FAIL_COND(v.channel==AudioMixer::INVALID_CHANNEL);
|
||||||
float vol = p_vol/512.0;
|
float vol = p_vol/512.0;
|
||||||
|
@ -488,8 +489,9 @@ void CPMixerImpl::process_usecs(int p_usec,float p_volume,float p_pitch_scale,fl
|
||||||
|
|
||||||
p_usec-=callback_timeout;
|
p_usec-=callback_timeout;
|
||||||
callback_timeout=0;
|
callback_timeout=0;
|
||||||
if (callback)
|
if (callback) {
|
||||||
callback(userdata);
|
callback(userdata);
|
||||||
|
}
|
||||||
callback_timeout=callback_interval*(1.0/p_tempo_scale);
|
callback_timeout=callback_interval*(1.0/p_tempo_scale);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
|
@ -704,6 +706,9 @@ float EventStreamPlaybackChibi::get_tempo_scale() const{
|
||||||
|
|
||||||
void EventStreamPlaybackChibi::set_channel_volume(int p_channel,float p_volume) {
|
void EventStreamPlaybackChibi::set_channel_volume(int p_channel,float p_volume) {
|
||||||
|
|
||||||
|
|
||||||
|
if (p_channel>=64)
|
||||||
|
return;
|
||||||
player->set_channel_global_volume(p_channel,p_volume*256);
|
player->set_channel_global_volume(p_channel,p_volume*256);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -784,28 +789,33 @@ RES ResourceFormatLoaderChibi::load(const String &p_path,const String& p_origina
|
||||||
|
|
||||||
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
||||||
CPLoader_IT loader(&f);
|
CPLoader_IT loader(&f);
|
||||||
loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
CPLoader::Error err = loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
||||||
|
ERR_FAIL_COND_V(err!=CPLoader::FILE_OK,RES());
|
||||||
|
|
||||||
return esc;
|
return esc;
|
||||||
|
|
||||||
} else if (el=="xm") {
|
} else if (el=="xm") {
|
||||||
|
|
||||||
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
||||||
CPLoader_XM loader(&f);
|
CPLoader_XM loader(&f);
|
||||||
loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
CPLoader::Error err=loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
||||||
|
ERR_FAIL_COND_V(err!=CPLoader::FILE_OK,RES());
|
||||||
return esc;
|
return esc;
|
||||||
|
|
||||||
} else if (el=="s3m") {
|
} else if (el=="s3m") {
|
||||||
|
|
||||||
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
||||||
CPLoader_S3M loader(&f);
|
CPLoader_S3M loader(&f);
|
||||||
loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
CPLoader::Error err=loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
||||||
|
ERR_FAIL_COND_V(err!=CPLoader::FILE_OK,RES());
|
||||||
return esc;
|
return esc;
|
||||||
|
|
||||||
} else if (el=="mod") {
|
} else if (el=="mod") {
|
||||||
|
|
||||||
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
Ref<EventStreamChibi> esc( memnew( EventStreamChibi ) );
|
||||||
CPLoader_MOD loader(&f);
|
CPLoader_MOD loader(&f);
|
||||||
loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
CPLoader::Error err=loader.load_song(p_path.utf8().get_data(),&esc->song,false);
|
||||||
|
ERR_FAIL_COND_V(err!=CPLoader::FILE_OK,RES());
|
||||||
return esc;
|
return esc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1956,7 +1956,7 @@ int RasterizerGLES1::mesh_get_surface_count(RID p_mesh) const {
|
||||||
return mesh->surfaces.size();
|
return mesh->surfaces.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
AABB RasterizerGLES1::mesh_get_aabb(RID p_mesh) const {
|
AABB RasterizerGLES1::mesh_get_aabb(RID p_mesh,RID p_skeleton) const {
|
||||||
|
|
||||||
Mesh *mesh = mesh_owner.get( p_mesh );
|
Mesh *mesh = mesh_owner.get( p_mesh );
|
||||||
ERR_FAIL_COND_V(!mesh,AABB());
|
ERR_FAIL_COND_V(!mesh,AABB());
|
||||||
|
|
|
@ -939,7 +939,7 @@ public:
|
||||||
virtual void mesh_remove_surface(RID p_mesh,int p_index);
|
virtual void mesh_remove_surface(RID p_mesh,int p_index);
|
||||||
virtual int mesh_get_surface_count(RID p_mesh) const;
|
virtual int mesh_get_surface_count(RID p_mesh) const;
|
||||||
|
|
||||||
virtual AABB mesh_get_aabb(RID p_mesh) const;
|
virtual AABB mesh_get_aabb(RID p_mesh,RID p_skeleton=RID()) const;
|
||||||
|
|
||||||
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb);
|
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb);
|
||||||
virtual AABB mesh_get_custom_aabb(RID p_mesh) const;
|
virtual AABB mesh_get_custom_aabb(RID p_mesh) const;
|
||||||
|
|
|
@ -1746,6 +1746,9 @@ void RasterizerGLES2::mesh_add_surface(RID p_mesh,VS::PrimitiveType p_primitive,
|
||||||
iaw = index_array_pre_vbo.write();
|
iaw = index_array_pre_vbo.write();
|
||||||
index_array_ptr=iaw.ptr();
|
index_array_ptr=iaw.ptr();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_surface_set_arrays(surface,array_ptr,index_array_ptr,p_arrays,true);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
surface->array_local = (uint8_t*)memalloc(surface->array_len*surface->stride);
|
surface->array_local = (uint8_t*)memalloc(surface->array_len*surface->stride);
|
||||||
|
@ -1755,6 +1758,8 @@ void RasterizerGLES2::mesh_add_surface(RID p_mesh,VS::PrimitiveType p_primitive,
|
||||||
index_array_ptr=(uint8_t*)surface->index_array_local;
|
index_array_ptr=(uint8_t*)surface->index_array_local;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_surface_set_arrays(surface,array_ptr,index_array_ptr,p_arrays,true);
|
||||||
|
|
||||||
if (mesh->morph_target_count) {
|
if (mesh->morph_target_count) {
|
||||||
|
|
||||||
surface->morph_targets_local = memnew_arr(Surface::MorphTarget,mesh->morph_target_count);
|
surface->morph_targets_local = memnew_arr(Surface::MorphTarget,mesh->morph_target_count);
|
||||||
|
@ -1769,7 +1774,6 @@ void RasterizerGLES2::mesh_add_surface(RID p_mesh,VS::PrimitiveType p_primitive,
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
_surface_set_arrays(surface,array_ptr,index_array_ptr,p_arrays,true);
|
|
||||||
|
|
||||||
|
|
||||||
/* create buffers!! */
|
/* create buffers!! */
|
||||||
|
@ -2167,6 +2171,67 @@ Error RasterizerGLES2::_surface_set_arrays(Surface *p_surface, uint8_t *p_mem,ui
|
||||||
p_surface->configured_format|=(1<<ai);
|
p_surface->configured_format|=(1<<ai);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (p_surface->format&VS::ARRAY_FORMAT_BONES) {
|
||||||
|
//create AABBs for each detected bone
|
||||||
|
int total_bones = p_surface->max_bone+1;
|
||||||
|
if (p_main) {
|
||||||
|
p_surface->skeleton_bone_aabb.resize(total_bones);
|
||||||
|
p_surface->skeleton_bone_used.resize(total_bones);
|
||||||
|
for(int i=0;i<total_bones;i++)
|
||||||
|
p_surface->skeleton_bone_used[i]=false;
|
||||||
|
}
|
||||||
|
DVector<Vector3> vertices = p_arrays[VS::ARRAY_VERTEX];
|
||||||
|
DVector<int> bones = p_arrays[VS::ARRAY_BONES];
|
||||||
|
DVector<float> weights = p_arrays[VS::ARRAY_WEIGHTS];
|
||||||
|
|
||||||
|
bool any_valid=false;
|
||||||
|
|
||||||
|
if (vertices.size() && bones.size()==vertices.size()*4 && weights.size()==bones.size()) {
|
||||||
|
//print_line("MAKING SKELETHONG");
|
||||||
|
int vs = vertices.size();
|
||||||
|
DVector<Vector3>::Read rv =vertices.read();
|
||||||
|
DVector<int>::Read rb=bones.read();
|
||||||
|
DVector<float>::Read rw=weights.read();
|
||||||
|
|
||||||
|
Vector<bool> first;
|
||||||
|
first.resize(total_bones);
|
||||||
|
for(int i=0;i<total_bones;i++) {
|
||||||
|
first[i]=p_main;
|
||||||
|
}
|
||||||
|
AABB *bptr = p_surface->skeleton_bone_aabb.ptr();
|
||||||
|
bool *fptr=first.ptr();
|
||||||
|
bool *usedptr=p_surface->skeleton_bone_used.ptr();
|
||||||
|
|
||||||
|
for(int i=0;i<vs;i++) {
|
||||||
|
|
||||||
|
Vector3 v = rv[i];
|
||||||
|
for(int j=0;j<4;j++) {
|
||||||
|
|
||||||
|
int idx = rb[i*4+j];
|
||||||
|
float w = rw[i*4+j];
|
||||||
|
if (w==0)
|
||||||
|
continue;//break;
|
||||||
|
ERR_FAIL_INDEX_V(idx,total_bones,ERR_INVALID_DATA);
|
||||||
|
|
||||||
|
if (fptr[idx]) {
|
||||||
|
bptr[idx].pos=v;
|
||||||
|
fptr[idx]=false;
|
||||||
|
any_valid=true;
|
||||||
|
} else {
|
||||||
|
bptr[idx].expand_to(v);
|
||||||
|
}
|
||||||
|
usedptr[idx]=true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (p_main && !any_valid) {
|
||||||
|
|
||||||
|
p_surface->skeleton_bone_aabb.clear();
|
||||||
|
p_surface->skeleton_bone_used.clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return OK;
|
return OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2343,7 +2408,7 @@ int RasterizerGLES2::mesh_get_surface_count(RID p_mesh) const {
|
||||||
return mesh->surfaces.size();
|
return mesh->surfaces.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
AABB RasterizerGLES2::mesh_get_aabb(RID p_mesh) const {
|
AABB RasterizerGLES2::mesh_get_aabb(RID p_mesh, RID p_skeleton) const {
|
||||||
|
|
||||||
Mesh *mesh = mesh_owner.get( p_mesh );
|
Mesh *mesh = mesh_owner.get( p_mesh );
|
||||||
ERR_FAIL_COND_V(!mesh,AABB());
|
ERR_FAIL_COND_V(!mesh,AABB());
|
||||||
|
@ -2351,14 +2416,62 @@ AABB RasterizerGLES2::mesh_get_aabb(RID p_mesh) const {
|
||||||
if (mesh->custom_aabb!=AABB())
|
if (mesh->custom_aabb!=AABB())
|
||||||
return mesh->custom_aabb;
|
return mesh->custom_aabb;
|
||||||
|
|
||||||
|
Skeleton *sk=NULL;
|
||||||
|
if (p_skeleton.is_valid())
|
||||||
|
sk=skeleton_owner.get(p_skeleton);
|
||||||
|
|
||||||
AABB aabb;
|
AABB aabb;
|
||||||
|
if (sk) {
|
||||||
|
|
||||||
for (int i=0;i<mesh->surfaces.size();i++) {
|
|
||||||
|
|
||||||
if (i==0)
|
for (int i=0;i<mesh->surfaces.size();i++) {
|
||||||
aabb=mesh->surfaces[i]->aabb;
|
|
||||||
else
|
AABB laabb;
|
||||||
aabb.merge_with(mesh->surfaces[i]->aabb);
|
if (mesh->surfaces[i]->format&VS::ARRAY_FORMAT_BONES && mesh->surfaces[i]->skeleton_bone_aabb.size()) {
|
||||||
|
|
||||||
|
|
||||||
|
int bs = mesh->surfaces[i]->skeleton_bone_aabb.size();
|
||||||
|
const AABB *skbones = mesh->surfaces[i]->skeleton_bone_aabb.ptr();
|
||||||
|
const bool *skused = mesh->surfaces[i]->skeleton_bone_used.ptr();
|
||||||
|
|
||||||
|
int sbs = sk->bones.size();
|
||||||
|
ERR_CONTINUE(bs>sbs);
|
||||||
|
Skeleton::Bone *skb = sk->bones.ptr();
|
||||||
|
|
||||||
|
bool first=true;
|
||||||
|
for(int j=0;j<bs;j++) {
|
||||||
|
|
||||||
|
if (!skused[j])
|
||||||
|
continue;
|
||||||
|
AABB baabb = skb[ j ].transform_aabb ( skbones[j] );
|
||||||
|
if (first) {
|
||||||
|
laabb=baabb;
|
||||||
|
first=false;
|
||||||
|
} else {
|
||||||
|
laabb.merge_with(baabb);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
|
||||||
|
laabb=mesh->surfaces[i]->aabb;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (i==0)
|
||||||
|
aabb=laabb;
|
||||||
|
else
|
||||||
|
aabb.merge_with(laabb);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
|
||||||
|
for (int i=0;i<mesh->surfaces.size();i++) {
|
||||||
|
|
||||||
|
if (i==0)
|
||||||
|
aabb=mesh->surfaces[i]->aabb;
|
||||||
|
else
|
||||||
|
aabb.merge_with(mesh->surfaces[i]->aabb);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return aabb;
|
return aabb;
|
||||||
|
|
|
@ -312,6 +312,8 @@ class RasterizerGLES2 : public Rasterizer {
|
||||||
// no support for the above, array in localmem.
|
// no support for the above, array in localmem.
|
||||||
uint8_t *array_local;
|
uint8_t *array_local;
|
||||||
uint8_t *index_array_local;
|
uint8_t *index_array_local;
|
||||||
|
Vector<AABB> skeleton_bone_aabb;
|
||||||
|
Vector<bool> skeleton_bone_used;
|
||||||
|
|
||||||
//bool packed;
|
//bool packed;
|
||||||
|
|
||||||
|
@ -547,6 +549,42 @@ class RasterizerGLES2 : public Rasterizer {
|
||||||
r_dst[1]+=((mtx[0][1]*p_src[0] ) + ( mtx[1][1]*p_src[1] ) + ( mtx[2][1]*p_src[2] ) )*p_weight;
|
r_dst[1]+=((mtx[0][1]*p_src[0] ) + ( mtx[1][1]*p_src[1] ) + ( mtx[2][1]*p_src[2] ) )*p_weight;
|
||||||
r_dst[2]+=((mtx[0][2]*p_src[0] ) + ( mtx[1][2]*p_src[1] ) + ( mtx[2][2]*p_src[2] ) )*p_weight;
|
r_dst[2]+=((mtx[0][2]*p_src[0] ) + ( mtx[1][2]*p_src[1] ) + ( mtx[2][2]*p_src[2] ) )*p_weight;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_ALWAYS_INLINE_ AABB transform_aabb(const AABB& p_aabb) const {
|
||||||
|
|
||||||
|
float vertices[8][3]={
|
||||||
|
{p_aabb.pos.x+p_aabb.size.x, p_aabb.pos.y+p_aabb.size.y, p_aabb.pos.z+p_aabb.size.z},
|
||||||
|
{p_aabb.pos.x+p_aabb.size.x, p_aabb.pos.y+p_aabb.size.y, p_aabb.pos.z},
|
||||||
|
{p_aabb.pos.x+p_aabb.size.x, p_aabb.pos.y, p_aabb.pos.z+p_aabb.size.z},
|
||||||
|
{p_aabb.pos.x+p_aabb.size.x, p_aabb.pos.y, p_aabb.pos.z},
|
||||||
|
{p_aabb.pos.x, p_aabb.pos.y+p_aabb.size.y, p_aabb.pos.z+p_aabb.size.z},
|
||||||
|
{p_aabb.pos.x, p_aabb.pos.y+p_aabb.size.y, p_aabb.pos.z},
|
||||||
|
{p_aabb.pos.x, p_aabb.pos.y, p_aabb.pos.z+p_aabb.size.z},
|
||||||
|
{p_aabb.pos.x, p_aabb.pos.y, p_aabb.pos.z}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
AABB ret;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
for (int i=0;i<8;i++) {
|
||||||
|
|
||||||
|
Vector3 xv(
|
||||||
|
|
||||||
|
((mtx[0][0]*vertices[i][0] ) + ( mtx[1][0]*vertices[i][1] ) + ( mtx[2][0]*vertices[i][2] ) + mtx[3][0] ),
|
||||||
|
((mtx[0][1]*vertices[i][0] ) + ( mtx[1][1]*vertices[i][1] ) + ( mtx[2][1]*vertices[i][2] ) + mtx[3][1] ),
|
||||||
|
((mtx[0][2]*vertices[i][0] ) + ( mtx[1][2]*vertices[i][1] ) + ( mtx[2][2]*vertices[i][2] ) + mtx[3][2] )
|
||||||
|
);
|
||||||
|
|
||||||
|
if (i==0)
|
||||||
|
ret.pos=xv;
|
||||||
|
else
|
||||||
|
ret.expand_to(xv);
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
GLuint tex_id;
|
GLuint tex_id;
|
||||||
|
@ -1242,7 +1280,7 @@ public:
|
||||||
virtual void mesh_remove_surface(RID p_mesh,int p_index);
|
virtual void mesh_remove_surface(RID p_mesh,int p_index);
|
||||||
virtual int mesh_get_surface_count(RID p_mesh) const;
|
virtual int mesh_get_surface_count(RID p_mesh) const;
|
||||||
|
|
||||||
virtual AABB mesh_get_aabb(RID p_mesh) const;
|
virtual AABB mesh_get_aabb(RID p_mesh,RID p_skeleton=RID()) const;
|
||||||
|
|
||||||
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb);
|
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb);
|
||||||
virtual AABB mesh_get_custom_aabb(RID p_mesh) const;
|
virtual AABB mesh_get_custom_aabb(RID p_mesh) const;
|
||||||
|
|
|
@ -76,8 +76,9 @@ Ref<EventStream> EventPlayer::get_stream() const {
|
||||||
void EventPlayer::play() {
|
void EventPlayer::play() {
|
||||||
|
|
||||||
ERR_FAIL_COND(!is_inside_scene());
|
ERR_FAIL_COND(!is_inside_scene());
|
||||||
if (playback.is_null())
|
if (playback.is_null()) {
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
if (playback->is_playing()) {
|
if (playback->is_playing()) {
|
||||||
AudioServer::get_singleton()->lock();
|
AudioServer::get_singleton()->lock();
|
||||||
stop();
|
stop();
|
||||||
|
|
|
@ -32,10 +32,12 @@
|
||||||
Error EventStreamPlayback::play() {
|
Error EventStreamPlayback::play() {
|
||||||
if (stream.is_valid())
|
if (stream.is_valid())
|
||||||
stop();
|
stop();
|
||||||
|
|
||||||
Error err = _play();
|
Error err = _play();
|
||||||
if (err)
|
if (err)
|
||||||
return err;
|
return err;
|
||||||
|
|
||||||
|
|
||||||
playing=true;
|
playing=true;
|
||||||
AudioServer::get_singleton()->stream_set_active(stream,true);
|
AudioServer::get_singleton()->stream_set_active(stream,true);
|
||||||
|
|
||||||
|
|
|
@ -369,7 +369,17 @@ void AudioMixerSW::mix_channel(Channel& c) {
|
||||||
AS::SampleLoopFormat loop_format=sample_manager->sample_get_loop_format(c.sample);
|
AS::SampleLoopFormat loop_format=sample_manager->sample_get_loop_format(c.sample);
|
||||||
AS::SampleFormat format=sample_manager->sample_get_format(c.sample);
|
AS::SampleFormat format=sample_manager->sample_get_format(c.sample);
|
||||||
|
|
||||||
bool use_fx=fx_enabled && (c.mix.old_reverb_vol || c.mix.reverb_vol || c.mix.old_chorus_vol || c.mix.chorus_vol );
|
bool use_fx=false;
|
||||||
|
|
||||||
|
if (fx_enabled) {
|
||||||
|
|
||||||
|
for(int i=0;i<mix_channels;i++) {
|
||||||
|
if (c.mix.old_reverb_vol[i] || c.mix.reverb_vol[i] || c.mix.old_chorus_vol[i] || c.mix.chorus_vol[i] ) {
|
||||||
|
use_fx=true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* audio data */
|
/* audio data */
|
||||||
|
|
||||||
|
@ -547,8 +557,8 @@ void AudioMixerSW::mix_channel(Channel& c) {
|
||||||
}
|
}
|
||||||
|
|
||||||
c.mix.offset+=rstate.pos;
|
c.mix.offset+=rstate.pos;
|
||||||
dst_buff+=target*2;
|
dst_buff+=target*mix_channels;
|
||||||
|
rstate.reverb_buffer+=target*mix_channels;
|
||||||
}
|
}
|
||||||
|
|
||||||
c.filter.old_coefs=c.filter.coefs;
|
c.filter.old_coefs=c.filter.coefs;
|
||||||
|
|
|
@ -502,6 +502,7 @@ void AudioServerSW::voice_set_reverb(RID p_voice, ReverbRoomType p_room_type, fl
|
||||||
cmd.voice=p_voice;
|
cmd.voice=p_voice;
|
||||||
cmd.reverb.room=p_room_type;
|
cmd.reverb.room=p_room_type;
|
||||||
cmd.reverb.send=p_reverb;
|
cmd.reverb.send=p_reverb;
|
||||||
|
|
||||||
voice_rb.push_command(cmd);
|
voice_rb.push_command(cmd);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -146,6 +146,38 @@ void SampleManagerMallocSW::sample_set_data(RID p_sample, const DVector<uint8_t>
|
||||||
dst[i]=src[i];
|
dst[i]=src[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
switch(s->format) {
|
||||||
|
|
||||||
|
case AS::SAMPLE_FORMAT_PCM8: {
|
||||||
|
|
||||||
|
if (s->stereo) {
|
||||||
|
dst[s->length]=dst[s->length-2];
|
||||||
|
dst[s->length+1]=dst[s->length-1];
|
||||||
|
} else {
|
||||||
|
|
||||||
|
dst[s->length]=dst[s->length-1];
|
||||||
|
}
|
||||||
|
|
||||||
|
} break;
|
||||||
|
case AS::SAMPLE_FORMAT_PCM16: {
|
||||||
|
|
||||||
|
if (s->stereo) {
|
||||||
|
dst[s->length]=dst[s->length-4];
|
||||||
|
dst[s->length+1]=dst[s->length-3];
|
||||||
|
dst[s->length+2]=dst[s->length-2];
|
||||||
|
dst[s->length+3]=dst[s->length-1];
|
||||||
|
} else {
|
||||||
|
|
||||||
|
dst[s->length]=dst[s->length-2];
|
||||||
|
dst[s->length+1]=dst[s->length-1];
|
||||||
|
}
|
||||||
|
|
||||||
|
} break;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const DVector<uint8_t> SampleManagerMallocSW::sample_get_data(RID p_sample) const {
|
const DVector<uint8_t> SampleManagerMallocSW::sample_get_data(RID p_sample) const {
|
||||||
|
|
|
@ -275,7 +275,7 @@ public:
|
||||||
virtual void mesh_remove_surface(RID p_mesh,int p_index)=0;
|
virtual void mesh_remove_surface(RID p_mesh,int p_index)=0;
|
||||||
virtual int mesh_get_surface_count(RID p_mesh) const=0;
|
virtual int mesh_get_surface_count(RID p_mesh) const=0;
|
||||||
|
|
||||||
virtual AABB mesh_get_aabb(RID p_mesh) const=0;
|
virtual AABB mesh_get_aabb(RID p_mesh,RID p_skeleton=RID()) const=0;
|
||||||
|
|
||||||
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb)=0;
|
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb)=0;
|
||||||
virtual AABB mesh_get_custom_aabb(RID p_mesh) const=0;
|
virtual AABB mesh_get_custom_aabb(RID p_mesh) const=0;
|
||||||
|
|
|
@ -561,7 +561,7 @@ int RasterizerDummy::mesh_get_surface_count(RID p_mesh) const {
|
||||||
return mesh->surfaces.size();
|
return mesh->surfaces.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
AABB RasterizerDummy::mesh_get_aabb(RID p_mesh) const {
|
AABB RasterizerDummy::mesh_get_aabb(RID p_mesh,RID p_skeleton) const {
|
||||||
|
|
||||||
Mesh *mesh = mesh_owner.get( p_mesh );
|
Mesh *mesh = mesh_owner.get( p_mesh );
|
||||||
ERR_FAIL_COND_V(!mesh,AABB());
|
ERR_FAIL_COND_V(!mesh,AABB());
|
||||||
|
|
|
@ -471,7 +471,7 @@ public:
|
||||||
virtual void mesh_remove_surface(RID p_mesh,int p_index);
|
virtual void mesh_remove_surface(RID p_mesh,int p_index);
|
||||||
virtual int mesh_get_surface_count(RID p_mesh) const;
|
virtual int mesh_get_surface_count(RID p_mesh) const;
|
||||||
|
|
||||||
virtual AABB mesh_get_aabb(RID p_mesh) const;
|
virtual AABB mesh_get_aabb(RID p_mesh,RID p_skeleton=RID()) const;
|
||||||
|
|
||||||
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb);
|
virtual void mesh_set_custom_aabb(RID p_mesh,const AABB& p_aabb);
|
||||||
virtual AABB mesh_get_custom_aabb(RID p_mesh) const;
|
virtual AABB mesh_get_custom_aabb(RID p_mesh) const;
|
||||||
|
|
|
@ -888,8 +888,17 @@ int VisualServerRaster::skeleton_get_bone_count(RID p_skeleton) const {
|
||||||
|
|
||||||
void VisualServerRaster::skeleton_bone_set_transform(RID p_skeleton,int p_bone, const Transform& p_transform) {
|
void VisualServerRaster::skeleton_bone_set_transform(RID p_skeleton,int p_bone, const Transform& p_transform) {
|
||||||
VS_CHANGED;
|
VS_CHANGED;
|
||||||
return rasterizer->skeleton_bone_set_transform(p_skeleton,p_bone,p_transform);
|
rasterizer->skeleton_bone_set_transform(p_skeleton,p_bone,p_transform);
|
||||||
|
|
||||||
|
Map< RID, Set<Instance*> >::Element *E=skeleton_dependency_map.find(p_skeleton);
|
||||||
|
|
||||||
|
if (E) {
|
||||||
|
//detach skeletons
|
||||||
|
for (Set<Instance*>::Element *F=E->get().front();F;F=F->next()) {
|
||||||
|
|
||||||
|
_instance_queue_update( F->get() , true);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Transform VisualServerRaster::skeleton_bone_get_transform(RID p_skeleton,int p_bone) {
|
Transform VisualServerRaster::skeleton_bone_get_transform(RID p_skeleton,int p_bone) {
|
||||||
|
@ -2113,8 +2122,17 @@ void VisualServerRaster::instance_attach_skeleton(RID p_instance,RID p_skeleton)
|
||||||
VS_CHANGED;
|
VS_CHANGED;
|
||||||
Instance *instance = instance_owner.get( p_instance );
|
Instance *instance = instance_owner.get( p_instance );
|
||||||
ERR_FAIL_COND( !instance );
|
ERR_FAIL_COND( !instance );
|
||||||
|
|
||||||
|
if (instance->data.skeleton.is_valid()) {
|
||||||
|
skeleton_dependency_map[instance->data.skeleton].erase(instance);
|
||||||
|
}
|
||||||
|
|
||||||
instance->data.skeleton=p_skeleton;
|
instance->data.skeleton=p_skeleton;
|
||||||
|
|
||||||
|
if (instance->data.skeleton.is_valid()) {
|
||||||
|
skeleton_dependency_map[instance->data.skeleton].insert(instance);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
RID VisualServerRaster::instance_get_skeleton(RID p_instance) const {
|
RID VisualServerRaster::instance_get_skeleton(RID p_instance) const {
|
||||||
|
@ -2773,7 +2791,7 @@ void VisualServerRaster::_update_instance_aabb(Instance *p_instance) {
|
||||||
} break;
|
} break;
|
||||||
case VisualServer::INSTANCE_MESH: {
|
case VisualServer::INSTANCE_MESH: {
|
||||||
|
|
||||||
new_aabb = rasterizer->mesh_get_aabb(p_instance->base_rid);
|
new_aabb = rasterizer->mesh_get_aabb(p_instance->base_rid,p_instance->data.skeleton);
|
||||||
|
|
||||||
} break;
|
} break;
|
||||||
case VisualServer::INSTANCE_MULTIMESH: {
|
case VisualServer::INSTANCE_MULTIMESH: {
|
||||||
|
@ -3673,10 +3691,23 @@ void VisualServerRaster::free( RID p_rid ) {
|
||||||
|
|
||||||
VS_CHANGED;
|
VS_CHANGED;
|
||||||
|
|
||||||
if (rasterizer->is_texture(p_rid) || rasterizer->is_material(p_rid) || rasterizer->is_skeleton(p_rid) || rasterizer->is_shader(p_rid)) {
|
if (rasterizer->is_texture(p_rid) || rasterizer->is_material(p_rid) || rasterizer->is_shader(p_rid)) {
|
||||||
|
|
||||||
rasterizer->free(p_rid);
|
rasterizer->free(p_rid);
|
||||||
|
} else if (rasterizer->is_skeleton(p_rid)) {
|
||||||
|
|
||||||
|
Map< RID, Set<Instance*> >::Element *E=skeleton_dependency_map.find(p_rid);
|
||||||
|
|
||||||
|
if (E) {
|
||||||
|
//detach skeletons
|
||||||
|
for (Set<Instance*>::Element *F=E->get().front();F;F=F->next()) {
|
||||||
|
|
||||||
|
F->get()->data.skeleton=RID();
|
||||||
|
}
|
||||||
|
skeleton_dependency_map.erase(E);
|
||||||
|
}
|
||||||
|
|
||||||
|
rasterizer->free(p_rid);
|
||||||
} else if (rasterizer->is_mesh(p_rid) || rasterizer->is_multimesh(p_rid) || rasterizer->is_light(p_rid) || rasterizer->is_particles(p_rid) ) {
|
} else if (rasterizer->is_mesh(p_rid) || rasterizer->is_multimesh(p_rid) || rasterizer->is_light(p_rid) || rasterizer->is_particles(p_rid) ) {
|
||||||
//delete the resource
|
//delete the resource
|
||||||
|
|
||||||
|
@ -3763,6 +3794,8 @@ void VisualServerRaster::free( RID p_rid ) {
|
||||||
instance_set_scenario(p_rid,RID());
|
instance_set_scenario(p_rid,RID());
|
||||||
instance_geometry_set_baked_light(p_rid,RID());
|
instance_geometry_set_baked_light(p_rid,RID());
|
||||||
instance_set_base(p_rid,RID());
|
instance_set_base(p_rid,RID());
|
||||||
|
if (instance->data.skeleton.is_valid())
|
||||||
|
instance_attach_skeleton(p_rid,RID());
|
||||||
|
|
||||||
instance_owner.free(p_rid);
|
instance_owner.free(p_rid);
|
||||||
memdelete(instance);
|
memdelete(instance);
|
||||||
|
|
|
@ -610,7 +610,7 @@ class VisualServerRaster : public VisualServer {
|
||||||
void _portal_disconnect(Instance *p_portal,bool p_cleanup=false);
|
void _portal_disconnect(Instance *p_portal,bool p_cleanup=false);
|
||||||
void _portal_attempt_connect(Instance *p_portal);
|
void _portal_attempt_connect(Instance *p_portal);
|
||||||
void _dependency_queue_update(RID p_rid,bool p_update_aabb=false);
|
void _dependency_queue_update(RID p_rid,bool p_update_aabb=false);
|
||||||
void _instance_queue_update(Instance *p_instance,bool p_update_aabb=false);
|
_FORCE_INLINE_ void _instance_queue_update(Instance *p_instance,bool p_update_aabb=false);
|
||||||
void _update_instances();
|
void _update_instances();
|
||||||
void _update_instance_aabb(Instance *p_instance);
|
void _update_instance_aabb(Instance *p_instance);
|
||||||
void _update_instance(Instance *p_instance);
|
void _update_instance(Instance *p_instance);
|
||||||
|
@ -640,7 +640,8 @@ class VisualServerRaster : public VisualServer {
|
||||||
mutable RID_Owner<CanvasItem> canvas_item_owner;
|
mutable RID_Owner<CanvasItem> canvas_item_owner;
|
||||||
|
|
||||||
Map< RID, Set<RID> > instance_dependency_map;
|
Map< RID, Set<RID> > instance_dependency_map;
|
||||||
|
Map< RID, Set<Instance*> > skeleton_dependency_map;
|
||||||
|
|
||||||
|
|
||||||
ViewportRect viewport_rect;
|
ViewportRect viewport_rect;
|
||||||
_FORCE_INLINE_ void _instance_draw(Instance *p_instance);
|
_FORCE_INLINE_ void _instance_draw(Instance *p_instance);
|
||||||
|
|
Loading…
Reference in a new issue