private IObservable <T> Search(IEnvelop envelope, int zoomLevel) { var minMargin = ZoomHelper.GetMinMargin(zoomLevel); return(Observable.Create <T>(observer => { var node = Root; if (!envelope.Intersects(node.Envelope)) { observer.OnCompleted(); return Disposable.Empty; } var nodesToSearch = new Stack <RTreeNode>(); while (node != null && node.Envelope != null) { if (node.Children != null) { foreach (var child in node.Children) { var childEnvelope = child.Envelope; if (envelope.Intersects(childEnvelope)) { if (node.IsLeaf && childEnvelope.Margin >= minMargin) { observer.OnNext(child.Data); } else if (envelope.Contains(childEnvelope)) { Collect(child, minMargin, observer); } else { nodesToSearch.Push(child); } } } } node = nodesToSearch.TryPop(); } observer.OnCompleted(); return Disposable.Empty; })); }