25 const std::filesystem::path root(
argv[1]);
26 const auto folder = std::filesystem::temp_directory_path() /
27 (
"bicrystal-boundary-topology-" + std::to_string(std::chrono::steady_clock::now().time_since_epoch().count()));
28 const auto input = folder /
"inputFiles";
29 std::filesystem::create_directories(input);
30 std::filesystem::create_directories(folder /
"F");
31 std::filesystem::copy_file(root /
"Library/Materials/W.txt", input /
"W.txt");
33 std::filesystem::copy_file(root /
"Library/Meshes/bicrystal_48.msh", input /
"mesh.msh");
34 std::filesystem::copy_file(root /
"Library/DislocationDynamics/DD.txt", input /
"DD.txt");
35 std::filesystem::create_directories(folder /
"config");
36 const double length=3671.9477120460206;
38 std::ofstream
f(input /
"DefectiveCrystal.txt");
39 f <<
"physics=DislocationDynamics;\nuseFEM=0;\nNsteps=0;\nmaxResolveSteps=0;\ndtMax=1;\noutputFrequency=1;\noutputBinary=0;\nstartAtTimeStep=0;\nperiodicImageSize=0 0 0;\nEwaldLengthFactor=0;\n";
40 std::ofstream
p(input /
"polycrystal.txt");
41 p << std::setprecision(17) <<
"materialFile=W.txt;\nmeshFile=mesh.msh;\nabsoluteTemperature=300;\nC2G1=1 0 0 0 1 0 0 0 1;\n"
42 <<
"C2G2=0.8 0 0.6 0 1 0 -0.6 0 0.8;\nF=" << length <<
" 0 0 0 " << length <<
" 0 0 0 " << length
43 <<
";\nX0=0 0 0;\nperiodicFaceIDs=-1;\n";
47 const auto dd=input/
"DD.txt";
48 std::ifstream source(dd);
49 std::string contents((std::istreambuf_iterator<char>(source)),std::istreambuf_iterator<char>());
50 const auto location=contents.find(
"Lmax=100;");
51 require(location!=std::string::npos,
"Expected library remeshing default");
52 contents.replace(location,std::string(
"Lmax=100;").size(),
"Lmax=150;");
53 std::ofstream output(dd);
56 for(
int frame : {430,433})
62 std::ifstream stream(root/
"tests/data"/(
"bicrystalBoundary"+std::to_string(frame)+
".txt"));
63 require(
bool(stream),
"Missing bicrystal boundary regression fixture");
66 using V=Eigen::Vector3d;
67 const auto areas=[&]()
70 for(
const auto& entry : network.
loops())
73 for(
const auto* link : entry.second.lock()->linkSequence())
75 area+=0.5*link->source->get_P().cross(link->sink->get_P());
81 const auto check=[&](
const std::map<size_t,V>& before,
double tolerance)
83 const auto after=areas();
84 require(after.size()==7 && after.size()==before.size(),
"Boundary update split or lost a loop");
85 for(
const auto& entry : before)
87 require((after.at(entry.first)-entry.second).norm()<tolerance*std::max(1.0,entry.second.norm()),
88 "Boundary walk jumped to another contour branch");
90 for(
const auto& entry : network.
loopNodes())
92 const auto node=entry.second.lock();
93 require((node->get_P()+node->periodicPlanePatch()->shift-node->networkNode->get_P()).norm()<1.e-7,
94 "Loop/network periodic mapping is inconsistent");
97 const auto initial=areas();
99 check(initial,1.e-10);
101 check(initial,1.e-10);
107 const auto node=entry.second.lock();
108 node->trySet_P(node->get_P()+16.95870980823875*node->get_V());
110 const auto trial=areas();
114 const auto clipped=areas();
116 check(clipped,1.e-10);
117 const auto plasticArea=[&]()
119 Eigen::Matrix3d
result=Eigen::Matrix3d::Zero();
120 for(
const auto& entry : areas())
122 result+=network.
loops().at(entry.first).lock()->burgers()*entry.second.transpose();
126 const Eigen::Matrix3d plasticBefore=plasticArea();
128 require((plasticArea()-plasticBefore).norm()<1.e-3*std::max(1.0,plasticBefore.norm()),
129 "Junction formation changed Burgers-weighted slipped area");
132 V areaBefore=V::Zero();
133 V areaAfter=V::Zero();
134 for(
const auto& entry : clipped)
136 areaBefore+=entry.second;
138 for(
const auto& entry : areas())
140 areaAfter+=entry.second;
142 require((areaAfter-areaBefore).norm()<1.e-3*std::max(1.0,areaBefore.norm()),
143 "Junction formation changed retained oriented area");
144 for(
const auto& entry : network.
loops())
146 require(entry.second.lock()->isLoop(),
"Junction formation broke loop closure");
148 for(
const auto& entry : network.
loopNodes())
150 const auto node=entry.second.lock();
151 require((node->get_P()+node->periodicPlanePatch()->shift-node->networkNode->get_P()).norm()<1.e-7,
152 "Junction formation broke periodic mapping");
154 std::cout<<
"PASS: bicrystal frame "<<frame<<
" topology, mapping, area and remeshing\n";
156 std::filesystem::remove_all(folder);
159 catch(
const std::exception& error)
161 std::cerr<<error.what()<<
'\n';