168 lines
6.2 KiB
C++
168 lines
6.2 KiB
C++
|
|
#include <gtest/gtest.h>
|
||
|
|
#include "vde/brep/brep.h"
|
||
|
|
#include "vde/brep/modeling.h"
|
||
|
|
#include "vde/brep/brep_validate.h"
|
||
|
|
#include "vde/brep/sheet_metal.h"
|
||
|
|
#include "vde/curves/nurbs_surface.h"
|
||
|
|
|
||
|
|
using namespace vde::brep;
|
||
|
|
using namespace vde::core;
|
||
|
|
using namespace vde::curves;
|
||
|
|
|
||
|
|
namespace {
|
||
|
|
|
||
|
|
/// 创建默认钢板材料
|
||
|
|
SheetMetalMaterial make_steel() {
|
||
|
|
SheetMetalMaterial mat;
|
||
|
|
mat.name = "Steel_A36";
|
||
|
|
mat.yield_strength_mpa = 250.0;
|
||
|
|
mat.tensile_strength_mpa = 400.0;
|
||
|
|
mat.elastic_modulus_gpa = 200.0;
|
||
|
|
mat.poisson_ratio = 0.3;
|
||
|
|
return mat;
|
||
|
|
}
|
||
|
|
|
||
|
|
/// 创建默认铝板材料
|
||
|
|
SheetMetalMaterial make_aluminum() {
|
||
|
|
SheetMetalMaterial mat;
|
||
|
|
mat.name = "Aluminum_6061";
|
||
|
|
mat.yield_strength_mpa = 276.0;
|
||
|
|
mat.tensile_strength_mpa = 310.0;
|
||
|
|
mat.elastic_modulus_gpa = 68.9;
|
||
|
|
mat.poisson_ratio = 0.33;
|
||
|
|
return mat;
|
||
|
|
}
|
||
|
|
|
||
|
|
} // namespace
|
||
|
|
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
// K-Factor 测试
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, KFactor_Steel_ThinSheet) {
|
||
|
|
auto steel = make_steel();
|
||
|
|
double k = compute_k_factor(steel, 1.0, 1.0);
|
||
|
|
EXPECT_GT(k, 0.15);
|
||
|
|
EXPECT_LT(k, 0.5);
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, KFactor_Aluminum_ThickSheet) {
|
||
|
|
auto al = make_aluminum();
|
||
|
|
double k = compute_k_factor(al, 3.0, 3.0);
|
||
|
|
EXPECT_GT(k, 0.2);
|
||
|
|
EXPECT_LT(k, 0.5);
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, KFactor_LargeRadius_HigherK) {
|
||
|
|
auto steel = make_steel();
|
||
|
|
double k_small_r = compute_k_factor(steel, 1.0, 0.5);
|
||
|
|
double k_large_r = compute_k_factor(steel, 1.0, 5.0);
|
||
|
|
// Larger R/T ratio → higher K-factor
|
||
|
|
EXPECT_GE(k_large_r, k_small_r - 0.05);
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, KFactor_Simple_ReturnsRange) {
|
||
|
|
double k = compute_k_factor_simple(1.5, 2.0);
|
||
|
|
EXPECT_GT(k, 0.25);
|
||
|
|
EXPECT_LT(k, 0.5);
|
||
|
|
}
|
||
|
|
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
// 折弯计算测试
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, BendAllowance_90Degree_Positive) {
|
||
|
|
double ba = compute_bend_allowance(1.0, 1.0, 90.0, 0.33);
|
||
|
|
EXPECT_GT(ba, 0.0);
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, BendDeduction_90Degree_Positive) {
|
||
|
|
double bd = compute_bend_deduction(1.0, 1.0, 90.0, 0.33);
|
||
|
|
EXPECT_GT(bd, 0.0);
|
||
|
|
}
|
||
|
|
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
// 折弯扣除表测试
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, BendDeductionTable_GeneratesEntries) {
|
||
|
|
auto steel = make_steel();
|
||
|
|
auto table = bend_deduction_table(steel, 1.5);
|
||
|
|
EXPECT_GT(table.size(), 0u);
|
||
|
|
EXPECT_EQ(table.entries().size(), table.size());
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, BendDeductionTable_Lookup_ExactMatch) {
|
||
|
|
auto steel = make_steel();
|
||
|
|
auto table = bend_deduction_table(steel, 1.5, {1.0});
|
||
|
|
|
||
|
|
auto entry = table.lookup(1.5, 1.0, 90.0);
|
||
|
|
EXPECT_GT(entry.bend_deduction, 0.0);
|
||
|
|
EXPECT_DOUBLE_EQ(entry.bend_angle_deg, 90.0);
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, BendDeductionTable_Interpolated_Fallback) {
|
||
|
|
auto steel = make_steel();
|
||
|
|
auto table = bend_deduction_table(steel, 1.5, {1.0, 2.0});
|
||
|
|
|
||
|
|
auto entry = table.lookup_interpolated(1.5, 1.5, 90.0);
|
||
|
|
EXPECT_GT(entry.bend_deduction, 0.0);
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, BendDeductionTable_Angles_MultiAngle) {
|
||
|
|
auto steel = make_steel();
|
||
|
|
auto table = bend_deduction_table_angles(steel, 1.5, 2.0,
|
||
|
|
{30.0, 45.0, 60.0, 90.0, 120.0});
|
||
|
|
EXPECT_EQ(table.size(), 5u);
|
||
|
|
|
||
|
|
// 90° should have larger deduction than 30°
|
||
|
|
auto e30 = table.lookup(1.5, 2.0, 30.0);
|
||
|
|
auto e90 = table.lookup(1.5, 2.0, 90.0);
|
||
|
|
EXPECT_GT(e90.bend_deduction, e30.bend_deduction);
|
||
|
|
}
|
||
|
|
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
// 钣金展开测试
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, UnfoldSheetMetal_InvalidFace_ReturnsError) {
|
||
|
|
auto box = make_box(10, 5, 2);
|
||
|
|
auto result = unfold_sheet_metal(box, 999);
|
||
|
|
EXPECT_FALSE(result.success);
|
||
|
|
EXPECT_FALSE(result.errors.empty());
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, UnfoldSheetMetal_Box_NoCrash) {
|
||
|
|
auto box = make_box(10, 5, 2);
|
||
|
|
auto result = unfold_sheet_metal(box, 0);
|
||
|
|
// Box face 0 is planar; unfolding should succeed
|
||
|
|
EXPECT_TRUE(result.success);
|
||
|
|
EXPECT_GT(result.k_factor_used, 0.0);
|
||
|
|
}
|
||
|
|
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
// 法兰创建测试
|
||
|
|
// ═══════════════════════════════════════════════════════════
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, CreateFlange_InvalidEdge_ReturnsError) {
|
||
|
|
auto box = make_box(10, 5, 2);
|
||
|
|
auto result = create_flange(box, 999, 90.0, 5.0);
|
||
|
|
EXPECT_FALSE(result.success);
|
||
|
|
EXPECT_FALSE(result.errors.empty());
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, CreateFlange_ValidEdge_CreatesFlange) {
|
||
|
|
auto box = make_box(10, 5, 2);
|
||
|
|
// Use edge 0 (first edge of box)
|
||
|
|
auto result = create_flange(box, 0, 90.0, 5.0);
|
||
|
|
EXPECT_TRUE(result.success);
|
||
|
|
EXPECT_FALSE(result.new_face_ids.empty());
|
||
|
|
EXPECT_GT(result.body.num_faces(), box.num_faces());
|
||
|
|
}
|
||
|
|
|
||
|
|
TEST(SheetMetalTest, CreateFlange_ZeroLength_ReturnsError) {
|
||
|
|
auto box = make_box(10, 5, 2);
|
||
|
|
auto result = create_flange(box, 0, 90.0, 0.0);
|
||
|
|
EXPECT_FALSE(result.success);
|
||
|
|
}
|