Skip to content

Commit

Permalink
make allpass filter radius configurable
Browse files Browse the repository at this point in the history
  • Loading branch information
gisogrimm committed Nov 11, 2024
1 parent 64e45c4 commit 2f1e2a9
Show file tree
Hide file tree
Showing 7 changed files with 97 additions and 67 deletions.
8 changes: 5 additions & 3 deletions libtascar/include/fdn.h
Original file line number Diff line number Diff line change
Expand Up @@ -185,7 +185,7 @@ namespace TASCAR {
public:
enum gainmethod_t { original, mean, schroeder };
fdn_t(uint32_t fdnorder, uint32_t maxdelay, bool logdelays, gainmethod_t gm,
bool feedback_);
bool feedback_, std::vector<float> rallpass);
~fdn_t(){};
void set_logdelays(bool ld) { logdelays_ = ld; };
inline void process(std::vector<fdnpath_t>& src, bool use_biquad)
Expand All @@ -196,8 +196,8 @@ namespace TASCAR {
// rotation:
for(auto& path : fdnpath) {
foa_sample_t tmp(path.delayline[path.pos]);
path.reflection.filter(tmp, use_biquad);
path.rotation.rotate(tmp);
path.reflection.filter(tmp, use_biquad);
path.dlout = tmp;
outval += tmp;
}
Expand Down Expand Up @@ -247,8 +247,8 @@ namespace TASCAR {
// rotation:
for(auto& path : fdnpath) {
foa_sample_t tmp(path.delayline[path.pos]);
path.reflection.filter(tmp, use_biquad);
path.rotation.rotate(tmp);
path.reflection.filter(tmp, use_biquad);
path.dlout = tmp;
outval += tmp;
}
Expand Down Expand Up @@ -279,6 +279,8 @@ namespace TASCAR {
reflectionfilter_t prefilt1;
// FDN path:
std::vector<fdnpath_t> fdnpath;
// allpass filter radius, requires four entries:
std::vector<float> rallpass;
};

} // namespace TASCAR
Expand Down
11 changes: 6 additions & 5 deletions libtascar/src/acousticmodel.cc
Original file line number Diff line number Diff line change
Expand Up @@ -260,8 +260,8 @@ uint32_t acoustic_model_t::process(const TASCAR::transport_t& tp)
return 1;
}
} // of visible
} // of layers check
} // of ISM order check
} // of layers check
} // of ISM order check
} else {
delayline.add_chunk(audio);
}
Expand Down Expand Up @@ -631,8 +631,9 @@ void receiver_t::configure()
scatter_handle = create_diffuse_state_data(f_sample, n_fragment);
scatterfilterpath.resize(scatterreflections);
if(scatterreflections > 0) {
scatterfilter = new TASCAR::fdn_t(scatterreflections, (uint32_t)f_sample,
true, TASCAR::fdn_t::mean, false);
scatterfilter =
new TASCAR::fdn_t(scatterreflections, (uint32_t)f_sample, true,
TASCAR::fdn_t::mean, false, {0.0f, 0.0f, 0.0f, 0.0f});
scatterfilter->set_scatterpar(
scatterspread, f_sample * (0.1f * scatterstructuresize / 340.0f),
f_sample * (scatterstructuresize / 340.0f), f_sample,
Expand Down Expand Up @@ -750,7 +751,7 @@ void receiver_t::postproc(std::vector<wave_t>& output)
// path.dlout = x;
++kflt;
}
scatterfilter->process(scatterfilterpath,false);
scatterfilter->process(scatterfilterpath, false);
scatterbuffer->w()[k] = scatterfilter->outval.w;
scatterbuffer->x()[k] = scatterfilter->outval.x;
scatterbuffer->y()[k] = scatterfilter->outval.y;
Expand Down
21 changes: 13 additions & 8 deletions libtascar/src/fdn.cc
Original file line number Diff line number Diff line change
Expand Up @@ -36,14 +36,20 @@ void fdnpath_t::init(uint32_t maxdelay)
};

