diff --git a/crates/specialized/rtx-fea/tests/flag3d_structure.rs b/crates/specialized/rtx-fea/tests/flag3d_structure.rs index 0bfb4eb..38ea1fd 100644 --- a/crates/specialized/rtx-fea/tests/flag3d_structure.rs +++ b/crates/specialized/rtx-fea/tests/flag3d_structure.rs @@ -355,6 +355,34 @@ fn plane_strain_3d_reproduces_the_2d_csm1() { assert!(rel(uy2, -66.1029e-3) < 0.02 && rel(ux2, -7.18777e-3) < 0.04); } +/// The free-lateral-face path, pinned: a narrow strip (span 0.02 = the +/// thickness) under CSM1 gravity. Measured with `flag3d_csm1_table` +/// (R8-b, 2026-09-25): u_y(A) = −76.340e-3 — softer than plane strain +/// (−65.141e-3) because the free faces relax the spanwise stress. +#[test] +fn free_lateral_faces_csm1_strip_pin() { + let tip = static_3d_csm1( + Flag3dSpec::turek_hron(0.02, -0.01, 35, 2, 1), + LateralFaces::Free, + 5, + ); + println!( + " CSM1 35x2x1 span 0.02 free faces: u(A) = ({:.6e}, {:.6e}, {:.2e})", + tip.a.x, tip.a.y, tip.a.z + ); + assert!(rel(tip.a.y, -76.340_06e-3) < 1e-5, "uy {}", tip.a.y); + assert!(rel(tip.a.x, -9.680_464e-3) < 1e-5, "ux {}", tip.a.x); + assert!( + tip.a.z.abs() < 1e-12, + "mid-span must not move in z: {}", + tip.a.z + ); + assert!( + (tip.side_low.y - tip.side_high.y).abs() < 1e-12, + "span symmetry" + ); +} + fn csm3_2d(dt: f64) -> (NonlinearDynamicAnalysis, NodeId) { let mesh = quad8_flag(35, 2); let a = point_2d(&mesh, 0.6, 0.2);