00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016 #ifndef _FFT_MEMORY_CACHE_H_
00017 #define _FFT_MEMORY_CACHE_H_
00018
00019 #include "FFTCache.h"
00020
00021 #include "base/ResizeableBitset.h"
00022
00042 class FFTMemoryCache : public FFTCache
00043 {
00044 public:
00045 enum StorageType {
00046 Compact,
00047 Rectangular,
00048 Polar
00049 };
00050
00051 FFTMemoryCache(StorageType storageType);
00052 virtual ~FFTMemoryCache();
00053
00054 virtual size_t getWidth() const { return m_width; }
00055 virtual size_t getHeight() const { return m_height; }
00056
00057 virtual void resize(size_t width, size_t height);
00058 virtual void reset();
00059
00060 virtual float getMagnitudeAt(size_t x, size_t y) const {
00061 if (m_storageType == Rectangular) {
00062 return sqrt(m_freal[x][y] * m_freal[x][y] +
00063 m_fimag[x][y] * m_fimag[x][y]);
00064 } else {
00065 return getNormalizedMagnitudeAt(x, y) * m_factor[x];
00066 }
00067 }
00068
00069 virtual float getNormalizedMagnitudeAt(size_t x, size_t y) const {
00070 if (m_storageType == Rectangular) return getMagnitudeAt(x, y) / m_factor[x];
00071 else if (m_storageType == Polar) return m_fmagnitude[x][y];
00072 else return float(m_magnitude[x][y]) / 65535.0;
00073 }
00074
00075 virtual float getMaximumMagnitudeAt(size_t x) const {
00076 return m_factor[x];
00077 }
00078
00079 virtual float getPhaseAt(size_t x, size_t y) const {
00080 if (m_storageType == Rectangular) {
00081 return atan2f(m_fimag[x][y], m_freal[x][y]);
00082 } else if (m_storageType == Polar) {
00083 return m_fphase[x][y];
00084 } else {
00085 int16_t i = (int16_t)m_phase[x][y];
00086 return (float(i) / 32767.0) * M_PI;
00087 }
00088 }
00089
00090 virtual void getValuesAt(size_t x, size_t y, float &real, float &imag) const {
00091 if (m_storageType == Rectangular) {
00092 real = m_freal[x][y];
00093 imag = m_fimag[x][y];
00094 } else {
00095 float mag = getMagnitudeAt(x, y);
00096 float phase = getPhaseAt(x, y);
00097 real = mag * cosf(phase);
00098 imag = mag * sinf(phase);
00099 }
00100 }
00101
00102 virtual bool haveSetColumnAt(size_t x) const {
00103 return m_colset.get(x);
00104 }
00105
00106 virtual void setColumnAt(size_t x, float *mags, float *phases, float factor);
00107
00108 virtual void setColumnAt(size_t x, float *reals, float *imags);
00109
00110 static size_t getCacheSize(size_t width, size_t height, StorageType type);
00111
00112 virtual Type getType() { return MemoryCache; }
00113
00114 private:
00115 size_t m_width;
00116 size_t m_height;
00117 uint16_t **m_magnitude;
00118 uint16_t **m_phase;
00119 float **m_fmagnitude;
00120 float **m_fphase;
00121 float **m_freal;
00122 float **m_fimag;
00123 float *m_factor;
00124 StorageType m_storageType;
00125 ResizeableBitset m_colset;
00126
00127 virtual void setNormalizationFactor(size_t x, float factor) {
00128 if (x < m_width) m_factor[x] = factor;
00129 }
00130
00131 virtual void setMagnitudeAt(size_t x, size_t y, float mag) {
00132
00133 setNormalizedMagnitudeAt(x, y, mag / m_factor[x]);
00134 }
00135
00136 virtual void setNormalizedMagnitudeAt(size_t x, size_t y, float norm) {
00137 if (x < m_width && y < m_height) {
00138 if (m_storageType == Polar) m_fmagnitude[x][y] = norm;
00139 else m_magnitude[x][y] = uint16_t(norm * 65535.0);
00140 }
00141 }
00142
00143 virtual void setPhaseAt(size_t x, size_t y, float phase) {
00144
00145 if (x < m_width && y < m_height) {
00146 if (m_storageType == Polar) m_fphase[x][y] = phase;
00147 else m_phase[x][y] = uint16_t(int16_t((phase * 32767) / M_PI));
00148 }
00149 }
00150
00151 void resize(uint16_t **&, size_t, size_t);
00152 void resize(float **&, size_t, size_t);
00153 };
00154
00155
00156 #endif
00157