VABinauralCluster.cpp 5.95 KB
Newer Older
1
2
3
#define NOMINMAX

#include <math.h>
4
5
#include "VABinauralCluster.h"

Lucas Moesch's avatar
WIP    
Lucas Moesch committed
6
7
8
// VA includes
#include "../../../../../directivities/VADirectivityDAFFHRIR.h"

9
10
11
// ITA includes
#include <ITAConstants.h>

12
// Utils
13
#include "../RelationMetrics/VARelationMetrics.h"
14
15
#include "../BinauralTimeOfArrivalEstimator/VABinauralTOAEstimator.h"

16
17
18
19
20
21
VABinauralCluster::VABinauralCluster()
{
}

VABinauralCluster::VABinauralCluster(const VABinauralCluster& cluster) :
	maxError(cluster.maxError),
Lucas Moesch's avatar
wip    
Lucas Moesch committed
22
	numSources(cluster.numSources),
23
24
25
26
27
28
29
30
	_clusterSourcePos(cluster._clusterSourcePos)
{

}


VABinauralCluster::~VABinauralCluster()
{
31
32
33
34
35
36
37
38
39
40
41
	VABinauralSoundSource* source;
	std::map<int, VABinauralSoundSource*>::const_iterator it;

	// clear all references from this cluster
	for (it = _sources.begin(); it != _sources.end();)
	{
		source = it->second;
		it = _sources.erase(it);

		source->RemoveReference();
	}
42
43
44
}

void
45
VABinauralCluster::init(int sourceID, VABinauralSoundSource* source, VABinauralListener* listener, ITAUPConvolution* FIRConvolverChL, ITAUPConvolution* FIRConvolverChR)
46
{
47
48
	_FIRConvolverChL = FIRConvolverChL;
	_FIRConvolverChR = FIRConvolverChR;
49
50
	_listener = listener;
	_listenerPos = listener->predPos;
51
	_clusterSourcePos = _clusterSourcePos + source->predPos;
52
53
54
55
56
57
58
	_clusterSourceToListenerPos = _clusterSourcePos - _listenerPos;

	_output = new ITASampleFrame(2, listener->output->GetLength(), true);
	
	_tmpChL.Init(listener->output->GetLength(), true);
	_tmpChR.Init(listener->output->GetLength(), true);

59
60
	maxError = getDistError(source);

Lucas Moesch's avatar
WIP    
Lucas Moesch committed
61
62
	_sources.insert(std::pair<int, VABinauralSoundSource*>(sourceID, source));

63
64
65
	// --
	source->AddReference();

Lucas Moesch's avatar
wip    
Lucas Moesch committed
66
	++numSources;
67
68
}

Lucas Moesch's avatar
Lucas Moesch committed
69
70
71
void
VABinauralCluster::init(VABinauralCluster* cluster)
{
72
73
	_FIRConvolverChL = cluster->_FIRConvolverChL;
	_FIRConvolverChR = cluster->_FIRConvolverChR;
Lucas Moesch's avatar
Lucas Moesch committed
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
	_listener = cluster->_listener;
	_listenerPos = _listener->predPos;
	_clusterSourcePos = cluster->_clusterSourcePos;
	_clusterSourceToListenerPos = _clusterSourcePos - _listenerPos;

	_output = new ITASampleFrame(2, _listener->output->GetLength(), true);

	_tmpChL.Init(_listener->output->GetLength(), true);
	_tmpChR.Init(_listener->output->GetLength(), true);

	maxError = cluster->maxError;

	std::map< int, VABinauralSoundSource*>::const_iterator it;
	for (it = cluster->_sources.begin(); it != cluster->_sources.end(); ++it)
	{
		_sources.insert(std::pair<int, VABinauralSoundSource*>(it->first, it->second));
		it->second->AddReference();
	}

	numSources = cluster->numSources;
}

