#include <processor.h>
Inheritance diagram for EMAN::FourierToCenterProcessor:
Public Member Functions | |
virtual void | process_inplace (EMData *image) |
Fourier origin shift the image in the forward direction. | |
virtual string | get_name () const |
Get the processor's name. | |
virtual string | get_desc () const |
Get the descrition of this specific processor. | |
Static Public Member Functions | |
Processor * | NEW () |
Static Public Attributes | |
const string | NAME = "xform.fourierorigin.tocenter" |
After this you operate on the Fourier image in convenient format, then you call FourierToCornerProcessor (above) and then inverse FT to get to the original image
Definition at line 4623 of file processor.h.
|
Get the descrition of this specific processor. This function must be overwritten by a subclass.
Implements EMAN::Processor. Definition at line 4643 of file processor.h. 04644 { 04645 return "Translates the origin in Fourier space from the corner to the center in y and z - works in 2D and 3D"; 04646 }
|
|
Get the processor's name. Each processor is identified by a unique name.
Implements EMAN::Processor. Definition at line 4633 of file processor.h. 04634 {
04635 return NAME;
04636 }
|
|
Definition at line 4638 of file processor.h. 04639 { 04640 return new FourierToCenterProcessor(); 04641 }
|
|
Fourier origin shift the image in the forward direction.
Implements EMAN::Processor. Definition at line 4532 of file processor.cpp. References EMAN::EMData::get_data(), EMAN::EMData::get_xsize(), EMAN::EMData::get_ysize(), EMAN::EMData::get_zsize(), ImageFormatException, EMAN::EMData::is_complex(), nx, ny, rdata, EMAN::EMData::set_shuffled(), x, and y. 04533 { 04534 // if ( !image->is_complex() ) throw ImageFormatException("Can not Fourier origin shift an image that is not complex"); 04535 04536 int nx=image->get_xsize(); 04537 int ny=image->get_ysize(); 04538 int nz=image->get_zsize(); 04539 04540 int nxy = nx*ny; 04541 04542 if ( ny == 1 && nz == 1 ){ 04543 cout << "Warning- attempted Fourier origin shift a 1D image - no action taken" << endl; 04544 return; 04545 } 04546 04547 int yodd = (ny%2==1); 04548 int zodd = (nz%2==1); 04549 04550 float* rdata = image->get_data(); 04551 04552 float tmp[2]; 04553 float* p1; 04554 float* p2; 04555 04556 // This will tackle the 'normalization' images which come out of the Fourier reconstructor. 04557 // ie- real-space 1/2 FFt images centered on the corner 04558 if ( !image->is_complex() ) { 04559 if (nz!=1 && !yodd && !zodd) { 04560 for (int x=0; x<nx; x++) { 04561 for (int y=0; y<ny; y++) { 04562 for (int z=0; z<nz/2; z++) { 04563 int y2=(y+ny/2)%ny; 04564 int z2=(z+nz/2)%nz; // %nz should be redundant here 04565 size_t i=x+y*nx+(size_t)z*nxy; 04566 size_t i2=x+y2*nx+(size_t)z2*nxy; 04567 float swp=rdata[i]; 04568 rdata[i]=rdata[i2]; 04569 rdata[i2]=swp; 04570 } 04571 } 04572 } 04573 04574 return; 04575 } 04576 else throw ImageFormatException("Can not Fourier origin shift an image that is not complex unless it is even in ny,nz and nx=ny/2+1"); 04577 } 04578 04579 if (yodd){ 04580 // In 3D this is swapping the bottom slice (with respect to the y direction) and the middle slice, 04581 // shifting all slices below the middle slice down one. In 2D it is equivalent, but in terms of rows. 04582 float prev[2]; 04583 size_t idx; 04584 for( int s = 0; s < nz; s++ ) { 04585 for( int c =0; c < nx; c += 2 ) { 04586 idx = (size_t)s*nxy+c; 04587 prev[0] = rdata[idx]; 04588 prev[1] = rdata[idx+1]; 04589 for( int r = ny/2; r >= 0; --r ) { 04590 idx = (size_t)s*nxy+r*nx+c; 04591 float* p1 = &rdata[idx]; 04592 tmp[0] = p1[0]; 04593 tmp[1] = p1[1]; 04594 04595 p1[0] = prev[0]; 04596 p1[1] = prev[1]; 04597 04598 prev[0] = tmp[0]; 04599 prev[1] = tmp[1]; 04600 } 04601 } 04602 } 04603 } 04604 04605 // 3D - Shift slices correctly in the y direction, 2D - shift rows 04606 size_t idx1, idx2; 04607 for( int s = 0; s < nz; ++s ) { 04608 for( int r = 0; r < ny/2; ++r ) { 04609 for( int c =0; c < nx; c += 2 ) { 04610 idx1 = (size_t)s*nxy+r*nx+c; 04611 idx2 = (size_t)s*nxy+(r+ny/2+yodd)*nx+c; 04612 p1 = &rdata[idx1]; 04613 p2 = &rdata[idx2]; 04614 04615 tmp[0] = p1[0]; 04616 tmp[1] = p1[1]; 04617 04618 p1[0] = p2[0]; 04619 p1[1] = p2[1]; 04620 04621 p2[0] = tmp[0]; 04622 p2[1] = tmp[1]; 04623 } 04624 } 04625 } 04626 04627 if ( nz != 1 ) { 04628 if (zodd){ 04629 // Swap the front slice (with respect to the z direction) and the middle slice 04630 // shifting all slices behind the middles slice towards the front slice 1 voxel. 04631 float prev[2]; 04632 size_t idx; 04633 for( int r = 0; r < ny; ++r ) { 04634 for( int c =0; c < nx; c += 2 ) { 04635 prev[0] = rdata[r*nx+c]; 04636 prev[1] = rdata[r*nx+c+1]; 04637 for( int s = nz/2; s >= 0; --s ) { 04638 idx = (size_t)s*nxy+r*nx+c; 04639 float* p1 = &rdata[idx]; 04640 tmp[0] = p1[0]; 04641 tmp[1] = p1[1]; 04642 04643 p1[0] = prev[0]; 04644 p1[1] = prev[1]; 04645 04646 prev[0] = tmp[0]; 04647 prev[1] = tmp[1]; 04648 } 04649 } 04650 } 04651 } 04652 04653 // Shift slices correctly in the y direction 04654 size_t idx1, idx2; 04655 for( int s = 0; s < nz/2; ++s ) { 04656 for( int r = 0; r < ny; ++r ) { 04657 for( int c =0; c < nx; c += 2 ) { 04658 idx1 = (size_t)s*nxy+r*nx+c; 04659 idx2 = (size_t)(s+nz/2+zodd)*nxy+r*nx+c; 04660 p1 = &rdata[idx1]; 04661 p2 = &rdata[idx2]; 04662 04663 tmp[0] = p1[0]; 04664 tmp[1] = p1[1]; 04665 04666 p1[0] = p2[0]; 04667 p1[1] = p2[1]; 04668 04669 p2[0] = tmp[0]; 04670 p2[1] = tmp[1]; 04671 } 04672 } 04673 } 04674 } 04675 image->set_shuffled(true); 04676 }
|
|
Definition at line 160 of file processor.cpp. |