fdn_t::fdn_t(uint32_t fdnorder, uint32_t maxdelay, bool logdelays,
gainmethod_t gm, bool feedback_)
gainmethod_t gm, bool feedback_, std::vector<float> rallpass_)
: logdelays_(logdelays), fdnorder_(fdnorder), maxdelay_(maxdelay),
feedbackmat(fdnorder_ * fdnorder_), gainmethod(gm), feedback(feedback_)
feedbackmat(fdnorder_ * fdnorder_), gainmethod(gm), feedback(feedback_),
rallpass(rallpass_)
{
if(rallpass.size() != 4u)
throw TASCAR::ErrMsg(
"Allpass filter radius vector requires four entries, received " +
std::to_string(rallpass.size()));
for(auto& v : feedbackmat)
v = 0.0f;
prefilt0.set_allpass(0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f);
prefilt1.set_allpass(0.87f, 0.87f, 0.87f, 0.87f, 0.87f, 0.25f * TASCAR_PIf);
prefilt1.set_allpass(0.87f, rallpass[0], rallpass[1], rallpass[2],
rallpass[3], 0.25f * TASCAR_PIf);
fdnpath.resize(fdnorder);
for(size_t k = 0; k < fdnpath.size(); ++k) {
fdnpath[k].init(maxdelay);
Expand Down Expand Up @@ -85,8 +91,8 @@ void fdn_t::setpar_t60(float az, float daz, float t_min, float t_max, float t60,
uint32_t d((uint32_t)std::max(0.0f, t_));
fdnpath[tap].delay = std::max(2u, std::min(maxdelay_ - 1u, d));
fdnpath[tap].reflection.set_allpass(
0.87f * (float)tap / ((float)fdnorder_ - 1.0f), 0.87f, 0.88f, 0.89f,
0.9f,
0.87f * (float)tap / ((float)fdnorder_ - 1.0f), rallpass[0],
rallpass[1], rallpass[2], rallpass[3],
TASCAR_PIf * (0.001f + 0.25f * (float)tap / ((float)fdnorder_ - 1.0f)));
// eta[k] = 0.87f * (float)k / ((float)d1 - 1.0f);
t_mean += (float)(fdnpath[tap].delay);
Expand Down Expand Up @@ -182,10 +188,9 @@ void fdn_t::set_scatterpar(float daz, float t_min, float t_max, float t60,
uint32_t d((uint32_t)std::max(0.0f, t_));
fdnpath[tap].delay = std::max(2u, std::min(maxdelay_ - 1u, d));
fdnpath[tap].reflection.set_allpass(
0.87f * (float)tap / ((float)fdnorder_ - 1.0f), 0.87f, 0.88f, 0.89f,
0.9f,
0.87f * (float)tap / ((float)fdnorder_ - 1.0f), rallpass[0],
rallpass[1], rallpass[2], rallpass[3],
TASCAR_PIf * (0.001f + 0.25f * (float)tap / ((float)fdnorder_ - 1.0f)));
// eta[k] = 0.87f * (float)k / ((float)d1 - 1.0f);
t_mean += (float)(fdnpath[tap].delay);
}
// if feed forward model, then truncate delays:
Expand Down
15 changes: 11 additions & 4 deletions plugins/src/receivermod_simplefdn.cc
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ class simplefdn_vars_t : public TASCAR::receivermod_base_t {
bool use_lowcut = false;
bool truncate_forward = false;
bool use_biquad_allpass = false;
std::vector<float> rallpass = {0.96f, 0.95f, 0.951f, 0.93f};
};

simplefdn_vars_t::simplefdn_vars_t(tsccfg::node_t xmlsrc)
Expand Down Expand Up @@ -101,6 +102,12 @@ simplefdn_vars_t::simplefdn_vars_t(tsccfg::node_t xmlsrc)
GET_ATTRIBUTE_BOOL(
use_biquad_allpass,
"Use biquad allpass filters instead of first order filters");
GET_ATTRIBUTE(rallpass, "[0,1]",
"Allpass filter radius vector (requires four entries)");
if(rallpass.size() != 4u)
throw TASCAR::ErrMsg(
"Allpass filter radius vector requires four entries, received " +
std::to_string(rallpass.size()));
}

simplefdn_vars_t::~simplefdn_vars_t() {}
Expand Down Expand Up @@ -264,14 +271,14 @@ void simplefdn_t::configure()
if(feedback_delay_network)
delete feedback_delay_network;
srcpath.resize(fdnorder);
feedback_delay_network =
new TASCAR::fdn_t(fdnorder, (uint32_t)f_sample, logdelays, gm, true);
feedback_delay_network = new TASCAR::fdn_t(fdnorder, (uint32_t)f_sample,
logdelays, gm, true, rallpass);
for(auto& pff : feedforward_delay_network)
delete pff;
feedforward_delay_network.clear();
for(uint32_t k = 0; k < forwardstages; ++k)
feedforward_delay_network.push_back(
new TASCAR::fdn_t(fdnorder, (uint32_t)f_sample, logdelays, gm, false));
feedforward_delay_network.push_back(new TASCAR::fdn_t(
fdnorder, (uint32_t)f_sample, logdelays, gm, false, rallpass));
if(foa_out)
delete foa_out;
foa_out = new TASCAR::amb1wave_t(n_fragment);
Expand Down
100 changes: 53 additions & 47 deletions test/Makefile
Original file line number Diff line number Diff line change
@@ -1,50 +1,56 @@
TESTS = test_snd_pink_diffuse test_ir1 test_ir2 test_ir3 test_ir4 \
test_ir_proxy_air test_ir_proxy_gain test_ir_proxy_delay \
test_ir_proxy_direction test_ir6_ismminmax test_snd1 \
test_snd_include_sound test_snd2 test_snd4 test_snd3 test_snd5 \
test_pos1 test_pos2 test_pos_trackinterp test_snd_door1 \
test_snd_door2 test_snd_door3 test_pos_door test_snd_layers \
test_snd_rec_amb1h1v test_wav_diffuse test_wav_diffuse_hoa2d \
test_ir_hoa2d_offset test_wav_diffuse_nsp4 test_wav_diffuse_hoa2d4 \
test_wav_diffuse_layerbug test_wav_diffirs test_sndgainramp \
test_sndgainramp2 test_ir_spkcorr test_snd_calib1 test_snd_calib2 \
test_snd_vbap51 test_snd_pink test_snd_sndfile test_snd_sndfile2 \
test_snd_door4 test_snd_roommic test_level_vbap3d test_ir_ortf_0deg \
test_ir_ortf_55deg test_ir_scatter test_ir_noscatter \
test_ir_scatter_ortf test_snd_sourcedir_generic \
test_snd_sourcedir_generic1 test_snd_sourcedir_generic_cardioid \
test_ir_wfs test_ir_wfs_noplanewave test_level_hoa2d_basic \
test_level_hoa2d_maxre test_ir_reverb test_ir_simplefdn \
test_ir_simplefdn_gain test_ir_simplefdn_feedforward \
test_snd_vbap3d_speakermatch test_ir_volumetric test_pos_obstacle \
test_pos_obstacle_inner test_level_absorption test_ir_hrtf_0deg \
test_ir_hrtf_45deg test_ir_hrtf_75deg test_ir_hrtf_90deg \
test_ir_hrtf_105deg test_ir_hrtf_135deg test_ir_hrtf_180deg \
test_ir_hrtf_225deg test_ir_hrtf_270deg test_ir_hrtf_315deg \
test_ir_hrtf_el90deg test_ir_hrtf_el-90deg test_ir_hrtf_el45deg \
test_ir_hrtf_el-45deg test_ir_hrtf_diffuse1 test_ir_hrtf_diffuse2 \
test_ir_delay test_ir_delay2 test_ir_delay3 test_snd_reverb \
test_wav_multichannel test_snd_zeros test_ir_sub test_ir_sub_hoa2d \
test_ir_sub_nsp test_ir_partconvrev test_ir_partconvrev_offset \
test_ir_micarray_az0deg test_ir_micarray_az45deg \
test_ir_micarray_az75deg test_ir_micarray_az90deg \
test_ir_micarray_az105deg test_ir_micarray_az135deg \
test_ir_micarray_az180deg test_ir_micarray_az225deg \
test_ir_micarray_az270deg test_ir_micarray_az315deg \
test_ir_micarray_el45deg test_ir_micarray_el90deg \
test_ir_micarray_el-45deg test_ir_micarray_el-90deg \
test_snd_diffuse_micarray test_snd_micarray_az0deg \
test_ir_micarraysinc test_ir_amb1 test_ir_amb1_y test_ir_amb1_z \
test_snd_diffuse_0deg test_snd_diffuse_17deg \
test_snd_diffuse_rec17deg test_snd_maskplugin_fig8 \
test_snd_maskplugin_multibeam test_snd_maskplugin_multibeam1 \
test_snd_maskplugin_sampledgain test_snd_diffuse_inphase \
test_snd_diffuse_basic test_snd_diffuse_maxre \
test_snd_maskplugin_multibeam_diff test_ir_apfilter_highpass \
test_ir_apfilter_lowpass test_snd_hoa2d_fuma_hos \
test_ir_material_carpet test_ir_material_window test_ir1_spkcalib \
test_snd_spkcorr0 test_snd_spkcorr70 test_snd_nospkcorr \
test_snd_spkcorr_long test_ir_nodelaylineimagesource
TESTS = test_snd_pink_diffuse test_ir1 test_ir2 test_ir3 test_ir4 \
test_ir_proxy_air test_ir_proxy_gain test_ir_proxy_delay \
test_ir_proxy_direction test_ir6_ismminmax test_snd1 \
test_snd_include_sound test_snd2 test_snd4 test_snd3 \
test_snd5 test_pos1 test_pos2 test_pos_trackinterp \
test_snd_door1 test_snd_door2 test_snd_door3 test_pos_door \
test_snd_layers test_snd_rec_amb1h1v test_wav_diffuse \
test_wav_diffuse_hoa2d test_ir_hoa2d_offset \
test_wav_diffuse_nsp4 test_wav_diffuse_hoa2d4 \
test_wav_diffuse_layerbug test_wav_diffirs test_sndgainramp \
test_sndgainramp2 test_ir_spkcorr test_snd_calib1 \
test_snd_calib2 test_snd_vbap51 test_snd_pink \
test_snd_sndfile test_snd_sndfile2 test_snd_door4 \
test_snd_roommic test_level_vbap3d test_ir_ortf_0deg \
test_ir_ortf_55deg test_ir_scatter test_ir_noscatter \
test_ir_scatter_ortf test_snd_sourcedir_generic \
test_snd_sourcedir_generic1 \
test_snd_sourcedir_generic_cardioid test_ir_wfs \
test_ir_wfs_noplanewave test_level_hoa2d_basic \
test_level_hoa2d_maxre test_ir_reverb test_ir_simplefdn \
test_ir_simplefdn_biquadallpass test_ir_simplefdn_gain \
test_ir_simplefdn_feedforward test_snd_vbap3d_speakermatch \
test_ir_volumetric test_pos_obstacle test_pos_obstacle_inner \
test_level_absorption test_ir_hrtf_0deg test_ir_hrtf_45deg \
test_ir_hrtf_75deg test_ir_hrtf_90deg test_ir_hrtf_105deg \
test_ir_hrtf_135deg test_ir_hrtf_180deg test_ir_hrtf_225deg \
test_ir_hrtf_270deg test_ir_hrtf_315deg test_ir_hrtf_el90deg \
test_ir_hrtf_el-90deg test_ir_hrtf_el45deg \
test_ir_hrtf_el-45deg test_ir_hrtf_diffuse1 \
test_ir_hrtf_diffuse2 test_ir_delay test_ir_delay2 \
test_ir_delay3 test_snd_reverb test_wav_multichannel \
test_snd_zeros test_ir_sub test_ir_sub_hoa2d test_ir_sub_nsp \
test_ir_partconvrev test_ir_partconvrev_offset \
test_ir_micarray_az0deg test_ir_micarray_az45deg \
test_ir_micarray_az75deg test_ir_micarray_az90deg \
test_ir_micarray_az105deg test_ir_micarray_az135deg \
test_ir_micarray_az180deg test_ir_micarray_az225deg \
test_ir_micarray_az270deg test_ir_micarray_az315deg \
test_ir_micarray_el45deg test_ir_micarray_el90deg \
test_ir_micarray_el-45deg test_ir_micarray_el-90deg \
test_snd_diffuse_micarray test_snd_micarray_az0deg \
test_ir_micarraysinc test_ir_amb1 test_ir_amb1_y \
test_ir_amb1_z test_snd_diffuse_0deg test_snd_diffuse_17deg \
test_snd_diffuse_rec17deg test_snd_maskplugin_fig8 \
test_snd_maskplugin_multibeam test_snd_maskplugin_multibeam1 \
test_snd_maskplugin_sampledgain test_snd_diffuse_inphase \
test_snd_diffuse_basic test_snd_diffuse_maxre \
test_snd_maskplugin_multibeam_diff test_ir_apfilter_highpass \
test_ir_apfilter_lowpass test_snd_hoa2d_fuma_hos \
test_ir_material_carpet test_ir_material_window \
test_ir1_spkcalib test_snd_spkcorr0 test_snd_spkcorr70 \
test_snd_nospkcorr test_snd_spkcorr_long \
test_ir_nodelaylineimagesource

#test_ir_simplefdn_optimt60
#test_ir_scatter_reflections
Expand Down
Binary file added test/expected_ir_simplefdn_biquadallpass.wav
Binary file not shown.
9 changes: 9 additions & 0 deletions test/test_ir_simplefdn_biquadallpass.tsc
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<?xml version="1.0"?>
<session license="CC0">
<scene>
<source><sound x="1"/></source>
<reverb type="simplefdn" use_biquad_allpass="true"/>
<!--<reverb type="simplefdn" use_biquad_allpass="true" rallpass="0.95 0.95 0.95 0.95"/>-->
<receiver type="amb1h1v"/>
</scene>
</session>

0 comments on commit 2f1e2a9

Please sign in to comment.