public LazyClosestPointsAmountEnumerator(RTree tree, IReadOnlyList <Point3d> oversized_tree_pts_array, IEnumerable <Point3d> needlePts, int amount)
            {
                if (tree.Count < amount)
                {
                    throw new ArgumentException("Requested more items than the quantity present in tree.");
                }

                m_tree = tree;
                m_oversized_tree_pts_array = oversized_tree_pts_array;
                m_needlePts = needlePts;
                m_amount    = amount;
            }
Beispiel #2
0
        /// <summary>
        /// Constructs a new tree with an element for each pointcloud point.
        /// </summary>
        /// <param name="cloud">A pointcloud.</param>
        /// <returns>A new tree, or null on error.</returns>
        public static RTree CreatePointCloudTree(PointCloud cloud)
        {
            RTree  rc          = new RTree();
            IntPtr pRtree      = rc.NonConstPointer();
            IntPtr pConstCloud = cloud.ConstPointer();

            if (!UnsafeNativeMethods.ON_RTree_CreatePointCloudTree(pRtree, pConstCloud))
            {
                rc.Dispose();
                return(null);
            }
            uint size = UnsafeNativeMethods.ON_RTree_SizeOf(pRtree);

            rc.m_memory_pressure = size;
            GC.AddMemoryPressure(rc.m_memory_pressure);
            return(rc);
        }
    public static Rhino.Commands.Result RTreeClosestPoint(RhinoDoc doc)
    {
        Rhino.DocObjects.ObjRef objref;
        var rc = Rhino.Input.RhinoGet.GetOneObject("select mesh", false, Rhino.DocObjects.ObjectType.Mesh, out objref);
        if (rc != Rhino.Commands.Result.Success)
          return rc;

        Mesh mesh = objref.Mesh();
        objref.Object().Select(false);
        doc.Views.Redraw();

        using (RTree tree = new RTree())
        {
          for (int i = 0; i < mesh.Vertices.Count; i++)
          {
        // we can make a C++ function that just builds an rtree from the
        // vertices in one quick shot, but for now...
        tree.Insert(mesh.Vertices[i], i);
          }

          while (true)
          {
        Point3d point;
        rc = Rhino.Input.RhinoGet.GetPoint("test point", false, out point);
        if (rc != Rhino.Commands.Result.Success)
          break;

        SearchData data = new SearchData(mesh, point);
        // Use the first vertex in the mesh to define a start sphere
        double distance = point.DistanceTo(mesh.Vertices[0]);
        Sphere sphere = new Sphere(point, distance * 1.1);
        if (tree.Search(sphere, SearchCallback, data))
        {
          doc.Objects.AddPoint(mesh.Vertices[data.Index]);
          doc.Views.Redraw();
          RhinoApp.WriteLine("Found point in {0} tests", data.HitCount);
        }
          }
        }
        return Rhino.Commands.Result.Success;
    }
        internal static RTree CreateFromPointArray(IEnumerable <Point3d> points, out Point3d[] potentiallyOversizePtsArray, out int count)
        {
            if (points == null)
            {
                throw new ArgumentNullException(nameof(points));
            }

            potentiallyOversizePtsArray = RhinoListHelpers.GetConstArray(points, out count);

            IntPtr ptr_rtree = UnsafeNativeMethods.ON_RTree_CreatePointArrayTree(potentiallyOversizePtsArray, count);

            if (ptr_rtree == IntPtr.Zero)
            {
                throw new InvalidOperationException("Could not create a tree with these inputs.");
            }

            var tree = new RTree(ptr_rtree)
            {
                m_count = count //avoid thread-unsafe tree traversal to fill Count.
            };

            return(tree);
        }
        /// <summary>
        /// Constructs a new tree with an element for each pointcloud point.
        /// </summary>
        /// <param name="cloud">A pointcloud.</param>
        /// <returns>A new tree, or null on error.</returns>
        public static RTree CreatePointCloudTree(PointCloud cloud)
        {
            if (cloud == null)
            {
                throw new ArgumentNullException(nameof(cloud));
            }

            IntPtr const_ptr_cloud = cloud.ConstPointer();
            IntPtr ptr_rtree       = UnsafeNativeMethods.ON_RTree_CreatePointCloudTree(const_ptr_cloud);

            if (IntPtr.Zero == ptr_rtree)
            {
                return(null);
            }

            RTree rc   = new RTree(ptr_rtree);
            uint  size = UnsafeNativeMethods.ON_RTree_SizeOf(ptr_rtree);

            rc.m_memory_pressure = size;
            GC.AddMemoryPressure(rc.m_memory_pressure);
            rc.m_count = cloud.Count;
            GC.KeepAlive(cloud);
            return(rc);
        }
        /// <summary>
        /// Constructs a new tree with an element for each face in the mesh.
        /// The element id is set to the index of the face.
        /// </summary>
        /// <param name="mesh">A mesh.</param>
        /// <returns>A new tree, or null on error.</returns>
        public static RTree CreateMeshFaceTree(Mesh mesh)
        {
            if (mesh == null)
            {
                throw new ArgumentNullException(nameof(mesh));
            }

            RTree  rc         = new RTree();
            IntPtr pRtree     = rc.NonConstPointer();
            IntPtr pConstMesh = mesh.ConstPointer();

            if (!UnsafeNativeMethods.ON_RTree_CreateMeshFaceTree(pRtree, pConstMesh))
            {
                rc.Dispose();
                return(null);
            }
            uint size = UnsafeNativeMethods.ON_RTree_SizeOf(pRtree);

            rc.m_memory_pressure = size;
            GC.AddMemoryPressure(rc.m_memory_pressure);
            rc.m_count = mesh.Faces.Count;
            GC.KeepAlive(mesh);
            return(rc);
        }