96
97
98
99
100
101
ITASampleFrame*
VABinauralCluster::getOutput()
{
	// reset output Buffer
	_output->zero();

102
103
104
105
106
107
108
	// get cluster HRTF TOA
	VARelationMetrics clusterSourceMetrics;
	clusterSourceMetrics.calc(_listener->predPos, _listener->predView, _listener->predUp, _clusterSourcePos);

	double toaHRTFChL = _listener->toaEstimator->getTOALeft(clusterSourceMetrics.phi, clusterSourceMetrics.theta);
	double toaHRTFChR = _listener->toaEstimator->getTOARight(clusterSourceMetrics.phi, clusterSourceMetrics.theta);

109
110
111
112
113
114
115
	// set VDL Values
	std::map<int, VABinauralSoundSource*>::const_iterator it;
	for (it = _sources.begin(); it != _sources.end(); ++it)
	{
		VABinauralSoundSource* source = it->second;
		const ITASampleBuffer* input = source->data->pSignalSourceInputBuf;

116
117
		VARelationMetrics sourceMetrics;
		sourceMetrics.calc(_listener->predPos, _listener->predView, _listener->predUp, source->predPos);
118

119
120
121
122
		double toaDistance = sourceMetrics.dist / 343; // TODO: Medium Propagation....
	
		double toaSourceChL = _listener->toaEstimator->getTOALeft(sourceMetrics.phi, sourceMetrics.theta);
		double toSourceaChR = _listener->toaEstimator->getTOARight(sourceMetrics.phi, sourceMetrics.theta);
123

124
125
		source->vdlChL->SetDelayTime(toaDistance + toaSourceChL - toaHRTFChL);
		source->vdlChR->SetDelayTime(toaDistance + toSourceaChR - toaHRTFChR);
Lucas Moesch's avatar
WIP    
Lucas Moesch committed
126

127
128
		//source->vdlChL->SetDelayTime(toaDistance + toaSourceChL);
		//source->vdlChR->SetDelayTime(toaDistance + toSourceaChR);
129
130
131
132
133
134
135
136

		source->vdlChL->Process(input, &(_tmpChL));
		source->vdlChR->Process(input, &(_tmpChR));

		(*_output)[0] += _tmpChL;
		(*_output)[1] += _tmpChR;
	}

137
	// convolve here!
Lucas Moesch's avatar
WIP    
Lucas Moesch committed
138
139
140
141
	CVADirectivityDAFFHRIR* HRIR = (CVADirectivityDAFFHRIR *)_listener->directivity;

	if (HRIR){
		int index = -1;
142

Lucas Moesch's avatar
WIP    
Lucas Moesch committed
143
144
145
146
147
		HRIR->GetNearestNeighbour(clusterSourceMetrics.phi, clusterSourceMetrics.theta, &index);

		_FIRConvolverChL->Process((*_output)[0].data(), (*_output)[0].data(), ITABase::MixingMethod::OVERWRITE);
		_FIRConvolverChR->Process((*_output)[1].data(), (*_output)[1].data(), ITABase::MixingMethod::OVERWRITE);
	}
148

149
150
151
	return _output;
}

152
153
154
double
VABinauralCluster::getDistError(VABinauralSoundSource* source)
{
155
156
	VAVec3 sourceToListenerPos = source->predPos - _listenerPos;
	double dotp = _clusterSourceToListenerPos.Dot(sourceToListenerPos);
157

158
	return (dotp * dotp) / (_clusterSourcePos.Dot(_clusterSourcePos) * sourceToListenerPos.Dot(sourceToListenerPos));
159
160
161
}

void 
Lucas Moesch's avatar
WIP    
Lucas Moesch committed
162
VABinauralCluster::addSource(int sourceID, VABinauralSoundSource* source)
163
164
165
{
	double err = getDistError(source);

Lucas Moesch's avatar
wip    
Lucas Moesch committed
166
	_clusterSourcePos = (source->predPos + _clusterSourcePos * numSources) / (numSources + 1);
167
168
	_clusterSourceToListenerPos = _clusterSourcePos - _listenerPos;

169
170
	maxError = std::max(err, maxError);

Lucas Moesch's avatar
WIP    
Lucas Moesch committed
171
172
	_sources.insert(std::pair<int, VABinauralSoundSource*>(sourceID, source));

173
174
175
	// --
	source->AddReference();

Lucas Moesch's avatar
wip    
Lucas Moesch committed
176
	++numSources;
177
178
179
}

void
180
VABinauralCluster::addSource(int sourceID, VABinauralSoundSource* source, double error)
181
{
Lucas Moesch's avatar
wip    
Lucas Moesch committed
182
	_clusterSourcePos = (source->predPos + _clusterSourcePos * numSources) / (numSources + 1);
183
184
	_clusterSourceToListenerPos = _clusterSourcePos - _listenerPos;

185
186
	maxError = std::max(error, maxError);

187
188
189
190
	_sources.insert(std::pair<int, VABinauralSoundSource*>(sourceID, source));
	// --
	source->AddReference();

Lucas Moesch's avatar
wip    
Lucas Moesch committed
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
	++numSources;
}

void
VABinauralCluster::removeSource(int sourceID)
{
	std::map<int, VABinauralSoundSource*>::const_iterator it = _sources.find(sourceID);
	VABinauralSoundSource* source = it->second;

	_sources.erase(it);

	source->RemoveReference();

	_clusterSourcePos = (_clusterSourcePos * numSources - source->predPos) / (numSources - 1);

	//TODO: MaxError
	--numSources;

209
210
}