From 8f0dda5eab181b0f14f2652b4e984aaaae3f258c Mon Sep 17 00:00:00 2001 From: rtk0c Date: Mon, 27 Jun 2022 18:27:13 -0700 Subject: Start from a clean slate --- 3rdparty/imgui-node-editor/imgui_bezier_math.inl | 675 ----------------------- 1 file changed, 675 deletions(-) delete mode 100644 3rdparty/imgui-node-editor/imgui_bezier_math.inl (limited to '3rdparty/imgui-node-editor/imgui_bezier_math.inl') diff --git a/3rdparty/imgui-node-editor/imgui_bezier_math.inl b/3rdparty/imgui-node-editor/imgui_bezier_math.inl deleted file mode 100644 index 3020bdb..0000000 --- a/3rdparty/imgui-node-editor/imgui_bezier_math.inl +++ /dev/null @@ -1,675 +0,0 @@ -//------------------------------------------------------------------------------ -// VERSION 0.1 -// -// LICENSE -// This software is dual-licensed to the public domain and under the following -// license: you are granted a perpetual, irrevocable license to copy, modify, -// publish, and distribute this file as you see fit. -// -// CREDITS -// Written by Michal Cichon -//------------------------------------------------------------------------------ -# ifndef __IMGUI_BEZIER_MATH_INL__ -# define __IMGUI_BEZIER_MATH_INL__ -# pragma once - - -//------------------------------------------------------------------------------ -# include "imgui_bezier_math.h" -# include // used in ImCubicBezierFixedStep - - -//------------------------------------------------------------------------------ -template -inline T ImLinearBezier(const T& p0, const T& p1, float t) -{ - return p0 + t * (p1 - p0); -} - -template -inline T ImLinearBezierDt(const T& p0, const T& p1, float t) -{ - IM_UNUSED(t); - - return p1 - p0; -} - -template -inline T ImQuadraticBezier(const T& p0, const T& p1, const T& p2, float t) -{ - const auto a = 1 - t; - - return a * a * p0 + 2 * t * a * p1 + t * t * p2; -} - -template -inline T ImQuadraticBezierDt(const T& p0, const T& p1, const T& p2, float t) -{ - return 2 * (1 - t) * (p1 - p0) + 2 * t * (p2 - p1); -} - -template -inline T ImCubicBezier(const T& p0, const T& p1, const T& p2, const T& p3, float t) -{ - const auto a = 1 - t; - const auto b = a * a * a; - const auto c = t * t * t; - - return b * p0 + 3 * t * a * a * p1 + 3 * t * t * a * p2 + c * p3; -} - -template -inline T ImCubicBezierDt(const T& p0, const T& p1, const T& p2, const T& p3, float t) -{ - const auto a = 1 - t; - const auto b = a * a; - const auto c = t * t; - const auto d = 2 * t * a; - - return -3 * p0 * b + 3 * p1 * (b - d) + 3 * p2 * (d - c) + 3 * p3 * c; -} - -template -inline T ImCubicBezierSample(const T& p0, const T& p1, const T& p2, const T& p3, float t) -{ - const auto cp0_zero = ImLengthSqr(p1 - p0) < 1e-5f; - const auto cp1_zero = ImLengthSqr(p3 - p2) < 1e-5f; - - if (cp0_zero && cp1_zero) - return ImLinearBezier(p0, p3, t); - else if (cp0_zero) - return ImQuadraticBezier(p0, p2, p3, t); - else if (cp1_zero) - return ImQuadraticBezier(p0, p1, p3, t); - else - return ImCubicBezier(p0, p1, p2, p3, t); -} - -template -inline T ImCubicBezierSample(const ImCubicBezierPointsT& curve, float t) -{ - return ImCubicBezierSample(curve.P0, curve.P1, curve.P2, curve.P3, t); -} - -template -inline T ImCubicBezierTangent(const T& p0, const T& p1, const T& p2, const T& p3, float t) -{ - const auto cp0_zero = ImLengthSqr(p1 - p0) < 1e-5f; - const auto cp1_zero = ImLengthSqr(p3 - p2) < 1e-5f; - - if (cp0_zero && cp1_zero) - return ImLinearBezierDt(p0, p3, t); - else if (cp0_zero) - return ImQuadraticBezierDt(p0, p2, p3, t); - else if (cp1_zero) - return ImQuadraticBezierDt(p0, p1, p3, t); - else - return ImCubicBezierDt(p0, p1, p2, p3, t); -} - -template -inline T ImCubicBezierTangent(const ImCubicBezierPointsT& curve, float t) -{ - return ImCubicBezierTangent(curve.P0, curve.P1, curve.P2, curve.P3, t); -} - -template -inline float ImCubicBezierLength(const T& p0, const T& p1, const T& p2, const T& p3) -{ - // Legendre-Gauss abscissae with n=24 (x_i values, defined at i=n as the roots of the nth order Legendre polynomial Pn(x)) - static const float t_values[] = - { - -0.0640568928626056260850430826247450385909f, - 0.0640568928626056260850430826247450385909f, - -0.1911188674736163091586398207570696318404f, - 0.1911188674736163091586398207570696318404f, - -0.3150426796961633743867932913198102407864f, - 0.3150426796961633743867932913198102407864f, - -0.4337935076260451384870842319133497124524f, - 0.4337935076260451384870842319133497124524f, - -0.5454214713888395356583756172183723700107f, - 0.5454214713888395356583756172183723700107f, - -0.6480936519369755692524957869107476266696f, - 0.6480936519369755692524957869107476266696f, - -0.7401241915785543642438281030999784255232f, - 0.7401241915785543642438281030999784255232f, - -0.8200019859739029219539498726697452080761f, - 0.8200019859739029219539498726697452080761f, - -0.8864155270044010342131543419821967550873f, - 0.8864155270044010342131543419821967550873f, - -0.9382745520027327585236490017087214496548f, - 0.9382745520027327585236490017087214496548f, - -0.9747285559713094981983919930081690617411f, - 0.9747285559713094981983919930081690617411f, - -0.9951872199970213601799974097007368118745f, - 0.9951872199970213601799974097007368118745f - }; - - // Legendre-Gauss weights with n=24 (w_i values, defined by a function linked to in the Bezier primer article) - static const float c_values[] = - { - 0.1279381953467521569740561652246953718517f, - 0.1279381953467521569740561652246953718517f, - 0.1258374563468282961213753825111836887264f, - 0.1258374563468282961213753825111836887264f, - 0.1216704729278033912044631534762624256070f, - 0.1216704729278033912044631534762624256070f, - 0.1155056680537256013533444839067835598622f, - 0.1155056680537256013533444839067835598622f, - 0.1074442701159656347825773424466062227946f, - 0.1074442701159656347825773424466062227946f, - 0.0976186521041138882698806644642471544279f, - 0.0976186521041138882698806644642471544279f, - 0.0861901615319532759171852029837426671850f, - 0.0861901615319532759171852029837426671850f, - 0.0733464814110803057340336152531165181193f, - 0.0733464814110803057340336152531165181193f, - 0.0592985849154367807463677585001085845412f, - 0.0592985849154367807463677585001085845412f, - 0.0442774388174198061686027482113382288593f, - 0.0442774388174198061686027482113382288593f, - 0.0285313886289336631813078159518782864491f, - 0.0285313886289336631813078159518782864491f, - 0.0123412297999871995468056670700372915759f, - 0.0123412297999871995468056670700372915759f - }; - - static_assert(sizeof(t_values) / sizeof(*t_values) == sizeof(c_values) / sizeof(*c_values), ""); - - auto arc = [p0, p1, p2, p3](float t) - { - const auto p = ImCubicBezierDt(p0, p1, p2, p3, t); - const auto l = ImLength(p); - return l; - }; - - const auto z = 0.5f; - const auto n = sizeof(t_values) / sizeof(*t_values); - - auto accumulator = 0.0f; - for (size_t i = 0; i < n; ++i) - { - const auto t = z * t_values[i] + z; - accumulator += c_values[i] * arc(t); - } - - return z * accumulator; -} - -template -inline float ImCubicBezierLength(const ImCubicBezierPointsT& curve) -{ - return ImCubicBezierLength(curve.P0, curve.P1, curve.P2, curve.P3); -} - -template -inline ImCubicBezierSplitResultT ImCubicBezierSplit(const T& p0, const T& p1, const T& p2, const T& p3, float t) -{ - const auto z1 = t; - const auto z2 = z1 * z1; - const auto z3 = z1 * z1 * z1; - const auto s1 = z1 - 1; - const auto s2 = s1 * s1; - const auto s3 = s1 * s1 * s1; - - return ImCubicBezierSplitResultT - { - ImCubicBezierPointsT - { - p0, - z1 * p1 - s1 * p0, - z2 * p2 - 2 * z1 * s1 * p1 + s2 * p0, - z3 * p3 - 3 * z2 * s1 * p2 + 3 * z1 * s2 * p1 - s3 * p0 - }, - ImCubicBezierPointsT - { - z3 * p0 - 3 * z2 * s1 * p1 + 3 * z1 * s2 * p2 - s3 * p3, - z2 * p1 - 2 * z1 * s1 * p2 + s2 * p3, - z1 * p2 - s1 * p3, - p3, - } - }; -} - -template -inline ImCubicBezierSplitResultT ImCubicBezierSplit(const ImCubicBezierPointsT& curve, float t) -{ - return ImCubicBezierSplit(curve.P0, curve.P1, curve.P2, curve.P3, t); -} - -inline ImRect ImCubicBezierBoundingRect(const ImVec2& p0, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3) -{ - auto a = 3 * p3 - 9 * p2 + 9 * p1 - 3 * p0; - auto b = 6 * p0 - 12 * p1 + 6 * p2; - auto c = 3 * p1 - 3 * p0; - auto delta_squared = ImMul(b, b) - 4 * ImMul(a, c); - - auto tl = ImMin(p0, p3); - auto rb = ImMax(p0, p3); - -# define IM_VEC2_INDEX(v, i) *(&v.x + i) - - for (int i = 0; i < 2; ++i) - { - if (IM_VEC2_INDEX(a, i) == 0.0f) - continue; - - if (IM_VEC2_INDEX(delta_squared, i) >= 0) - { - auto delta = ImSqrt(IM_VEC2_INDEX(delta_squared, i)); - - auto t0 = (-IM_VEC2_INDEX(b, i) + delta) / (2 * IM_VEC2_INDEX(a, i)); - if (t0 > 0 && t0 < 1) - { - auto p = ImCubicBezier(IM_VEC2_INDEX(p0, i), IM_VEC2_INDEX(p1, i), IM_VEC2_INDEX(p2, i), IM_VEC2_INDEX(p3, i), t0); - IM_VEC2_INDEX(tl, i) = ImMin(IM_VEC2_INDEX(tl, i), p); - IM_VEC2_INDEX(rb, i) = ImMax(IM_VEC2_INDEX(rb, i), p); - } - - auto t1 = (-IM_VEC2_INDEX(b, i) - delta) / (2 * IM_VEC2_INDEX(a, i)); - if (t1 > 0 && t1 < 1) - { - auto p = ImCubicBezier(IM_VEC2_INDEX(p0, i), IM_VEC2_INDEX(p1, i), IM_VEC2_INDEX(p2, i), IM_VEC2_INDEX(p3, i), t1); - IM_VEC2_INDEX(tl, i) = ImMin(IM_VEC2_INDEX(tl, i), p); - IM_VEC2_INDEX(rb, i) = ImMax(IM_VEC2_INDEX(rb, i), p); - } - } - } - -# undef IM_VEC2_INDEX - - return ImRect(tl, rb); -} - -inline ImRect ImCubicBezierBoundingRect(const ImCubicBezierPoints& curve) -{ - return ImCubicBezierBoundingRect(curve.P0, curve.P1, curve.P2, curve.P3); -} - -inline ImProjectResult ImProjectOnCubicBezier(const ImVec2& point, const ImVec2& p0, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const int subdivisions) -{ - // http://pomax.github.io/bezierinfo/#projections - - const float epsilon = 1e-5f; - const float fixed_step = 1.0f / static_cast(subdivisions - 1); - - ImProjectResult result; - result.Point = point; - result.Time = 0.0f; - result.Distance = FLT_MAX; - - // Step 1: Coarse check - for (int i = 0; i < subdivisions; ++i) - { - auto t = i * fixed_step; - auto p = ImCubicBezier(p0, p1, p2, p3, t); - auto s = point - p; - auto d = ImDot(s, s); - - if (d < result.Distance) - { - result.Point = p; - result.Time = t; - result.Distance = d; - } - } - - if (result.Time == 0.0f || ImFabs(result.Time - 1.0f) <= epsilon) - { - result.Distance = ImSqrt(result.Distance); - return result; - } - - // Step 2: Fine check - auto left = result.Time - fixed_step; - auto right = result.Time + fixed_step; - auto step = fixed_step * 0.1f; - - for (auto t = left; t < right + step; t += step) - { - auto p = ImCubicBezier(p0, p1, p2, p3, t); - auto s = point - p; - auto d = ImDot(s, s); - - if (d < result.Distance) - { - result.Point = p; - result.Time = t; - result.Distance = d; - } - } - - result.Distance = ImSqrt(result.Distance); - - return result; -} - -inline ImProjectResult ImProjectOnCubicBezier(const ImVec2& p, const ImCubicBezierPoints& curve, const int subdivisions) -{ - return ImProjectOnCubicBezier(p, curve.P0, curve.P1, curve.P2, curve.P3, subdivisions); -} - -inline ImCubicBezierIntersectResult ImCubicBezierLineIntersect(const ImVec2& p0, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& a0, const ImVec2& a1) -{ - auto cubic_roots = [](float a, float b, float c, float d, float* roots) -> int - { - int count = 0; - - auto sign = [](float x) -> float { return x < 0 ? -1.0f : 1.0f; }; - - auto A = b / a; - auto B = c / a; - auto C = d / a; - - auto Q = (3 * B - ImPow(A, 2)) / 9; - auto R = (9 * A * B - 27 * C - 2 * ImPow(A, 3)) / 54; - auto D = ImPow(Q, 3) + ImPow(R, 2); // polynomial discriminant - - if (D >= 0) // complex or duplicate roots - { - auto S = sign(R + ImSqrt(D)) * ImPow(ImFabs(R + ImSqrt(D)), (1.0f / 3.0f)); - auto T = sign(R - ImSqrt(D)) * ImPow(ImFabs(R - ImSqrt(D)), (1.0f / 3.0f)); - - roots[0] = -A / 3 + (S + T); // real root - roots[1] = -A / 3 - (S + T) / 2; // real part of complex root - roots[2] = -A / 3 - (S + T) / 2; // real part of complex root - auto Im = ImFabs(ImSqrt(3) * (S - T) / 2); // complex part of root pair - - // discard complex roots - if (Im != 0) - count = 1; - else - count = 3; - } - else // distinct real roots - { - auto th = ImAcos(R / ImSqrt(-ImPow(Q, 3))); - - roots[0] = 2 * ImSqrt(-Q) * ImCos(th / 3) - A / 3; - roots[1] = 2 * ImSqrt(-Q) * ImCos((th + 2 * IM_PI) / 3) - A / 3; - roots[2] = 2 * ImSqrt(-Q) * ImCos((th + 4 * IM_PI) / 3) - A / 3; - - count = 3; - } - - return count; - }; - - // https://github.com/kaishiqi/Geometric-Bezier/blob/master/GeometricBezier/src/kaishiqi/geometric/intersection/Intersection.as - // - // Start with Bezier using Bernstein polynomials for weighting functions: - // (1-t^3)P0 + 3t(1-t)^2P1 + 3t^2(1-t)P2 + t^3P3 - // - // Expand and collect terms to form linear combinations of original Bezier - // controls. This ends up with a vector cubic in t: - // (-P0+3P1-3P2+P3)t^3 + (3P0-6P1+3P2)t^2 + (-3P0+3P1)t + P0 - // /\ /\ /\ /\ - // || || || || - // c3 c2 c1 c0 - - // Calculate the coefficients - auto c3 = -p0 + 3 * p1 - 3 * p2 + p3; - auto c2 = 3 * p0 - 6 * p1 + 3 * p2; - auto c1 = -3 * p0 + 3 * p1; - auto c0 = p0; - - // Convert line to normal form: ax + by + c = 0 - auto a = a1.y - a0.y; - auto b = a0.x - a1.x; - auto c = a0.x * (a0.y - a1.y) + a0.y * (a1.x - a0.x); - - // Rotate each cubic coefficient using line for new coordinate system? - // Find roots of rotated cubic - float roots[3]; - auto rootCount = cubic_roots( - a * c3.x + b * c3.y, - a * c2.x + b * c2.y, - a * c1.x + b * c1.y, - a * c0.x + b * c0.y + c, - roots); - - // Any roots in closed interval [0,1] are intersections on Bezier, but - // might not be on the line segment. - // Find intersections and calculate point coordinates - - auto min = ImMin(a0, a1); - auto max = ImMax(a0, a1); - - ImCubicBezierIntersectResult result; - auto points = result.Points; - - for (int i = 0; i < rootCount; ++i) - { - auto root = roots[i]; - - if (0 <= root && root <= 1) - { - // We're within the Bezier curve - // Find point on Bezier - auto p = ImCubicBezier(p0, p1, p2, p3, root); - - // See if point is on line segment - // Had to make special cases for vertical and horizontal lines due - // to slight errors in calculation of p00 - if (a0.x == a1.x) - { - if (min.y <= p.y && p.y <= max.y) - *points++ = p; - } - else if (a0.y == a1.y) - { - if (min.x <= p.x && p.x <= max.x) - *points++ = p; - } - else if (p.x >= min.x && p.y >= min.y && p.x <= max.x && p.y <= max.y) - { - *points++ = p; - } - } - } - - result.Count = static_cast(points - result.Points); - - return result; -} - -inline ImCubicBezierIntersectResult ImCubicBezierLineIntersect(const ImCubicBezierPoints& curve, const ImLine& line) -{ - return ImCubicBezierLineIntersect(curve.P0, curve.P1, curve.P2, curve.P3, line.A, line.B); -} - -inline void ImCubicBezierSubdivide(ImCubicBezierSubdivideCallback callback, void* user_pointer, const ImVec2& p0, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, float tess_tol, ImCubicBezierSubdivideFlags flags) -{ - return ImCubicBezierSubdivide(callback, user_pointer, ImCubicBezierPoints{ p0, p1, p2, p3 }, tess_tol, flags); -} - -inline void ImCubicBezierSubdivide(ImCubicBezierSubdivideCallback callback, void* user_pointer, const ImCubicBezierPoints& curve, float tess_tol, ImCubicBezierSubdivideFlags flags) -{ - struct Tesselator - { - ImCubicBezierSubdivideCallback Callback; - void* UserPointer; - float TesselationTollerance; - ImCubicBezierSubdivideFlags Flags; - - void Commit(const ImVec2& p, const ImVec2& t) - { - ImCubicBezierSubdivideSample sample; - sample.Point = p; - sample.Tangent = t; - Callback(sample, UserPointer); - } - - void Subdivide(const ImCubicBezierPoints& curve, int level = 0) - { - float dx = curve.P3.x - curve.P0.x; - float dy = curve.P3.y - curve.P0.y; - float d2 = ((curve.P1.x - curve.P3.x) * dy - (curve.P1.y - curve.P3.y) * dx); - float d3 = ((curve.P2.x - curve.P3.x) * dy - (curve.P2.y - curve.P3.y) * dx); - d2 = (d2 >= 0) ? d2 : -d2; - d3 = (d3 >= 0) ? d3 : -d3; - if ((d2 + d3) * (d2 + d3) < TesselationTollerance * (dx * dx + dy * dy)) - { - Commit(curve.P3, ImCubicBezierTangent(curve, 1.0f)); - } - else if (level < 10) - { - const auto p12 = (curve.P0 + curve.P1) * 0.5f; - const auto p23 = (curve.P1 + curve.P2) * 0.5f; - const auto p34 = (curve.P2 + curve.P3) * 0.5f; - const auto p123 = (p12 + p23) * 0.5f; - const auto p234 = (p23 + p34) * 0.5f; - const auto p1234 = (p123 + p234) * 0.5f; - - Subdivide(ImCubicBezierPoints { curve.P0, p12, p123, p1234 }, level + 1); - Subdivide(ImCubicBezierPoints { p1234, p234, p34, curve.P3 }, level + 1); - } - } - }; - - if (tess_tol < 0) - tess_tol = 1.118f; // sqrtf(1.25f) - - Tesselator tesselator; - tesselator.Callback = callback; - tesselator.UserPointer = user_pointer; - tesselator.TesselationTollerance = tess_tol * tess_tol; - tesselator.Flags = flags; - - if (!(tesselator.Flags & ImCubicBezierSubdivide_SkipFirst)) - tesselator.Commit(curve.P0, ImCubicBezierTangent(curve, 0.0f)); - - tesselator.Subdivide(curve, 0); -} - -template inline void ImCubicBezierSubdivide(F& callback, const ImVec2& p0, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, float tess_tol, ImCubicBezierSubdivideFlags flags) -{ - auto handler = [](const ImCubicBezierSubdivideSample& p, void* user_pointer) - { - auto& callback = *reinterpret_cast(user_pointer); - callback(p); - }; - - ImCubicBezierSubdivide(handler, &callback, ImCubicBezierPoints{ p0, p1, p2, p3 }, tess_tol, flags); -} - -template inline void ImCubicBezierSubdivide(F& callback, const ImCubicBezierPoints& curve, float tess_tol, ImCubicBezierSubdivideFlags flags) -{ - auto handler = [](const ImCubicBezierSubdivideSample& p, void* user_pointer) - { - auto& callback = *reinterpret_cast(user_pointer); - callback(p); - }; - - ImCubicBezierSubdivide(handler, &callback, curve, tess_tol, flags); -} - -inline void ImCubicBezierFixedStep(ImCubicBezierFixedStepCallback callback, void* user_pointer, const ImVec2& p0, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, float step, bool overshoot, float max_value_error, float max_t_error) -{ - if (step <= 0.0f || !callback || max_value_error <= 0 || max_t_error <= 0) - return; - - ImCubicBezierFixedStepSample sample; - sample.T = 0.0f; - sample.Length = 0.0f; - sample.Point = p0; - sample.BreakSearch = false; - - callback(sample, user_pointer); - if (sample.BreakSearch) - return; - - const auto total_length = ImCubicBezierLength(p0, p1, p2, p3); - const auto point_count = static_cast(total_length / step) + (overshoot ? 2 : 1); - const auto t_min = 0.0f; - const auto t_max = step * point_count / total_length; - const auto t_0 = (t_min + t_max) * 0.5f; - - // #todo: replace map with ImVector + binary search - std::map cache; - for (int point_index = 1; point_index < point_count; ++point_index) - { - const auto targetLength = point_index * step; - - float t_start = t_min; - float t_end = t_max; - float t = t_0; - - float t_best = t; - float error_best = total_length; - - while (true) - { - auto cacheIt = cache.find(t); - if (cacheIt == cache.end()) - { - const auto front = ImCubicBezierSplit(p0, p1, p2, p3, t).Left; - const auto split_length = ImCubicBezierLength(front); - - cacheIt = cache.emplace(t, split_length).first; - } - - const auto length = cacheIt->second; - const auto error = targetLength - length; - - if (error < error_best) - { - error_best = error; - t_best = t; - } - - if (ImFabs(error) <= max_value_error || ImFabs(t_start - t_end) <= max_t_error) - { - sample.T = t; - sample.Length = length; - sample.Point = ImCubicBezier(p0, p1, p2, p3, t); - - callback(sample, user_pointer); - if (sample.BreakSearch) - return; - - break; - } - else if (error < 0.0f) - t_end = t; - else // if (error > 0.0f) - t_start = t; - - t = (t_start + t_end) * 0.5f; - } - } -} - -inline void ImCubicBezierFixedStep(ImCubicBezierFixedStepCallback callback, void* user_pointer, const ImCubicBezierPoints& curve, float step, bool overshoot, float max_value_error, float max_t_error) -{ - ImCubicBezierFixedStep(callback, user_pointer, curve.P0, curve.P1, curve.P2, curve.P3, step, overshoot, max_value_error, max_t_error); -} - -// F has signature void(const ImCubicBezierFixedStepSample& p) -template -inline void ImCubicBezierFixedStep(F& callback, const ImVec2& p0, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, float step, bool overshoot, float max_value_error, float max_t_error) -{ - auto handler = [](ImCubicBezierFixedStepSample& sample, void* user_pointer) - { - auto& callback = *reinterpret_cast(user_pointer); - callback(sample); - }; - - ImCubicBezierFixedStep(handler, &callback, p0, p1, p2, p3, step, overshoot, max_value_error, max_t_error); -} - -template -inline void ImCubicBezierFixedStep(F& callback, const ImCubicBezierPoints& curve, float step, bool overshoot, float max_value_error, float max_t_error) -{ - auto handler = [](ImCubicBezierFixedStepSample& sample, void* user_pointer) - { - auto& callback = *reinterpret_cast(user_pointer); - callback(sample); - }; - - ImCubicBezierFixedStep(handler, &callback, curve.P0, curve.P1, curve.P2, curve.P3, step, overshoot, max_value_error, max_t_error); -} - - -//------------------------------------------------------------------------------ -# endif // __IMGUI_BEZIER_MATH_INL__ -- cgit v1.2.3-70-g09d2