private void Build3DDensityField() { PixelsBuffer DensityField = new PixelsBuffer(DENSITY_FIELD_SIZE * DENSITY_FIELD_SIZE * DENSITY_FIELD_HEIGHT); byte D; float3 P; float3 C = new float3(0.5f, 0.5f, 0.5f); using (System.IO.BinaryWriter W = DensityField.OpenStreamWrite()) for (int X = 0; X < DENSITY_FIELD_SIZE; X++) { P.x = (0.5f + X) / DENSITY_FIELD_SIZE; for (int Y = 0; Y < DENSITY_FIELD_HEIGHT; Y++) { P.y = (0.5f + Y) / DENSITY_FIELD_HEIGHT; for (int Z = 0; Z < DENSITY_FIELD_SIZE; Z++) { P.z = (0.5f + Z) / DENSITY_FIELD_SIZE; // D = 0; // Empty for now: photons should go straight through! D = (byte)((P - C).LengthSquared < 0.125f ? 255 : 0); W.Write(D); } } } Reg(m_Tex_DensityField = new Texture3D(m_Device, DENSITY_FIELD_SIZE, DENSITY_FIELD_HEIGHT, DENSITY_FIELD_SIZE, 1, PIXEL_FORMAT.R8_UNORM, false, false, new PixelsBuffer[] { DensityField })); DensityField.Dispose(); }
void CheckAgainstFFTW() { if (m_FFTW_2D == null) { m_FFTW_2D = new fftwlib.FFT2D(SIGNAL_SIZE_2D, SIGNAL_SIZE_2D); m_test_CPU = new Texture2D(m_device2D, SIGNAL_SIZE_2D, SIGNAL_SIZE_2D, 1, 1, ImageUtility.PIXEL_FORMAT.RG32F, ImageUtility.COMPONENT_FORMAT.AUTO, true, false, null); m_FFTW2D_Output = new Texture2D(m_device2D, SIGNAL_SIZE_2D, SIGNAL_SIZE_2D, 1, 1, ImageUtility.PIXEL_FORMAT.RG32F, ImageUtility.COMPONENT_FORMAT.AUTO, false, true, null); } // Retrieve input as CPU-accessible m_test_CPU.CopyFrom(m_FFT2D_GPU.Input); PixelsBuffer bufferIn = m_test_CPU.MapRead(0, 0); m_test_CPU.UnMap(bufferIn); float2[,] input_GPU = new float2[SIGNAL_SIZE_2D, SIGNAL_SIZE_2D]; using (System.IO.BinaryReader R = bufferIn.OpenStreamRead()) for (int Y = 0; Y < SIGNAL_SIZE_2D; Y++) { for (int X = 0; X < SIGNAL_SIZE_2D; X++) { input_GPU[X, Y].Set(R.ReadSingle(), R.ReadSingle()); } } bufferIn.Dispose(); // Apply FFT m_FFT2D_GPU.FFT_GPUInOut(-1.0f); // Retrieve output as CPU-accessible m_test_CPU.CopyFrom(m_FFT2D_GPU.Output); PixelsBuffer bufferOut = m_test_CPU.MapRead(0, 0); m_test_CPU.UnMap(bufferOut); float2[,] output_GPU = new float2[SIGNAL_SIZE_2D, SIGNAL_SIZE_2D]; using (System.IO.BinaryReader R = bufferOut.OpenStreamRead()) for (int Y = 0; Y < SIGNAL_SIZE_2D; Y++) { for (int X = 0; X < SIGNAL_SIZE_2D; X++) { output_GPU[X, Y].Set(R.ReadSingle(), R.ReadSingle()); } } bufferOut.Dispose(); // Process input with FFTW m_FFTW_2D.FillInputSpatial((int _x, int _y, out float _r, out float _i) => { _r = input_GPU[_x, _y].x; _i = input_GPU[_x, _y].y; }); m_FFTW_2D.Execute(fftwlib.FFT2D.Normalization.DIMENSIONS_PRODUCT); float2[,] output_FFTW = new float2[SIGNAL_SIZE_2D, SIGNAL_SIZE_2D]; m_FFTW_2D.GetOutput((int _x, int _y, float _r, float _i) => { output_FFTW[_x, _y].Set(_r, _i); }); // Upload FFTW output to GPU bufferOut = m_test_CPU.MapWrite(0, 0); using (System.IO.BinaryWriter W = bufferOut.OpenStreamWrite()) for (int Y = 0; Y < SIGNAL_SIZE_2D; Y++) { for (int X = 0; X < SIGNAL_SIZE_2D; X++) { W.Write(output_FFTW[X, Y].x); W.Write(output_FFTW[X, Y].y); } } m_test_CPU.UnMap(bufferOut); bufferOut.Dispose(); m_FFTW2D_Output.CopyFrom(m_test_CPU); // Compare float sumSqDiffR = 0.0f; float sumSqDiffI = 0.0f; for (int Y = 0; Y < SIGNAL_SIZE_2D; Y++) { for (int X = 0; X < SIGNAL_SIZE_2D; X++) { float2 GPU = output_GPU[X, Y]; float2 FFTW = output_FFTW[X, Y]; float2 diff = GPU - FFTW; sumSqDiffR += diff.x * diff.x; sumSqDiffI += diff.y * diff.y; } } labelDiff2D.Text = "SqDiff = " + sumSqDiffR.ToString("G3") + " , " + sumSqDiffI.ToString("G3"); }
private void Build3DDensityField() { PixelsBuffer DensityField = new PixelsBuffer( DENSITY_FIELD_SIZE*DENSITY_FIELD_SIZE*DENSITY_FIELD_HEIGHT ); byte D; float3 P; float3 C = new float3( 0.5f, 0.5f, 0.5f ); using ( System.IO.BinaryWriter W = DensityField.OpenStreamWrite() ) for ( int X=0; X < DENSITY_FIELD_SIZE; X++ ) { P.x = (0.5f+X) / DENSITY_FIELD_SIZE; for ( int Y=0; Y < DENSITY_FIELD_HEIGHT; Y++ ) { P.y = (0.5f+Y) / DENSITY_FIELD_HEIGHT; for ( int Z=0; Z < DENSITY_FIELD_SIZE; Z++ ) { P.z = (0.5f+Z) / DENSITY_FIELD_SIZE; // D = 0; // Empty for now: photons should go straight through! D = (byte) ((P - C).LengthSquared < 0.125f ? 255 : 0); W.Write( D ); } } } Reg( m_Tex_DensityField = new Texture3D( m_Device, DENSITY_FIELD_SIZE, DENSITY_FIELD_HEIGHT, DENSITY_FIELD_SIZE, 1, PIXEL_FORMAT.R8_UNORM, false, false, new PixelsBuffer[] { DensityField } ) ); DensityField.Dispose(); }