Commits

Barry Schwartz committed b7c33ad

Initial support for Bezier fragments.

  • Participants
  • Parent commits 4188f3c

Comments (0)

Files changed (5)

 
 #--------------------------------------------------------------------------
 
-UNITS = coord intCoord d2 point bezier #?????????????????????????????????????????????????????????????
-
 default: $(addprefix $(CAML2GEOM)., cmi cma cmxa) dll$(CAML2GEOM).so
 
 $(CAML2GEOM).cma: $(CAML2GEOM).cmo
 module type Fragment =
 sig
   type t
+  type output_type
   val is_zero : t -> bool
   val is_constant : t -> bool
   val is_finite : t -> bool
-  val at0 : t -> 'output_type
-  val at1 : t -> 'output_type
-  val value_at : t -> float -> 'output_type
+  val at0 : t -> output_type
+  val at1 : t -> output_type
+  val value_at : t -> float -> output_type
 end
 
 module D2 =
     val fst : t -> elt
     val snd : t -> elt
     val is_zero : t -> bool
+    val is_constant : t -> bool
     val is_finite : t -> bool
   end
 
     let fst (a,_) = a
     let snd (_,b) = b
     let is_zero (a,b) = Elt.is_zero a && Elt.is_zero b
+    let is_constant (a,b) = Elt.is_constant a && Elt.is_constant b
     let is_finite (a,b) = Elt.is_finite a && Elt.is_finite b
 
     let coord (a,b) i =
   external mul_by : t -> Coord.t -> unit = "point_mul_by_wrapper"
   external div_by : t -> Coord.t -> unit = "point_div_by_wrapper"
 end
+
+module Bezier =
+struct
+  type t
+  type output_type = Coord.t
+  external make_order3 : Coord.t -> Coord.t -> Coord.t -> Coord.t -> t = "new_bezier_order3_wrapper"
+  external is_zero : t -> bool = "bezier_is_zero_wrapper"
+  external is_constant : t -> bool = "bezier_is_constant_wrapper"
+  external is_finite : t -> bool = "bezier_is_finite_wrapper"
+  external at0 : t -> Coord.t = "bezier_at0_wrapper"
+  external at1 : t -> Coord.t = "bezier_at1_wrapper"
+  external value_at : t -> float -> Coord.t = "bezier_value_at_wrapper"
+end
+
+module Bezier_as_fragment = (Bezier : Fragment)
 module type Fragment =
 sig
   type t
+  type output_type
   val is_zero : t -> bool
   val is_constant : t -> bool
   val is_finite : t -> bool
-  val at0 : t -> 'output_type
-  val at1 : t -> 'output_type
-  val value_at : t -> float -> 'output_type
+  val at0 : t -> output_type
+  val at1 : t -> output_type
+  val value_at : t -> float -> output_type
 end
 
 module D2 :
     val fst : t -> elt
     val snd : t -> elt
     val is_zero : t -> bool
+    val is_constant : t -> bool
     val is_finite : t -> bool
   end
 
   external mul_by : t -> Coord.t -> unit = "point_mul_by_wrapper"
   external div_by : t -> Coord.t -> unit = "point_div_by_wrapper"
 end
+
+module Bezier :
+sig
+  type t
+  type output_type = Coord.t
+  external make_order3 : Coord.t -> Coord.t -> Coord.t -> Coord.t -> t = "new_bezier_order3_wrapper"
+  external is_zero : t -> bool = "bezier_is_zero_wrapper"
+  external is_constant : t -> bool = "bezier_is_constant_wrapper"
+  external is_finite : t -> bool = "bezier_is_finite_wrapper"
+  external at0 : t -> Coord.t = "bezier_at0_wrapper"
+  external at1 : t -> Coord.t = "bezier_at1_wrapper"
+  external value_at : t -> float -> Coord.t = "bezier_value_at_wrapper"
+end
+
+module Bezier_as_fragment : Fragment

caml2geom_stubs.c

 //-------------------------------------------------------------------------
 
 #include <2geom/affine.h>
+#include <2geom/bezier.h>
 #include <2geom/coord.h>
 #include <2geom/point.h>
 #include <2geom/transforms.h>
     custom_deserialize_default
 };
 
