diff options
author | Ruben Undheim <ruben.undheim@gmail.com> | 2016-07-05 18:02:38 +0200 |
---|---|---|
committer | Ruben Undheim <ruben.undheim@gmail.com> | 2016-07-05 18:02:38 +0200 |
commit | ef962f6008f25ab7cbd4ca21bcc72b97a1e2d76f (patch) | |
tree | 8149bee93d1a3f91d4503bfb3853adac4af0a85e /openEMS/FDTD/extensions/operator_ext_excitation.cpp |
Imported Upstream version 0.0.34
Diffstat (limited to 'openEMS/FDTD/extensions/operator_ext_excitation.cpp')
-rw-r--r-- | openEMS/FDTD/extensions/operator_ext_excitation.cpp | 372 |
1 files changed, 372 insertions, 0 deletions
diff --git a/openEMS/FDTD/extensions/operator_ext_excitation.cpp b/openEMS/FDTD/extensions/operator_ext_excitation.cpp new file mode 100644 index 0000000..d2085ff --- /dev/null +++ b/openEMS/FDTD/extensions/operator_ext_excitation.cpp @@ -0,0 +1,372 @@ +/* +* Copyright (C) 2011 Thorsten Liebig (Thorsten.Liebig@gmx.de) +* +* This program 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. +* +* This program 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 this program. If not, see <http://www.gnu.org/licenses/>. +*/ + +#include "operator_ext_excitation.h" +#include "engine_ext_excitation.h" +#include "FDTD/excitation.h" +#include "ContinuousStructure.h" + +#include "CSPrimCurve.h" +#include "CSPropExcitation.h" + +Operator_Ext_Excitation::Operator_Ext_Excitation(Operator* op) : Operator_Extension(op) +{ + Init(); +} + +Operator_Ext_Excitation::~Operator_Ext_Excitation() +{ + Reset(); +} + +Operator_Extension* Operator_Ext_Excitation::Clone(Operator* op) +{ + Operator_Ext_Excitation* clone = new Operator_Ext_Excitation(op, this); + return clone; +} + +void Operator_Ext_Excitation::Init() +{ + Operator_Extension::Init(); + Volt_delay = 0; + Volt_amp = 0; + Volt_dir = 0; + Volt_Count = 0; + Curr_delay = 0; + Curr_amp = 0; + Curr_dir = 0; + Curr_Count = 0; + + for (int n=0; n<3; ++n) + { + Volt_index[n] = 0; + Curr_index[n] = 0; + Volt_Count_Dir[n] = 0; + Curr_Count_Dir[n] = 0; + } + m_Exc = 0; +} + +void Operator_Ext_Excitation::Reset() +{ + Operator_Extension::Reset(); + delete[] Volt_delay; + Volt_delay = 0; + delete[] Volt_dir; + Volt_dir = 0; + delete[] Volt_amp; + Volt_amp = 0; + delete[] Curr_delay; + Curr_delay = 0; + delete[] Curr_dir; + Curr_dir = 0; + delete[] Curr_amp; + Curr_amp = 0; + + Volt_Count = 0; + Curr_Count = 0; + + for (int n=0; n<3; ++n) + { + delete[] Volt_index[n]; + Volt_index[n] = 0; + delete[] Curr_index[n]; + Curr_index[n] = 0; + + Volt_Count_Dir[n] = 0; + Curr_Count_Dir[n] = 0; + } +} + + +Operator_Ext_Excitation::Operator_Ext_Excitation(Operator* op, Operator_Ext_Excitation* op_ext) : Operator_Extension(op, op_ext) +{ + Init(); +} + +bool Operator_Ext_Excitation::BuildExtension() +{ + m_Exc = m_Op->GetExcitationSignal(); + double dT = m_Op->GetTimestep(); + if (dT==0) + return false; + if (m_Exc==0) + return false; + + Reset(); + ContinuousStructure* CSX = m_Op->GetGeometryCSX(); + + unsigned int pos[3]; + double amp=0; + + vector<unsigned int> volt_vIndex[3]; + vector<FDTD_FLOAT> volt_vExcit; + vector<unsigned int> volt_vDelay; + vector<unsigned int> volt_vDir; + double volt_coord[3]; + + vector<unsigned int> curr_vIndex[3]; + vector<FDTD_FLOAT> curr_vExcit; + vector<unsigned int> curr_vDelay; + vector<unsigned int> curr_vDir; + double curr_coord[3]; + + vector<CSProperties*> vec_prop = CSX->GetPropertyByType(CSProperties::EXCITATION); + + if (vec_prop.size()==0) + { + cerr << "Operator::CalcFieldExcitation: Warning, no excitation properties found" << endl; + return false; + } + + CSPropExcitation* elec=NULL; + CSProperties* prop=NULL; + int priority=0; + + unsigned int numLines[] = {m_Op->GetNumberOfLines(0,true),m_Op->GetNumberOfLines(1,true),m_Op->GetNumberOfLines(2,true)}; + + for (pos[2]=0; pos[2]<numLines[2]; ++pos[2]) + { + for (pos[1]=0; pos[1]<numLines[1]; ++pos[1]) + { + for (pos[0]=0; pos[0]<numLines[0]; ++pos[0]) + { + //electric field excite + for (int n=0; n<3; ++n) + { + if (m_Op->GetYeeCoords(n,pos,volt_coord,false)==false) + continue; + if (m_CC_R0_included && (n==2) && (pos[0]==0)) + volt_coord[1] = m_Op->GetDiscLine(1,0); + + if (m_CC_R0_included && (n==1) && (pos[0]==0)) + continue; + + for (size_t p=0; p<vec_prop.size(); ++p) + { + prop = vec_prop.at(p); + elec = prop->ToExcitation(); + if (elec==NULL) + continue; + if (prop->CheckCoordInPrimitive(volt_coord,priority,true)) + { + if ((elec->GetActiveDir(n)) && ( (elec->GetExcitType()==0) || (elec->GetExcitType()==1) ))//&& (pos[n]<numLines[n]-1)) + { + amp = elec->GetWeightedExcitation(n,volt_coord)*m_Op->GetEdgeLength(n,pos);// delta[n]*gridDelta; + if (amp!=0) + { + volt_vExcit.push_back(amp); + volt_vDelay.push_back((unsigned int)(elec->GetDelay()/dT)); + volt_vDir.push_back(n); + volt_vIndex[0].push_back(pos[0]); + volt_vIndex[1].push_back(pos[1]); + volt_vIndex[2].push_back(pos[2]); + } + if (elec->GetExcitType()==1) //hard excite + { + m_Op->SetVV(n,pos[0],pos[1],pos[2], 0 ); + m_Op->SetVI(n,pos[0],pos[1],pos[2], 0 ); + } + } + } + } + } + + //magnetic field excite + for (int n=0; n<3; ++n) + { + if ((pos[0]>=numLines[0]-1) || (pos[1]>=numLines[1]-1) || (pos[2]>=numLines[2]-1)) + continue; //skip the last H-Line which is outside the FDTD-domain + if (m_Op->GetYeeCoords(n,pos,curr_coord,true)==false) + continue; + for (size_t p=0; p<vec_prop.size(); ++p) + { + prop = vec_prop.at(p); + elec = prop->ToExcitation(); + if (elec==NULL) + continue; + if (prop->CheckCoordInPrimitive(curr_coord,priority,true)) + { + if ((elec->GetActiveDir(n)) && ( (elec->GetExcitType()==2) || (elec->GetExcitType()==3) )) + { + amp = elec->GetWeightedExcitation(n,curr_coord)*m_Op->GetEdgeLength(n,pos,true);// delta[n]*gridDelta; + if (amp!=0) + { + curr_vExcit.push_back(amp); + curr_vDelay.push_back((unsigned int)(elec->GetDelay()/dT)); + curr_vDir.push_back(n); + curr_vIndex[0].push_back(pos[0]); + curr_vIndex[1].push_back(pos[1]); + curr_vIndex[2].push_back(pos[2]); + } + if (elec->GetExcitType()==3) //hard excite + { + m_Op->SetII(n,pos[0],pos[1],pos[2], 0 ); + m_Op->SetIV(n,pos[0],pos[1],pos[2], 0 ); + } + } + } + } + } + + } + } + } + + //special treatment for primitives of type curve (treated as wires) see also Calc_PEC + double p1[3]; + double p2[3]; + Grid_Path path; + for (size_t p=0; p<vec_prop.size(); ++p) + { + prop = vec_prop.at(p); + elec = prop->ToExcitation(); + for (size_t n=0; n<prop->GetQtyPrimitives(); ++n) + { + CSPrimitives* prim = prop->GetPrimitive(n); + CSPrimCurve* curv = prim->ToCurve(); + if (curv) + { + for (size_t i=1; i<curv->GetNumberOfPoints(); ++i) + { + curv->GetPoint(i-1,p1,m_Op->m_MeshType); + curv->GetPoint(i,p2,m_Op->m_MeshType); + path = m_Op->FindPath(p1,p2); + if (path.dir.size()>0) + prim->SetPrimitiveUsed(true); + for (size_t t=0; t<path.dir.size(); ++t) + { + n = path.dir.at(t); + pos[0] = path.posPath[0].at(t); + pos[1] = path.posPath[1].at(t); + pos[2] = path.posPath[2].at(t); + m_Op->GetYeeCoords(n,pos,volt_coord,false); + if (elec!=NULL) + { + if ((elec->GetActiveDir(n)) && (pos[n]<numLines[n]-1) && ( (elec->GetExcitType()==0) || (elec->GetExcitType()==1) )) + { + amp = elec->GetWeightedExcitation(n,volt_coord)*m_Op->GetEdgeLength(n,pos); + if (amp!=0) + { + volt_vExcit.push_back(amp); + volt_vDelay.push_back((unsigned int)(elec->GetDelay()/dT)); + volt_vDir.push_back(n); + volt_vIndex[0].push_back(pos[0]); + volt_vIndex[1].push_back(pos[1]); + volt_vIndex[2].push_back(pos[2]); + } + if (elec->GetExcitType()==1) //hard excite + { + m_Op->SetVV(n,pos[0],pos[1],pos[2], 0 ); + m_Op->SetVI(n,pos[0],pos[1],pos[2], 0 ); + } + } + } + } + } + } + } + } + + // set voltage excitations + setupVoltageExcitation( volt_vIndex, volt_vExcit, volt_vDelay, volt_vDir ); + + // set current excitations + setupCurrentExcitation( curr_vIndex, curr_vExcit, curr_vDelay, curr_vDir ); + + return true; +} + +void Operator_Ext_Excitation::setupVoltageExcitation( vector<unsigned int> const volt_vIndex[3], vector<FDTD_FLOAT> const& volt_vExcit, + vector<unsigned int> const& volt_vDelay, vector<unsigned int> const& volt_vDir ) +{ + Volt_Count = volt_vIndex[0].size(); + for (int n=0; n<3; n++) + { + Volt_Count_Dir[n]=0; + delete[] Volt_index[n]; + Volt_index[n] = new unsigned int[Volt_Count]; + } + delete[] Volt_delay; + delete[] Volt_amp; + delete[] Volt_dir; + Volt_delay = new unsigned int[Volt_Count]; + Volt_amp = new FDTD_FLOAT[Volt_Count]; + Volt_dir = new unsigned short[Volt_Count]; + +// cerr << "Excitation::setupVoltageExcitation(): Number of voltage excitation points: " << Volt_Count << endl; +// if (Volt_Count==0) +// cerr << "No E-Field/voltage excitation found!" << endl; + for (int n=0; n<3; n++) + for (unsigned int i=0; i<Volt_Count; i++) + Volt_index[n][i] = volt_vIndex[n].at(i); + for (unsigned int i=0; i<Volt_Count; i++) + { + Volt_delay[i] = volt_vDelay.at(i); + Volt_amp[i] = volt_vExcit.at(i); + Volt_dir[i] = volt_vDir.at(i); + ++Volt_Count_Dir[Volt_dir[i]]; + } +} + +void Operator_Ext_Excitation::setupCurrentExcitation( vector<unsigned int> const curr_vIndex[3], vector<FDTD_FLOAT> const& curr_vExcit, + vector<unsigned int> const& curr_vDelay, vector<unsigned int> const& curr_vDir ) +{ + Curr_Count = curr_vIndex[0].size(); + for (int n=0; n<3; n++) + { + Curr_Count_Dir[n]=0; + delete[] Curr_index[n]; + Curr_index[n] = new unsigned int[Curr_Count]; + } + delete[] Curr_delay; + delete[] Curr_amp; + delete[] Curr_dir; + Curr_delay = new unsigned int[Curr_Count]; + Curr_amp = new FDTD_FLOAT[Curr_Count]; + Curr_dir = new unsigned short[Curr_Count]; + +// cerr << "Excitation::setupCurrentExcitation(): Number of current excitation points: " << Curr_Count << endl; +// if (Curr_Count==0) +// cerr << "No H-Field/current excitation found!" << endl; + for (int n=0; n<3; ++n) + for (unsigned int i=0; i<Curr_Count; i++) + Curr_index[n][i] = curr_vIndex[n].at(i); + for (unsigned int i=0; i<Curr_Count; i++) + { + Curr_delay[i] = curr_vDelay.at(i); + Curr_amp[i] = curr_vExcit.at(i); + Curr_dir[i] = curr_vDir.at(i); + ++Curr_Count_Dir[Curr_dir[i]]; + } + +} + +Engine_Extension* Operator_Ext_Excitation::CreateEngineExtention() +{ + return new Engine_Ext_Excitation(this); +} + +void Operator_Ext_Excitation::ShowStat(ostream &ostr) const +{ + Operator_Extension::ShowStat(ostr); + cout << "Voltage excitations\t: " << Volt_Count << "\t (" << Volt_Count_Dir[0] << ", " << Volt_Count_Dir[1] << ", " << Volt_Count_Dir[2] << ")" << endl; + cout << "Current excitations\t: " << Curr_Count << "\t (" << Curr_Count_Dir[0] << ", " << Curr_Count_Dir[1] << ", " << Curr_Count_Dir[2] << ")" << endl; + cout << "Excitation Length (TS)\t: " << m_Exc->GetLength() << endl; + cout << "Excitation Length (s)\t: " << m_Exc->GetLength()*m_Op->GetTimestep() << endl; +} + |