From b2fc6c70434674d74551c3a6c01ffb3233499312 Mon Sep 17 00:00:00 2001 From: Willem Jan Palenstijn Date: Mon, 1 Jul 2013 22:34:11 +0000 Subject: Update version to 1.3 --- src/ConeVecProjectionGeometry3D.cpp | 232 ++++++++++++++++++++++++++++++++++++ 1 file changed, 232 insertions(+) create mode 100644 src/ConeVecProjectionGeometry3D.cpp (limited to 'src/ConeVecProjectionGeometry3D.cpp') diff --git a/src/ConeVecProjectionGeometry3D.cpp b/src/ConeVecProjectionGeometry3D.cpp new file mode 100644 index 0000000..875a2c7 --- /dev/null +++ b/src/ConeVecProjectionGeometry3D.cpp @@ -0,0 +1,232 @@ +/* +----------------------------------------------------------------------- +Copyright 2012 iMinds-Vision Lab, University of Antwerp + +Contact: astra@ua.ac.be +Website: http://astra.ua.ac.be + + +This file is part of the +All Scale Tomographic Reconstruction Antwerp Toolbox ("ASTRA Toolbox"). + +The ASTRA Toolbox is free software: you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation, either version 3 of the License, or +(at your option) any later version. + +The ASTRA Toolbox is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with the ASTRA Toolbox. If not, see . + +----------------------------------------------------------------------- +$Id$ +*/ + +#include "astra/ConeVecProjectionGeometry3D.h" + +#include +#include + +using namespace std; + +namespace astra +{ + +//---------------------------------------------------------------------------------------- +// Default constructor. +CConeVecProjectionGeometry3D::CConeVecProjectionGeometry3D() : + CProjectionGeometry3D() +{ + m_pProjectionAngles = 0; +} + +//---------------------------------------------------------------------------------------- +// Constructor. +CConeVecProjectionGeometry3D::CConeVecProjectionGeometry3D(int _iProjectionAngleCount, + int _iDetectorRowCount, + int _iDetectorColCount, + const SConeProjection* _pProjectionAngles + ) : + CProjectionGeometry3D() +{ + initialize(_iProjectionAngleCount, + _iDetectorRowCount, + _iDetectorColCount, + _pProjectionAngles); +} + +//---------------------------------------------------------------------------------------- +// Destructor. +CConeVecProjectionGeometry3D::~CConeVecProjectionGeometry3D() +{ + delete[] m_pProjectionAngles; +} + +//--------------------------------------------------------------------------------------- +// Initialize - Config +bool CConeVecProjectionGeometry3D::initialize(const Config& _cfg) +{ + ASTRA_ASSERT(_cfg.self); + ConfigStackCheck CC("ConeVecProjectionGeometry3D", this, _cfg); + + XMLNode* node; + + // TODO: Fix up class hierarchy... this class doesn't fit very well. + // initialization of parent class + //CProjectionGeometry3D::initialize(_cfg); + + // Required: DetectorRowCount + node = _cfg.self->getSingleNode("DetectorRowCount"); + ASTRA_CONFIG_CHECK(node, "ConeVecProjectionGeometry3D", "No DetectorRowCount tag specified."); + m_iDetectorRowCount = boost::lexical_cast(node->getContent()); + ASTRA_DELETE(node); + CC.markNodeParsed("DetectorRowCount"); + + // Required: DetectorColCount + node = _cfg.self->getSingleNode("DetectorColCount"); + ASTRA_CONFIG_CHECK(node, "ConeVecProjectionGeometry3D", "No DetectorColCount tag specified."); + m_iDetectorColCount = boost::lexical_cast(node->getContent()); + m_iDetectorTotCount = m_iDetectorRowCount * m_iDetectorColCount; + ASTRA_DELETE(node); + CC.markNodeParsed("DetectorColCount"); + + // Required: Vectors + node = _cfg.self->getSingleNode("Vectors"); + ASTRA_CONFIG_CHECK(node, "ConeVecProjectionGeometry3D", "No Vectors tag specified."); + vector data = node->getContentNumericalArrayDouble(); + CC.markNodeParsed("Vectors"); + ASTRA_DELETE(node); + ASTRA_CONFIG_CHECK(data.size() % 12 == 0, "ConeVecProjectionGeometry3D", "Vectors doesn't consist of 12-tuples."); + m_iProjectionAngleCount = data.size() / 12; + m_pProjectionAngles = new SConeProjection[m_iProjectionAngleCount]; + + for (int i = 0; i < m_iProjectionAngleCount; ++i) { + SConeProjection& p = m_pProjectionAngles[i]; + p.fSrcX = data[12*i + 0]; + p.fSrcY = data[12*i + 1]; + p.fSrcZ = data[12*i + 2]; + p.fDetUX = data[12*i + 6]; + p.fDetUY = data[12*i + 7]; + p.fDetUZ = data[12*i + 8]; + p.fDetVX = data[12*i + 9]; + p.fDetVY = data[12*i + 10]; + p.fDetVZ = data[12*i + 11]; + + // The backend code currently expects the corner of the detector, while + // the matlab interface supplies the center + p.fDetSX = data[12*i + 3] - 0.5f * m_iDetectorRowCount * p.fDetVX - 0.5f * m_iDetectorColCount * p.fDetUX; + p.fDetSY = data[12*i + 4] - 0.5f * m_iDetectorRowCount * p.fDetVY - 0.5f * m_iDetectorColCount * p.fDetUY; + p.fDetSZ = data[12*i + 5] - 0.5f * m_iDetectorRowCount * p.fDetVZ - 0.5f * m_iDetectorColCount * p.fDetUZ; + } + + // success + m_bInitialized = _check(); + return m_bInitialized; +} + +//---------------------------------------------------------------------------------------- +// Initialization. +bool CConeVecProjectionGeometry3D::initialize(int _iProjectionAngleCount, + int _iDetectorRowCount, + int _iDetectorColCount, + const SConeProjection* _pProjectionAngles) +{ + m_iProjectionAngleCount = _iProjectionAngleCount; + m_iDetectorRowCount = _iDetectorRowCount; + m_iDetectorColCount = _iDetectorColCount; + m_pProjectionAngles = new SConeProjection[m_iProjectionAngleCount]; + for (int i = 0; i < m_iProjectionAngleCount; ++i) + m_pProjectionAngles[i] = _pProjectionAngles[i]; + + // TODO: check? + + // success + m_bInitialized = _check(); + return m_bInitialized; +} + +//---------------------------------------------------------------------------------------- +// Clone +CProjectionGeometry3D* CConeVecProjectionGeometry3D::clone() const +{ + CConeVecProjectionGeometry3D* res = new CConeVecProjectionGeometry3D(); + res->m_bInitialized = m_bInitialized; + res->m_iProjectionAngleCount = m_iProjectionAngleCount; + res->m_iDetectorRowCount = m_iDetectorRowCount; + res->m_iDetectorColCount = m_iDetectorColCount; + res->m_iDetectorTotCount = m_iDetectorTotCount; + res->m_fDetectorSpacingX = m_fDetectorSpacingX; + res->m_fDetectorSpacingY = m_fDetectorSpacingY; + res->m_pProjectionAngles = new SConeProjection[m_iProjectionAngleCount]; + memcpy(res->m_pProjectionAngles, m_pProjectionAngles, sizeof(m_pProjectionAngles[0])*m_iProjectionAngleCount); + return res; +} + +//---------------------------------------------------------------------------------------- +// is equal +bool CConeVecProjectionGeometry3D::isEqual(const CProjectionGeometry3D * _pGeom2) const +{ + if (_pGeom2 == NULL) return false; + + // try to cast argument to CConeProjectionGeometry3D + const CConeVecProjectionGeometry3D* pGeom2 = dynamic_cast(_pGeom2); + if (pGeom2 == NULL) return false; + + // both objects must be initialized + if (!m_bInitialized || !pGeom2->m_bInitialized) return false; + + // check all values + if (m_iProjectionAngleCount != pGeom2->m_iProjectionAngleCount) return false; + if (m_iDetectorRowCount != pGeom2->m_iDetectorRowCount) return false; + if (m_iDetectorColCount != pGeom2->m_iDetectorColCount) return false; + if (m_iDetectorTotCount != pGeom2->m_iDetectorTotCount) return false; + //if (m_fDetectorSpacingX != pGeom2->m_fDetectorSpacingX) return false; + //if (m_fDetectorSpacingY != pGeom2->m_fDetectorSpacingY) return false; + + for (int i = 0; i < m_iProjectionAngleCount; ++i) { + if (memcmp(&m_pProjectionAngles[i], &pGeom2->m_pProjectionAngles[i], sizeof(m_pProjectionAngles[i])) != 0) return false; + } + + return true; +} + +//---------------------------------------------------------------------------------------- +// is of type +bool CConeVecProjectionGeometry3D::isOfType(const std::string& _sType) const +{ + return (_sType == "cone3d_vec"); +} + +//---------------------------------------------------------------------------------------- +void CConeVecProjectionGeometry3D::toXML(XMLNode* _sNode) const +{ + _sNode->addAttribute("type","cone3d_vec"); + _sNode->addChildNode("DetectorRowCount", m_iDetectorRowCount); + _sNode->addChildNode("DetectorColCount", m_iDetectorColCount); + // TODO: + //_sNode->addChildNode("ProjectionAngles", m_pfProjectionAngles, m_iProjectionAngleCount); +} + +CVector3D CConeVecProjectionGeometry3D::getProjectionDirection(int _iProjectionIndex, int _iDetectorIndex) const +{ + const SConeProjection& p = m_pProjectionAngles[_iProjectionIndex]; + int u = _iDetectorIndex % m_iDetectorColCount; + int v = _iDetectorIndex / m_iDetectorColCount; + + return CVector3D(p.fDetSX + (u+0.5)*p.fDetUX + (v+0.5)*p.fDetVX - p.fSrcX, p.fDetSY + (u+0.5)*p.fDetUY + (v+0.5)*p.fDetVY - p.fSrcY, p.fDetSZ + (u+0.5)*p.fDetUZ + (v+0.5)*p.fDetVZ - p.fSrcZ); +} + + +//---------------------------------------------------------------------------------------- + +bool CConeVecProjectionGeometry3D::_check() +{ + // TODO + return true; +} + +} // end namespace astra -- cgit v1.2.3