public void SelectData(SphereDataView selectedPositionData, Point mousePosition) { // Show tooltip with details DataToolTipBorder.DataContext = selectedPositionData; Canvas.SetLeft(DataToolTipBorder, mousePosition.X + 10); Canvas.SetTop(DataToolTipBorder, mousePosition.Y + 10); DataToolTipBorder.Visibility = Visibility.Visible; // Add additional 3D lines that will show where the sphere is in the 3D space var centerPosition = AxesBox.CenterPosition; var size = AxesBox.Size; double wireBoxBottom = centerPosition.Y - size.Y * 0.5; var verticalLineVisual3D = new Ab3d.Visuals.LineVisual3D() { StartPosition = selectedPositionData.Position, EndPosition = new Point3D(selectedPositionData.Position.X, wireBoxBottom, selectedPositionData.Position.Z), LineThickness = 2, LineColor = Colors.Gray }; SelectedSphereLinesVisual.Children.Add(verticalLineVisual3D); double x1 = centerPosition.X - size.X * 0.5; double x2 = centerPosition.X + size.X * 0.5; var xLineVisual3D = new Ab3d.Visuals.LineVisual3D() { StartPosition = new Point3D(x1, wireBoxBottom, selectedPositionData.Position.Z), EndPosition = new Point3D(x2, wireBoxBottom, selectedPositionData.Position.Z), LineThickness = 2, LineColor = Colors.Gray }; SelectedSphereLinesVisual.Children.Add(xLineVisual3D); double z1 = centerPosition.Z - size.Z * 0.5; double z2 = centerPosition.Z + size.Z * 0.5; var zLineVisual3D = new Ab3d.Visuals.LineVisual3D() { StartPosition = new Point3D(selectedPositionData.Position.X, wireBoxBottom, z1), EndPosition = new Point3D(selectedPositionData.Position.X, wireBoxBottom, z2), LineThickness = 2, LineColor = Colors.Gray }; SelectedSphereLinesVisual.Children.Add(zLineVisual3D); }
public static SphereDataView Create(SphereData originalSphereData, Rect3D displayedDataBounds, double maxTime, Rect xyDataRange, Color color) { // First calculate normalized values (from 0 to 1) double x = originalSphereData.Time / maxTime; double y = (originalSphereData.Location.Y - xyDataRange.Y) / xyDataRange.Height; double z = (originalSphereData.Location.X - xyDataRange.X) / xyDataRange.Width; // Now put normalized values into a 3D space that is defined by displayedDataBounds x = (x * displayedDataBounds.SizeX) + displayedDataBounds.X; y = (y * displayedDataBounds.SizeY) + displayedDataBounds.Y; z = (z * displayedDataBounds.SizeZ) + displayedDataBounds.Z; Point3D position3D = new Point3D(x, y, z); // Now we have all the data to create the SphereDataView var sphereDataView = new SphereDataView(originalSphereData, position3D, color, originalSphereData.Size); return(sphereDataView); }
public void ShowData(List <SphereData> originalData, Rect3D displayedDataBounds, Rect xyDataRange) { // Now use original data to create our data view objects // All data will be displayed in a 3D box defined below: //var displayedDataBounds = new Rect3D(AxesBox.CenterPosition.X - AxesBox.Size.X * 0.5, // AxesBox.CenterPosition.Y - AxesBox.Size.Y * 0.5, // AxesBox.CenterPosition.Z - AxesBox.Size.Z * 0.5, // AxesBox.Size.X, // AxesBox.Size.Y, // AxesBox.Size.Z); _allSpheresData = new List <SphereDataView>(originalData.Count); foreach (var originalSphereData in originalData) { // Set color of the sphere based on its y position // We choose the color from the gradient defined in EnsureGradientColorsArray double relativeY = (originalSphereData.Location.Y - xyDataRange.Y) / xyDataRange.Height; int colorArrayIndex = (int)(relativeY * (_gradientColorsArray.Length - 1)); Color color = _gradientColorsArray[colorArrayIndex]; var sphereDataView = SphereDataView.Create(originalSphereData, displayedDataBounds, originalData.Count, xyDataRange, color); sphereDataView.IsSelectedChanged += delegate(object sender, EventArgs args) { var changedPositionDataView = (SphereDataView)sender; if (changedPositionDataView.IsSelected) { DataListBox.SelectedItems.Add(changedPositionDataView); } else { DataListBox.SelectedItems.Remove(changedPositionDataView); } UpdateSelectedSpheresData(); }; _allSpheresData.Add(sphereDataView); } // Bind positions data to ListBox DataListBox.ItemsSource = _allSpheresData; // Create curve through all positions // This is done by first creating all points that define the curve (10 points between each position that define the curve) List <Point3D> allPositions = new List <Point3D>(); foreach (var positionData in _allSpheresData) { allPositions.Add(positionData.Position); } BezierCurve bezierCurve = Ab3d.Utilities.BezierCurve.CreateFromCurvePositions(allPositions); Point3DCollection curvePoints = bezierCurve.CreateBezierCurve(positionsPerSegment: 10); // How many points between each defined position in the curve // Create 3D Polyline from curvePoints Model3D curveModel = Ab3d.Models.Line3DFactory.CreatePolyLine3D(curvePoints, thickness: 2, color: Colors.Blue, isClosed: false, startLineCap: LineCap.Flat, endLineCap: LineCap.Flat, parentViewport3D: MainViewport); CurveModelVisual.Content = curveModel; // Now create 3D sphere objects for each position SpheresModelVisual.Children.Clear(); // Each sphere will also need MouseEnter, MouseLeave and MouseClick event handlers // We use EventManager3D for that var eventManager3D = new Ab3d.Utilities.EventManager3D(MainViewport); // Add 3D sphere for each position foreach (var positionData in _allSpheresData) { SpheresModelVisual.Children.Add(positionData.ModelVisual3D); // Sphere Visual3D is created in SphereDataView object // Add event handlers (sphere Visual3D will be the source of the events) var visualEventSource3D = new VisualEventSource3D(positionData.ModelVisual3D); visualEventSource3D.MouseEnter += delegate(object sender, Mouse3DEventArgs e) { if (_isSelecting) { return; } // Use hand cursor Mouse.OverrideCursor = Cursors.Hand; // Find selected position data var selectedPositionData = _allSpheresData.FirstOrDefault(p => p.ModelVisual3D == e.HitObject); SelectData(selectedPositionData, e.CurrentMousePosition); }; visualEventSource3D.MouseLeave += delegate(object sender, Mouse3DEventArgs e) { if (_isSelecting) { return; } Mouse.OverrideCursor = null; DataToolTipBorder.Visibility = Visibility.Collapsed; DataToolTipBorder.DataContext = null; SelectedSphereLinesVisual.Children.Clear(); }; visualEventSource3D.MouseClick += delegate(object sender, MouseButton3DEventArgs e) { // Select / deselect on mouse click var clickedPositionData = _allSpheresData.FirstOrDefault(p => p.ModelVisual3D == e.HitObject); if (clickedPositionData != null) { positionData.IsSelected = !clickedPositionData.IsSelected; } }; // Register the event source eventManager3D.RegisterEventSource3D(visualEventSource3D); } }