+static struct custom_operations bezier_ops = {
+    (char *) "lib2geom.Bezier",
+    custom_finalize_default,
+    custom_compare_default,
+    custom_hash_default,
+    custom_serialize_default,
+    custom_deserialize_default
+};
+
 //-------------------------------------------------------------------------
 
 extern "C" CAMLprim value epsilon_wrapper(void)
     CAMLreturn(Val_unit);
 }
 
-#define unary_point_op(name,op)                                         \
+#define unary_point_op(name, op)                                        \
     extern "C" CAMLprim value name(value _p)                            \
     {                                                                   \
         CAMLparam1(_p);                                                 \
 unary_point_op(point_cw_wrapper, cw);
 unary_point_op(point_neg_wrapper, operator-);
 
-#define point_assign_point_op(name,op)                                  \
+#define point_assign_point_op(name, op)                                 \
     extern "C" CAMLprim value name(value _p, value _other)              \
     {                                                                   \
         CAMLparam2(_p, _other);                                         \
 point_assign_point_op(point_add_to_wrapper, operator+=);
 point_assign_point_op(point_sub_from_wrapper, operator-=);
 
-#define point_assign_double_op(name,op)                                 \
+#define point_assign_double_op(name, op)                                \
     extern "C" CAMLprim value name(value _p, value _other)              \
     {                                                                   \
         CAMLparam2(_p, _other);                                         \
 point_assign_double_op(point_div_by_wrapper, operator/=);
 
 //-------------------------------------------------------------------------
+
+extern "C" CAMLprim value new_bezier_order3_wrapper(value _c0, value _c1, value _c2, value _c3)
+{
+    CAMLparam4(_c0, _c1, _c2, _c3);
+    CAMLlocal1(_bez);
+    _bez = caml_alloc_custom(&bezier_ops, sizeof(Geom::Bezier), 0, 1);
+    *(Geom::Bezier *)Data_custom_val(_bez) = Geom::Bezier(Double_val(_c0), Double_val(_c1),
+                                                        Double_val(_c2), Double_val(_c3));
+    CAMLreturn(_bez);
+}
+
+#define bezier_getval_wrapper(name, func, typeconv)                     \
+    extern "C" CAMLprim value name(value _bez)                          \
+    {                                                                   \
+        CAMLparam1(_bez);                                               \
+        CAMLreturn(typeconv((*(Geom::Bezier *)Data_custom_val(_bez)).func())); \
+    }
+
+bezier_getval_wrapper(bezier_is_zero_wrapper, isZero, Val_bool);
+bezier_getval_wrapper(bezier_is_constant_wrapper, isConstant, Val_bool);
+bezier_getval_wrapper(bezier_is_finite_wrapper, isFinite, Val_bool);
+bezier_getval_wrapper(bezier_at0_wrapper, at0, caml_copy_double);
+bezier_getval_wrapper(bezier_at1_wrapper, at1, caml_copy_double);
+
+extern "C" CAMLprim value bezier_value_at_wrapper(value _bez, value _t)
+{
+    CAMLparam2(_bez, _t);
+    CAMLreturn(caml_copy_double((*(Geom::Bezier *)Data_custom_val(_bez)).valueAt(Double_val(_t))));
+}
+
+//-------------------------------------------------------------------------
 let _ = printf "(%f,%f) %f\n" (Point.coord q 0) (Point.coord q 1) (Point.length q);;
 
 (*-----------------------------------------------------------------------*)
+
+let bez = Bezier.make_order3 0. 10. 15. 1. ;;
+let _ = printf "at0 -> %f\n" (Bezier.at0 bez) ;;
+let _ = printf "at1 -> %f\n" (Bezier.at1 bez) ;;
+let _ = printf "at 0.25 -> %f\n" (Bezier.value_at bez 0.25) ;;
+let _ = printf "at 1/3 -> %f\n" (Bezier.value_at bez (1./.3.)) ;;
+let _ = printf "at 0.5 -> %f\n" (Bezier.value_at bez 0.5) ;;
+let _ = printf "at 2/3 -> %f\n" (Bezier.value_at bez (2./.3.)) ;;
+let _ = printf "at 0.75 -> %f\n" (Bezier.value_at bez 0.75) ;;
+
+(*-----------------------------------------------------------------------*)