using Autodesk.Revit.DB; using Autodesk.Revit.UI; using CommunityToolkit.Mvvm.ComponentModel; using CommunityToolkit.Mvvm.Input; using Nice3point.Revit.Toolkit.External.Handlers; using System; using System.Diagnostics; using System.Linq; namespace Szmedi.RvKits.MEPTools { public partial class QuickViewSectionViewModel(UIDocument uidoc) : ObservableObject { private readonly ActionEventHandler handler = new(); [ObservableProperty] private bool isParallel = true; private readonly List viewSections = []; [RelayCommand] private void DeleteViewSection() { handler.Raise( uiapp => { var uidoc = uiapp.ActiveUIDocument; var doc = uidoc.Document; doc.Invoke( ts => { for (var i = viewSections.Count - 1; i >= 0; i--) { var view = viewSections[i]; if (view.IsValidObject) { var uiView = uidoc.GetOpenUIViews().FirstOrDefault(ui => ui.ViewId == view.Id); uiView?.Close(); viewSections.Remove(view); doc.Delete(view.Id); } } }, "删除快速剖面"); }); } [RelayCommand] private void CreateViewSection() { try { var reference = uidoc.Selection .PickObject( Autodesk.Revit.UI.Selection.ObjectType.Element, new FuncFilter(elem => elem.GetLocCurve() is Line l && l.Direction.Z < 0.001), "请选择基于线的实例"); var element = uidoc.Document.GetElement(reference); if (element != null) { var lc = element.Location as LocationCurve; var line = lc.Curve as Line; var doc = uidoc.Document; var viewfamilyType = doc.OfType() .Cast() .Where(t => t.ViewFamily == ViewFamily.Section) .FirstOrDefault(); var bb = element.get_BoundingBox(null); var minZ = bb.Min.Z; var maxZ = bb.Max.Z; var baseLength = (bb.Max - bb.Min).GetLength(); ViewSection viewSection = null; BoundingBoxXYZ sectionBox; var offset = 2.0; var t = Transform.Identity; Debug.WriteLine($"Length:{baseLength}"); Debug.WriteLine($"Offset:{offset}"); Debug.WriteLine("拾取对象:"); Debug.WriteLine($"Min:{bb.Min}"); Debug.WriteLine($"Max:{bb.Max}"); t.Origin = line.Evaluate(0.5, true).Flatten(); Debug.WriteLine("定义剖面:"); Debug.WriteLine($"Transform.Origin:{t.Origin}"); t.BasisY = XYZ.BasisZ;//UpDirection var viewName = $"剖面-({element.Category.Name})-({element.Id})"; var min = new XYZ(-baseLength / 2, minZ - offset, -offset); var max = new XYZ(baseLength / 2, maxZ + offset, offset); Debug.WriteLine($"Min:{min}"); Debug.WriteLine($"Max:{max}"); var dir = line.Direction.Flatten(); if (IsParallel) { viewName = $"{viewName}-平行"; //与生成的最终剖面视图的RightDirection反向(定义Transform) t.BasisX = dir; //与生成的最终剖面视图的ViewDirection反向(定义Transform) t.BasisZ = dir.CrossProduct(XYZ.BasisZ); Debug.WriteLine($"Transform.BasisX:{t.BasisX}"); Debug.WriteLine($"Transform.BasisZ:{t.BasisZ}"); sectionBox = new BoundingBoxXYZ { Transform = t, Min = min, Max = max }; } else { //var transform = line.ComputeDerivatives(0.5, true);//求导切向为BasisX viewName = $"{viewName}-正交"; t.BasisX = XYZ.BasisZ.CrossProduct(dir); t.BasisZ = dir; //var min = new XYZ(-baseLength / 2, minZ - offset, -offset); //var max = new XYZ(baseLength / 2, maxZ + offset, offset); Debug.WriteLine($"Transform.BasisX:{t.BasisX}"); Debug.WriteLine($"Transform.BasisZ:{t.BasisZ}"); sectionBox = new BoundingBoxXYZ { Transform = t, Min = min, Max = max }; } handler.Raise( _ => { doc.Invoke( ts => { viewSection = ViewSection.CreateSection(uidoc.Document, viewfamilyType.Id, sectionBox); viewSection.DisplayStyle = DisplayStyle.ShadingWithEdges; viewSection.DetailLevel = ViewDetailLevel.Fine; var isExistName = false; try { viewSection.Name = viewName; } catch (Autodesk.Revit.Exceptions.ArgumentException) { isExistName = true; } if (isExistName) { for (var i = 0; i < 100; i++) { try { viewSection.Name = $"{viewName} {i + 1}"; break; } catch (Autodesk.Revit.Exceptions.ArgumentException) { } } } ts.Commit(); Debug.WriteLine("生成后:"); Debug.WriteLine($"CropBox.Origin:{viewSection.CropBox.Transform.Origin}"); Debug.WriteLine($"CropBox.BasisX:{viewSection.CropBox.Transform.BasisX}"); Debug.WriteLine($"CropBox.BasisZ:{viewSection.CropBox.Transform.BasisZ}"); Debug.WriteLine($"CropBox.Min:{viewSection.CropBox.Min}"); Debug.WriteLine($"CropBox.Max:{viewSection.CropBox.Max}"); Debug.WriteLine($"RightDirection:{viewSection.RightDirection}"); Debug.WriteLine($"ViewDirection:{viewSection.ViewDirection}"); if (viewSection != null) { uidoc.ActiveView = viewSection; uidoc.Selection.SetElementIds([element.Id]); } }); }); } } catch (Autodesk.Revit.Exceptions.OperationCanceledException) { } catch { } } } }