Beispiel #7
0
 internal static extern bool ON_RTree_Search2(IntPtr pConstRtreeA, IntPtr pConstRtreeB, double tolerance, int serial_number, RTree.SearchCallback searchCB);
Beispiel #8
0
 internal static extern bool ON_RTree_SearchSphere(IntPtr pConstRtree, Point3d center, double radius, int serial_number, RTree.SearchCallback searchCB);
Beispiel #9
0
 internal static extern bool ON_RTree_Search(IntPtr pConstRtree, Point3d pt0, Point3d pt1, int serial_number, RTree.SearchCallback searchCB);
 /// <summary>
 /// Searches two R-trees for all pairs elements whose bounding boxes overlap.
 /// </summary>
 /// <param name="treeA">A first tree.</param>
 /// <param name="treeB">A second tree.</param>
 /// <param name="tolerance">
 /// If the distance between a pair of bounding boxes is less than tolerance,
 /// then callback is called.
 /// </param>
 /// <param name="callback">A callback event handler.</param>
 /// <returns>
 /// true if entire tree was searched.  It is possible no results were found.
 /// </returns>
 public static bool SearchOverlaps(RTree treeA, RTree treeB, double tolerance, EventHandler<RTreeEventArgs> callback)
 {
   IntPtr pConstTreeA = treeA.ConstPointer();
   IntPtr pConstTreeB = treeB.ConstPointer();
   if (m_callbacks == null)
     m_callbacks = new List<Callbackholder>();
   Callbackholder cbh = new Callbackholder();
   cbh.SerialNumber = m_next_serial_number++;
   cbh.Callback = callback;
   cbh.Sender = null;
   m_callbacks.Add(cbh);
   SearchCallback searcher = CustomSearchCallback;
   bool rc = UnsafeNativeMethods.ON_RTree_Search2(pConstTreeA, pConstTreeB, tolerance, cbh.SerialNumber, searcher);
   for (int i = 0; i < m_callbacks.Count; i++)
   {
     if (m_callbacks[i].SerialNumber == cbh.SerialNumber)
     {
       m_callbacks.RemoveAt(i);
       break;
     }
   }
   return rc;
 }
    /// <summary>
    /// Constructs a new tree with an element for each pointcloud point.
    /// </summary>
    /// <param name="cloud">A pointcloud.</param>
    /// <returns>A new tree, or null on error.</returns>
    public static RTree CreatePointCloudTree(PointCloud cloud)
    {
      RTree rc = new RTree();
      IntPtr pRtree = rc.NonConstPointer();
      IntPtr pConstCloud = cloud.ConstPointer();
      if (!UnsafeNativeMethods.ON_RTree_CreatePointCloudTree(pRtree, pConstCloud))
      {
        rc.Dispose();
        return null;
      }
      uint size = UnsafeNativeMethods.ON_RTree_SizeOf(pRtree);
      rc.m_memory_pressure = size;
      GC.AddMemoryPressure(rc.m_memory_pressure);
      return rc;

    }