|
|
@ -22,8 +22,9 @@ function [frameFout, TNScoeffs] = TNS(frameFin, frameType) |
|
|
|
SHORT_WINDOW_NUMBER_OF_BANDS = 42; |
|
|
|
% Declares constant order of the linear prediction filter |
|
|
|
LPF_ORDER = 4; |
|
|
|
% Declares constant coefficients' resolution |
|
|
|
COEF_RES = 4; |
|
|
|
% Declares constant coefficients' resolution, in the form of number of |
|
|
|
% decimal digits used |
|
|
|
COEF_RES = 1; |
|
|
|
|
|
|
|
% Declares persistent variable holding the TNS tables and initializes if empty |
|
|
|
persistent TNSTables; |
|
|
@ -37,26 +38,13 @@ function [frameFout, TNScoeffs] = TNS(frameFin, frameType) |
|
|
|
for band = 1:LONG_WINDOW_NUMBER_OF_BANDS - 1 |
|
|
|
bandEnergy(band) = sumsqr(frameFin(TNSTables.B219a(band, 2) + 1:TNSTables.B219a(band + 1, 2))); |
|
|
|
end |
|
|
|
bandEnergy(LONG_WINDOW_NUMBER_OF_BANDS) = sumsqr( ... |
|
|
|
frameFin(TNSTables.B219a(LONG_WINDOW_NUMBER_OF_BANDS, 2) + 1:... |
|
|
|
TNSTables.B219a(LONG_WINDOW_NUMBER_OF_BANDS, 3) + 1)); |
|
|
|
bandEnergy(LONG_WINDOW_NUMBER_OF_BANDS) = sumsqr(frameFin( ... |
|
|
|
TNSTables.B219a(LONG_WINDOW_NUMBER_OF_BANDS, 2) + 1:end)); |
|
|
|
|
|
|
|
% Calculates the normalization factors |
|
|
|
|
|
|
|
% PROBABLY WRONG, THE ONE BELLOW SHOULD BE RIGHT AND BETTER |
|
|
|
% normalizationFactor(1024) = 0; |
|
|
|
% for normIndex = 1:1024 |
|
|
|
% bandIndices = find(TNSTables.B219a(:, 2) >= (normIndex - 1), 1); |
|
|
|
% if ~isempty(bandIndices) |
|
|
|
% normalizationFactor(normIndex) = sqrt(bandEnergy(bandIndices)); |
|
|
|
% else |
|
|
|
% normalizationFactor(normIndex) = sqrt(bandEnergy(find(TNSTables.B219a(:, 3) >= normIndex - 1, 1))); |
|
|
|
% end |
|
|
|
% end |
|
|
|
|
|
|
|
bandIndices = quantiz(0:1023, TNSTables.B219a(:, 2) - 1); |
|
|
|
normalizationFactor = sqrt(bandEnergy(bandIndices)); |
|
|
|
|
|
|
|
|
|
|
|
% Smooths normalization factors |
|
|
|
for normIndex = 1023:-1:1 |
|
|
|
normalizationFactor(normIndex) = (normalizationFactor(normIndex) + normalizationFactor(normIndex + 1)) / 2; |
|
|
@ -72,58 +60,34 @@ function [frameFout, TNScoeffs] = TNS(frameFin, frameType) |
|
|
|
[linPredCoeff, ~] = lpc(normalizedFrameFin, LPF_ORDER); |
|
|
|
|
|
|
|
% Quantizes these coefficients |
|
|
|
quantizedLinPredCoeff(LPF_ORDER) = 0; |
|
|
|
for coeffIndex = 2:length(linPredCoeff) |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = asin(linPredCoeff(coeffIndex)); |
|
|
|
if linPredCoeff(coeffIndex) >= 0 |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = round(quantizedLinPredCoeff(coeffIndex - 1) * ... |
|
|
|
(bitshift(1, COEF_RES - 1) - 0.5) / (pi / 2)); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = quantizedLinPredCoeff(coeffIndex - 1) / ... |
|
|
|
(bitshift(1, COEF_RES - 1) - 0.5) / (pi / 2); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = sin (quantizedLinPredCoeff(coeffIndex - 1)); |
|
|
|
else |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = round(quantizedLinPredCoeff(coeffIndex - 1) * ... |
|
|
|
(bitshift(1, COEF_RES - 1) + 0.5) / (pi / 2)); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = quantizedLinPredCoeff(coeffIndex - 1) / ... |
|
|
|
(bitshift(1, COEF_RES - 1) + 0.5) / (pi / 2); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = sin (quantizedLinPredCoeff(coeffIndex - 1)); |
|
|
|
end |
|
|
|
end |
|
|
|
|
|
|
|
quantizedLinPredCoeff = round(linPredCoeff, COEF_RES); |
|
|
|
|
|
|
|
% Filters MDCT coefficients |
|
|
|
if ~isstable(1, [1 (quantizedLinPredCoeff * (-1))]) |
|
|
|
if ~isstable(1, quantizedLinPredCoeff) |
|
|
|
error('TNS, l[79]: Inverse filter not stable!'); |
|
|
|
else |
|
|
|
TNScoeffs = quantizedLinPredCoeff; |
|
|
|
frameFout = filter([1 (quantizedLinPredCoeff * (-1))], 1, frameFin); |
|
|
|
TNScoeffs = quantizedLinPredCoeff(2:end); |
|
|
|
frameFout = filter(quantizedLinPredCoeff, 1, frameFin); |
|
|
|
end |
|
|
|
else |
|
|
|
% Initializes output vectors |
|
|
|
TNScoeffs(LPF_ORDER * 8) = 0; |
|
|
|
frameFout(1024) = 0; |
|
|
|
|
|
|
|
|
|
|
|
bandEnergy(SHORT_WINDOW_NUMBER_OF_BANDS) = 0; |
|
|
|
for subFrameIndex = 1:8 |
|
|
|
subFrame = frameFin((subFrameIndex - 1) * 128 + 1:subFrameIndex * 128); |
|
|
|
|
|
|
|
|
|
|
|
% Calculates the energy per band |
|
|
|
for band = 1:SHORT_WINDOW_NUMBER_OF_BANDS - 1 |
|
|
|
bandEnergy(band) = sumsqr(subFrame(TNSTables.B219b(band, 2) + 1:TNSTables.B219b(band + 1, 2))); |
|
|
|
end |
|
|
|
bandEnergy(SHORT_WINDOW_NUMBER_OF_BANDS) = sumsqr( ... |
|
|
|
subFrame(TNSTables.B219b(SHORT_WINDOW_NUMBER_OF_BANDS, 2) + 1:... |
|
|
|
TNSTables.B219b(SHORT_WINDOW_NUMBER_OF_BANDS, 3) + 1)); |
|
|
|
bandEnergy(SHORT_WINDOW_NUMBER_OF_BANDS) = sumsqr(subFrame( ... |
|
|
|
TNSTables.B219b(SHORT_WINDOW_NUMBER_OF_BANDS, 2) + 1:end)); |
|
|
|
|
|
|
|
% Calculates the normalization factors |
|
|
|
normalizationFactor(128) = 0; |
|
|
|
for normIndex = 1:128 |
|
|
|
bandIndices = find(TNSTables.B219b(:, 2) >= normIndex - 1, 1); |
|
|
|
if ~isempty(bandIndices) |
|
|
|
normalizationFactor(normIndex) = sqrt(bandEnergy(bandIndices)); |
|
|
|
else |
|
|
|
normalizationFactor(normIndex) = sqrt(bandEnergy(find(TNSTables.B219b(:, 3) <= normIndex - 1, 1))); |
|
|
|
end |
|
|
|
end |
|
|
|
bandIndices = quantiz(0:127, TNSTables.B219b(:, 2) - 1); |
|
|
|
normalizationFactor = sqrt(bandEnergy(bandIndices)); |
|
|
|
|
|
|
|
% Smooths normalization factors |
|
|
|
for normIndex = 127:-1:1 |
|
|
@ -140,33 +104,16 @@ function [frameFout, TNScoeffs] = TNS(frameFin, frameType) |
|
|
|
[linPredCoeff, ~] = lpc(normalizedFrameFin, LPF_ORDER); |
|
|
|
|
|
|
|
% Quantizes these coefficients |
|
|
|
quantizedLinPredCoeff(LPF_ORDER) = 0; |
|
|
|
for coeffIndex = 1:length(linPredCoeff) |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = asin(linPredCoeff(coeffIndex)); |
|
|
|
if linPredCoeff(coeffIndex) >= 0 |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = round(quantizedLinPredCoeff(coeffIndex - 1) * ... |
|
|
|
(bitshift(1, COEF_RES - 1) - 0.5) / (pi / 2)); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = quantizedLinPredCoeff(coeffIndex - 1) / ... |
|
|
|
(bitshift(1, COEF_RES - 1) - 0.5) / (pi / 2); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = sin (quantizedLinPredCoeff(coeffIndex - 1)); |
|
|
|
else |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = round(quantizedLinPredCoeff(coeffIndex - 1) * ... |
|
|
|
(bitshift(1, COEF_RES - 1) + 0.5) / (pi / 2)); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = quantizedLinPredCoeff(coeffIndex - 1) / ... |
|
|
|
(bitshift(1, COEF_RES - 1) + 0.5) / (pi / 2); |
|
|
|
quantizedLinPredCoeff(coeffIndex - 1) = sin (quantizedLinPredCoeff(coeffIndex - 1)); |
|
|
|
end |
|
|
|
end |
|
|
|
quantizedLinPredCoeff = round(linPredCoeff, COEF_RES); |
|
|
|
|
|
|
|
% Filters MDCT coefficients |
|
|
|
if ~isstable(1, [1 (quantizedLinPredCoeff * (-1))]) |
|
|
|
if ~isstable(1, quantizedLinPredCoeff) |
|
|
|
error('TNS, l[79]: Inverse filter not stable!'); |
|
|
|
else |
|
|
|
TNScoeffs((subFrameIndex - 1) * 4 + 1:subFrameIndex * 4) = quantizedLinPredCoeff; |
|
|
|
TNScoeffs((subFrameIndex - 1) * 4 + 1:subFrameIndex * 4) = quantizedLinPredCoeff(2:end); |
|
|
|
frameFout((subFrameIndex - 1) * 128 + 1:subFrameIndex * 128) = ... |
|
|
|
filter([1 (quantizedLinPredCoeff * (-1))], 1, subFrame); |
|
|
|
filter(quantizedLinPredCoeff, 1, subFrame); |
|
|
|
end |
|
|
|
end |
|
|
|
end |
|
|
|
end |
|
|
|
|
|
|
|