Mechanics of Defect Evolution Library
Loading...
Searching...
No Matches
DislocationLoopLink.cpp
Go to the documentation of this file.
1/* This file is part of MoDELib, the Mechanics Of Defects Evolution Library.
2 *
3 *
4 * MoDELib is distributed without any warranty under the
5 * GNU General Public License (GPL) v2 <http://www.gnu.org/licenses/>.
6 */
7
8#ifndef model_DislocationLoopLink_cpp_
9#define model_DislocationLoopLink_cpp_
10
11#include <DislocationLoopLink.h>
12
13namespace model
14{
15
16 template <int dim>
17 DislocationLoopLink<dim>::DislocationLoopLink(const std::shared_ptr<LoopNodeType>& so,
18 const std::shared_ptr<LoopNodeType>& si,
19 const std::shared_ptr<LoopType>& pL) :
20 /* init */ LoopLink<LoopLinkType>(so,si,pL)
21 {
22
23
24 }
25
26 template <int dim>
28 {
29 // return !((this->source->get_P()-this->sink->get_P()).squaredNorm()<FLT_EPSILON
30 // /* */ && this->source->periodicPlaneEdge
31 // /* */ && this->sink->periodicPlaneEdge
32 // /* */ && this->source->loop()->sID==this->sink->loop()->sID);
33
34 if(this->source->networkNode==this->sink->networkNode)
35 {
36 return false;
37 }
38
39 if ( this->source->periodicPlaneEdge.first
40 && this->sink->periodicPlaneEdge.first
41 && this->source->periodicPlanePatch()!=this->sink->periodicPlanePatch())
42 {
43 return false;
44 }
45
46// if (this->source->periodicPlaneEdge.first && this->sink->periodicPlaneEdge.first)
47// {
48// // bool temp((this->source->loop()->sID==this->sink->loop()->sID));
49// // if (temp)
50// // {
51// // std::cout<<"Checking Twin"<<std::endl;
52// // std::cout<<this->source->periodicPlaneEdge->twin->tag()<<"=>= " <<this->sink->periodicPlaneEdge->tag()<<std::endl;
53// // std::cout<<this->sink->periodicPlaneEdge->twin->tag()<<"=>= " <<this->source->periodicPlaneEdge->tag()<<std::endl;
54// // std::cout<<" Case A"<<std::flush;
55// if (this->source->periodicPlaneEdge.first->twin && this->sink->periodicPlaneEdge.first->twin)
56// {
57// // std::cout<<".1"<<std::endl;
58// // temp *= ((this->source->periodicPlaneEdge->twin == this->sink->periodicPlaneEdge.get()) &&
59// // (this->sink->periodicPlaneEdge->twin == this->source->periodicPlaneEdge.get()));
60// const bool firstEdgeMatch((this->source->periodicPlaneEdge.first->twin == this->sink->periodicPlaneEdge.first.get()) &&
61// (this->sink->periodicPlaneEdge.first->twin == this->source->periodicPlaneEdge.first.get()));
62// if (firstEdgeMatch && this->source->periodicPlaneEdge.second && this->sink->periodicPlaneEdge.second)
63// {
64// if (this->source->periodicPlaneEdge.second->twin && this->sink->periodicPlaneEdge.second->twin)
65// {
66// const bool secondEdgeMatch((this->source->periodicPlaneEdge.second->twin == this->sink->periodicPlaneEdge.second.get()) &&
67// (this->sink->periodicPlaneEdge.second->twin == this->source->periodicPlaneEdge.second.get()));
68// assert(secondEdgeMatch && "Second edge must match provided first edge match for network link creation");
69// }
70// }
71//
72// return !firstEdgeMatch;
73// }
74// }
75 return true;
76 }
77
78 template <int dim>
79 std::shared_ptr<PeriodicPlanePatch<dim>> DislocationLoopLink<dim>::periodicPlanePatch() const
80 {
81
82 return (this->source->periodicPlanePatch()==this->sink->periodicPlanePatch())? this->source->periodicPlanePatch() : std::shared_ptr<PeriodicPlanePatch<dim>>(nullptr);
83
84 }
85
86template <int dim>
88{
89 const auto controlPoint=[&](const bool before)->VectorDim
90 {
91 const LoopNodeType* node=before ? this->source.get() : this->sink.get();
92 bool backwards=before;
93 VectorDim offset=VectorDim::Zero();
94 std::set<std::pair<const LoopNodeType*,bool>> visited;
95 while(visited.emplace(node,backwards).second)
96 {
97 const auto* adjacent=backwards ? node->prev.second : node->next.second;
98 if(const auto* twin=adjacent->twin())
99 {
100 // Preserve the existing same-loop periodic continuation.
101 const auto* neighbor=backwards ? twin->source->periodicPrev() : twin->sink->periodicNext();
102 if(neighbor)
103 {
104 return offset+neighbor->get_P()-node->periodicPlanePatch()->shift+neighbor->periodicPlanePatch()->shift;
105 }
106 break;
107 }
108 if(const auto* twin=adjacent->twinnedLink())
109 {
110 // A two-link zero-Burgers connection is artificial. Switch at
111 // this endpoint, then follow the other loop away from it.
112 // Match network endpoints rather than assuming equal loop
113 // orientations: opposite Burgers vectors can also cancel.
114 const bool atSource=twin->source->networkNode==node->networkNode;
115 const auto* other=atSource ? twin->source.get() : twin->sink.get();
116 offset+=node->get_P()-other->get_P();
117 node=other;
118 backwards=atSource;
119 continue;
120 }
121 const auto* neighbor=backwards ? node->periodicPrev() : node->periodicNext();
122 if(neighbor)
123 {
124 return offset+neighbor->get_P();
125 }
126 break;
127 }
128 // A closed chain of cancelling links has no unique continuation.
129 // Retain the loop-local control point rather than circulating forever.
130 const auto* neighbor=before ? this->source->periodicPrev() : this->sink->periodicNext();
131 if(!neighbor)
132 {
133 throw std::runtime_error("Cannot determine spline control point.");
134 }
135 return neighbor->get_P();
136 };
137 return CatmullRomSplineSegment<dim>(controlPoint(true),this->source->get_P(),this->sink->get_P(),controlPoint(false));
138}
139
140
141 template <int dim>
142 void DislocationLoopLink<dim>::initFromFile(const std::string& fileName)
143 {
144 verboseDislocationLoopLink=TextFileParser(fileName).readScalar<int>("verboseDislocationLoopLink",false);
145 }
146
147 template <int dim>
149 {
150 if (hasNetworkLink())
151 {
152 if (this->networkLink()->loopLinks().size()==2 && this->networkLink()->hasZeroBurgers())
153 {
154 if (*this->networkLink()->loopLinks().begin()==this)
155 {
156 return (*this->networkLink()->loopLinks().rbegin());
157 }
158 else
159 {
160 return (*this->networkLink()->loopLinks().begin());
161 }
162
163 }
164 else
165 {
166 return nullptr;
167 }
168
169 }
170 else
171 {
172 return nullptr;
173 }
174
175 }
176
177 template <int dim>
179
180 template class DislocationLoopLink<3>;
181
182}
183#endif
Scalar readScalar(const std::string &key, const bool &verbose=false)
struct otri neighbor