| 10 | namespace |
| 11 | { |
| 12 | void UpdateNormalBetweenSegments(LineSegment * segment1, LineSegment * segment2) |
| 13 | { |
| 14 | ASSERT(segment1 != nullptr && segment2 != nullptr, ()); |
| 15 | |
| 16 | float const dotProduct = glsl::dot(segment1->m_leftNormals[EndPoint], segment2->m_leftNormals[StartPoint]); |
| 17 | float const absDotProduct = fabs(dotProduct); |
| 18 | float constexpr kEps = 1e-5; |
| 19 | |
| 20 | if (fabs(absDotProduct - 1.0f) < kEps) |
| 21 | { |
| 22 | // change nothing |
| 23 | return; |
| 24 | } |
| 25 | |
| 26 | float constexpr kMaxScalar = 5; |
| 27 | float const crossProduct = glsl::cross(glsl::vec3(segment1->m_tangent, 0), glsl::vec3(segment2->m_tangent, 0)).z; |
| 28 | if (crossProduct < 0) |
| 29 | { |
| 30 | segment1->m_hasLeftJoin[EndPoint] = true; |
| 31 | segment2->m_hasLeftJoin[StartPoint] = true; |
| 32 | |
| 33 | // change right-side normals |
| 34 | glsl::vec2 averageNormal = |
| 35 | glsl::normalize(segment1->m_rightNormals[EndPoint] + segment2->m_rightNormals[StartPoint]); |
| 36 | float const cosAngle = glsl::dot(segment1->m_tangent, averageNormal); |
| 37 | float const widthScalar = 1.0f / sqrt(1.0f - cosAngle * cosAngle); |
| 38 | if (widthScalar < kMaxScalar) |
| 39 | { |
| 40 | segment1->m_rightNormals[EndPoint] = averageNormal; |
| 41 | segment2->m_rightNormals[StartPoint] = averageNormal; |
| 42 | segment1->m_rightWidthScalar[EndPoint].x = widthScalar; |
| 43 | segment1->m_rightWidthScalar[EndPoint].y = widthScalar * cosAngle; |
| 44 | segment2->m_rightWidthScalar[StartPoint] = segment1->m_rightWidthScalar[EndPoint]; |
| 45 | } |
| 46 | else |
| 47 | { |
| 48 | segment1->m_generateJoin = false; |
| 49 | } |
| 50 | } |
| 51 | else |
| 52 | { |
| 53 | segment1->m_hasLeftJoin[EndPoint] = false; |
| 54 | segment2->m_hasLeftJoin[StartPoint] = false; |
| 55 | |
| 56 | // change left-side normals |
| 57 | glsl::vec2 averageNormal = glsl::normalize(segment1->m_leftNormals[EndPoint] + segment2->m_leftNormals[StartPoint]); |
| 58 | float const cosAngle = glsl::dot(segment1->m_tangent, averageNormal); |
| 59 | float const widthScalar = 1.0f / sqrt(1.0f - cosAngle * cosAngle); |
| 60 | if (widthScalar < kMaxScalar) |
| 61 | { |
| 62 | segment1->m_leftNormals[EndPoint] = averageNormal; |
| 63 | segment2->m_leftNormals[StartPoint] = averageNormal; |
| 64 | segment1->m_leftWidthScalar[EndPoint].x = widthScalar; |
| 65 | segment1->m_leftWidthScalar[EndPoint].y = widthScalar * cosAngle; |
| 66 | segment2->m_leftWidthScalar[StartPoint] = segment1->m_leftWidthScalar[EndPoint]; |
| 67 | } |
| 68 | else |
| 69 | { |
no test coverage detected