#[macro_use] extern crate derive_builder; extern crate triangle_sys as sys; #[cfg(test)] mod tests; use std::{ffi::CString, mem::MaybeUninit, ptr}; use anyhow::Result; #[derive(Builder)] pub struct TrianglulateOpts

{ point_list: P, /// Generates a Voronoi diagram #[builder(default)] voronoi: bool, } impl TrianglulateOpts

{ pub fn builder() -> TrianglulateOptsBuilder

{ TrianglulateOptsBuilder::default() } } #[derive(Clone, Copy, Debug)] pub struct Point { x: f64, y: f64, } #[derive(Debug)] pub struct TriangulateResult { pub point_list: Vec, } pub fn triangulate

(opts: TrianglulateOpts

) -> Result where P: IntoIterator, { let mut switches = Vec::new(); if opts.voronoi { switches.push("v"); } let switches = CString::new(switches.join(""))?; let point_list = opts.point_list.into_iter().collect::>(); let mut flat_point_list = point_list .iter() .flat_map(|point| [point.x, point.y]) .collect::>(); let input = MaybeUninit::::uninit(); let output = MaybeUninit::::uninit(); let mut vorout = ptr::null::(); let mut input = unsafe { input.assume_init() }; let mut output = unsafe { output.assume_init() }; input.pointlist = flat_point_list.as_mut_ptr(); input.numberofpoints = point_list.len() as i32; // TODO: Implement point attributes input.numberofpointattributes = 0; unsafe { sys::triangulate( switches.as_ptr() as *mut _, &mut input as *mut _, &mut output as *mut _, vorout as *mut _, ) }; let flat_point_list = unsafe { Vec::from_raw_parts( output.pointlist, output.numberofpoints as usize * 2, output.numberofpoints as usize * 2, ) }; let point_list = flat_point_list .chunks(2) .map(|points| Point { x: points[0], y: points[1], }) .collect::>(); Ok(TriangulateResult { point_list }) }