public static void LoadTextHeight(Document doc)
 {
     if (double.IsNaN(TextHeight))
     {
         var familyDoc   = doc.EditFamily(SingleTagSymbol.Family);
         var textElement = new FilteredElementCollector(familyDoc).OfClass(typeof(TextElement)).First(c => c.Name == "2.5") as TextElement;
         var textSizeStr = textElement.Symbol.get_Parameter(BuiltInParameter.TEXT_SIZE).AsValueString();
         var textSize    = double.Parse(textSizeStr.Substring(0, textSizeStr.IndexOf(" mm")));
         TextHeight = UnitHelper.ConvertToFoot(48, VLUnitType.millimeter) * textSize;//48是字体大小1mm在Revit中对应的高度
         var textWidth = textElement.Symbol.get_Parameter(BuiltInParameter.TEXT_WIDTH_SCALE).AsValueString();
     }
 }
Exemple #2
0
        //public void CalculateLocations(Element element, XYZ offset)
        //{
        //    var scale = 1 / VLConstraints.OrientFontSizeScale * VLConstraints.CurrentFontSizeScale;
        //    var width = CSALocationType.GetLineWidth() * scale;
        //    var height = 400 * scale;
        //    var widthFoot = UnitHelper.ConvertToFoot(width, VLUnitType.millimeter);
        //    var heightFoot = UnitHelper.ConvertToFoot(height, VLUnitType.millimeter);
        //    var verticalFix = UnitHelper.ConvertToFoot(100, VLUnitType.millimeter) * scale;
        //    var locationCurve = TargetType.GetLine(element);
        //    UpdateVectors(locationCurve);
        //    //线起始点 (中点)
        //    LineStartLocation = (locationCurve.GetEndPoint(0) + locationCurve.GetEndPoint(1)) / 2;
        //    //文本位置 start:(附着元素中点+线基本高度+文本高度*(文本个数-1))  end: start+宽
        //    //高度,宽度 取决于文本
        //    ParallelLinesLocations = new List<TextLocation>();
        //    TextLocations = new List<XYZ>();
        //    for (int i = Texts.Count() - 1; i >= 0; i--)
        //    {
        //        var start = LineStartLocation + (heightFoot + i * VLConstraints.CurrentFontHeight) * VerticalVector;
        //        var end = start + widthFoot * ParallelVector;
        //        ParallelLinesLocations.Add(new TextLocation(start, end));
        //        TextLocations.Add(CSALocationType.GetTextLocation(verticalFix, VerticalVector, start, end));
        //    }
        //    //线终点 (最高的文本位置)
        //    LineEndLocation = ParallelLinesLocations[0].Start;
        //}

        //public void CalculateLocations(Element element)
        //{
        //    CalculateLocations(element, new XYZ(0, 0, 0));
        //}
        #endregion


        #region 线族的计算方案
        public void CalculateLocations(Element element, FamilyInstance line, XYZ offset)
        {
            //数据准备
            var locationCurve = TargetType.GetLine(element);
            var miniHeight    = CurrentFontHeight * 2;

            UpdateVectors((locationCurve as Line));
            //ParallelVector = VLLocationHelper.GetVectorByQuadrant((locationCurve as Line).Direction, QuadrantType.OneAndFour);
            //VerticalVector = VLLocationHelper.GetVectorByQuadrant(new XYZ(ParallelVector.Y, -ParallelVector.X, 0), QuadrantType.OneAndTwo);
            //计算线的定位位置
            bool isRegenerate = offset != null;

            if (!isRegenerate)
            {
                LineLocation = (locationCurve.GetEndPoint(0) + locationCurve.GetEndPoint(1)) / 2;
                offset       = new XYZ(0, 0, 0);
                LineHeight   = UnitHelper.ConvertToFoot(1000, VLUnitType.millimeter);
            }
            else
            {
                LineLocation = locationCurve.Project(LineLocation + offset).XYZPoint;
                LineHeight   = line.GetParameters(TagProperty.线高度1.ToString()).First().AsDouble() + VLLocationHelper.GetLengthBySide(offset, VerticalVector);
                LineHeight   = LineHeight > miniHeight ? LineHeight : miniHeight;//确保最短长度有一个文字高度
            }
            //高度,宽度 取决于文本
            FontScale = 1 / VLConstraintsForCSA.OrientFontSizeScale * CurrentFontSizeScale;
            //LineWidth = UnitHelper.ConvertToFoot(CSALocationType.GetLineWidth() * FontScale, VLUnitType.millimeter);
            var verticalFix   = CurrentFontHeight * VLConstraintsForCSA.TextSpace;;  //偏移修正 为了显示更好 方便更改
            var horizontalFix = UnitHelper.ConvertToFoot(50, VLUnitType.millimeter); //偏移修正 为了显示更好 方便更改

            LineSpace     = CurrentFontHeight * (1 + VLConstraintsForCSA.TextSpace);
            TextLocations = new List <XYZ>();
            for (int i = Texts.Count() - 1; i >= 0; i--)
            {
                var start = LineLocation + (LineHeight + i * LineSpace) * VerticalVector;
                var end   = start + LineWidth * ParallelVector;
                TextLocations.Add(CSALocationType.GetTextLocation(CurrentFontHeight, verticalFix, VerticalVector, horizontalFix, ParallelVector, start, end));
            }
        }
Exemple #3
0
        /// <summary>
        /// 线 参数设置
        /// </summary>
        /// <param name="nodePoints"></param>
        /// <param name="line"></param>
        void UpdateLineParameters(List <XYZ> nodePoints, FamilyInstance line, XYZ verticalVector)
        {
            double deepLength = Math.Abs((nodePoints.Last() - nodePoints.First()).DotProduct(verticalVector));//nodePoints.First().DistanceTo(nodePoints.Last())

            line.GetParameters(TagProperty.线下探长度.ToString()).First().Set(deepLength);
            line.GetParameters(TagProperty.间距.ToString()).First().Set(UnitHelper.ConvertToFoot(AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType));
            line.GetParameters(TagProperty.文字行数.ToString()).First().Set(nodePoints.Count());
            for (int i = 2; i <= 8; i++)
            {
                var first = nodePoints.First();
                if (nodePoints.Count() >= i)
                {
                    var cur = nodePoints[i - 1];
                    line.GetParameters(string.Format("节点{0}可见性", i)).First().Set(1);
                    line.GetParameters(string.Format("节点{0}距离", i)).First().Set(Math.Abs((cur - first).DotProduct(verticalVector)));//cur.DistanceTo(first)
                }
                else
                {
                    line.GetParameters(string.Format("节点{0}可见性", i)).First().Set(0);
                    line.GetParameters(string.Format("节点{0}距离", i)).First().Set(0);
                }
            }
        }
Exemple #4
0
        public override void Execute()
        {
            var viewType = (CSAViewType)Enum.Parse(typeof(CSAViewType), ViewType.ToString());

            switch (viewType)
            {
            case CSAViewType.Idle:
                View = new CompoundStructureAnnotationWindow(this);
                IntPtr rvtPtr = Autodesk.Windows.ComponentManager.ApplicationWindow;
                WindowInteropHelper helper = new WindowInteropHelper(View);
                helper.Owner = rvtPtr;
                View.ShowDialog();
                break;

            case CSAViewType.Select:
                if (View.IsActive)
                {
                    View.Close();
                }
                using (PmSoft.Common.RevitClass.PickObjectsMouseHook MouseHook = new PmSoft.Common.RevitClass.PickObjectsMouseHook())
                {
                    MouseHook.InstallHook(PmSoft.Common.RevitClass.PickObjectsMouseHook.OKModeENUM.Objects);
                    try
                    {
                        Model.TargetId = UIDocument.Selection.PickObject(ObjectType.Element
                                                                         , new VLClassesFilter(false, typeof(Wall), typeof(Floor), typeof(ExtrusionRoof), typeof(FootPrintRoof))).ElementId;
                        MouseHook.UninstallHook();
                        ViewType = (int)CSAViewType.Generate;
                    }
                    catch (Exception ex)
                    {
                        MouseHook.UninstallHook();
                        ViewType = (int)CSAViewType.Idle;
                    }
                }
                break;

            case CSAViewType.Generate:
                var doc = UIDocument.Document;
                if (VLTransactionHelper.DelegateTransaction(doc, "生成结构标注", () =>
                {
                    var element = doc.GetElement(Model.TargetId);
                    var Collection = CSAContext.GetCollection(doc);
                    //避免重复生成 由于一个对象可能在不同的视图中进行标注设置 所以还是需要重复生成的
                    var existedModel = Collection.Data.FirstOrDefault(c => c.TargetId.IntegerValue == Model.TargetId.IntegerValue);
                    if (existedModel != null)
                    {
                        Collection.Data.Remove(existedModel);
                        CSAContext.Creator.Clear(doc, existedModel);
                    }
                    var fontScale = 1 / VLConstraintsForCSA.OrientFontSizeScale * Model.CurrentFontSizeScale;
                    Model.LineWidth = UnitHelper.ConvertToFoot(Model.CSALocationType.GetLineWidth() * fontScale, VLUnitType.millimeter);
                    CSAContext.Creator.Generate(doc, Model, element);
                    Collection.Data.Add(Model);
                    Collection.Save(doc);
                    return(true);
                }))
                {
                    ViewType = (int)CSAViewType.Select;
                }
                else
                {
                    ViewType = (int)CSAViewType.Idle;
                }
                break;

            case CSAViewType.Close:
                View.Close();
                break;

            case CSAViewType.Closing:
            default:
                break;
            }
        }
Exemple #5
0
        //private static bool CheckCollision(Document document, View view, IEnumerable<ElementId> selectedPipeIds, FamilyInstance currentLine, List<Line> currentLines, Triangle currentTriangle, FamilySymbol multipleTagSymbol)
        //{
        //    //管道避让
        //    var otherPipeLines = new FilteredElementCollector(document).OfClass(typeof(Pipe))
        //        .Select(c => Line.CreateBound((c.Location as LocationCurve).Curve.GetEndPoint(0), (c.Location as LocationCurve).Curve.GetEndPoint(1))).ToList();
        //    var pipeCollisions = new FilteredElementCollector(document).OfClass(typeof(Pipe)).Excluding(selectedPipeIds.ToList())
        //        .Select(c => Line.CreateBound((c.Location as LocationCurve).Curve.GetEndPoint(0), (c.Location as LocationCurve).Curve.GetEndPoint(1))).ToList()
        //        .Where(c => GeometryHelper.IsCover(currentLines, currentTriangle, c) != GeometryHelper.VLCoverType.Disjoint).ToList();
        //    //TODO 标注避让
        //    var collector = new FilteredElementCollector(document).OfClass(typeof(FamilyInstance)).WhereElementIsNotElementType().Excluding(new List<ElementId>() { currentLine.Id });
        //    var otherLines = collector.Where(c => (c as FamilyInstance).Symbol.Id == multipleTagSymbol.Id);
        //    var boundingBoxes = otherLines.Select(c => c.get_BoundingBox(view));
        //    List<BoundingBoxXYZ> crossedBoundingBox = new List<BoundingBoxXYZ>();
        //    List<BoundingBoxXYZ> uncrossedBoundingBox = new List<BoundingBoxXYZ>();
        //    foreach (var boundingBox in boundingBoxes.Where(c => c != null))
        //        if (GeometryHelper.VL_IsRectangleCrossed(currentTriangle.A, currentTriangle.C, boundingBox.Min, boundingBox.Max))
        //            crossedBoundingBox.Add(boundingBox);
        //        else
        //            uncrossedBoundingBox.Add(boundingBox);
        //    Utils.GraphicsDisplayerManager.Display(@"E:\WorkingSpace\Outputs\Images\0822标注避让1.png", currentTriangle, otherPipeLines, pipeCollisions, crossedBoundingBox, uncrossedBoundingBox);
        //    return crossedBoundingBox.Count() > 0;
        //}

        //private static List<Triangle> GetTrianglesFromBoundingBox(BoundingBoxXYZ lineBoundingBox)
        //{
        //    return new List<Triangle>()
        //    {
        //        new Triangle(lineBoundingBox.Min,lineBoundingBox.Max,lineBoundingBox.Min+new XYZ(0,(lineBoundingBox.Max-lineBoundingBox.Min).Y,0)),
        //        new Triangle(lineBoundingBox.Min,lineBoundingBox.Max,lineBoundingBox.Min+new XYZ(0,(lineBoundingBox.Max-lineBoundingBox.Min).X,0)),
        //    };
        //}

        //private static List<Line> GetLinesFromBoundingBox(BoundingBoxXYZ lineBoundingBox)
        //{
        //    return new List<Line>()
        //    {
        //        Line.CreateBound(lineBoundingBox.Min,lineBoundingBox.Min+new XYZ(0,(lineBoundingBox.Max-lineBoundingBox.Min).Y,0)),
        //        Line.CreateBound(lineBoundingBox.Max,lineBoundingBox.Min+new XYZ(0,(lineBoundingBox.Max-lineBoundingBox.Min).Y,0)),
        //        Line.CreateBound(lineBoundingBox.Max,lineBoundingBox.Max-new XYZ(0,(lineBoundingBox.Max-lineBoundingBox.Min).Y,0)),
        //        Line.CreateBound(lineBoundingBox.Min,lineBoundingBox.Max-new XYZ(0,(lineBoundingBox.Max-lineBoundingBox.Min).Y,0)),
        //    };
        //}

        /// <summary>
        /// 根据线的移动,重定位内容
        /// </summary>
        public bool RegenerateMultipleTagSymbolByEntity(Document document, PipeAnnotationEntity entity, XYZ skewVector)
        {
            Document = document;
            XYZ                     startPoint        = null;
            View                    view              = Document.ActiveView;
            FamilyInstance          line              = document.GetElement(new ElementId(entity.LineId)) as FamilyInstance;
            List <PipeAndNodePoint> pipeAndNodePoints = new List <PipeAndNodePoint>();

            for (int i = 0; i < entity.PipeIds.Count(); i++)
            {
                var pipeId = entity.PipeIds[i];
                var pipe   = Document.GetElement(new ElementId(pipeId));
                if (pipe == null)
                {
                    return(false);
                }
                var tagId = entity.TagIds[i];
                pipeAndNodePoints.Add(new PipeAndNodePoint(pipe as Pipe, Document.GetElement(new ElementId(tagId)) as IndependentTag));
            }
            ////偏移量
            //XYZ skew = (line.Location as LocationPoint).Point - entity.StartPoint;
            //管道 获取
            //平行,垂直 向量
            XYZ parallelVector = null;
            XYZ verticalVector = null;

            parallelVector = ((pipeAndNodePoints.First().Pipe.Location as LocationCurve).Curve as Line).Direction;
            verticalVector = new XYZ(parallelVector.Y, -parallelVector.X, 0);
            parallelVector = LocationHelper.GetVectorByQuadrant(parallelVector, QuadrantType.OneAndFour);
            verticalVector = LocationHelper.GetVectorByQuadrant(verticalVector, QuadrantType.OneAndTwo);
            if (parallelVector.Y == 1)
            {
                verticalVector = -verticalVector;
            }
            //原始线高度
            var orientLineHeight = line.GetParameters(TagProperty.线高度1.ToString()).First().AsDouble();

            ////原始对象清理
            //Document.Delete(line.Id);
            //foreach (var tagId in entity.TagIds)
            //    Document.Delete(new ElementId(tagId));
            ////平行检测
            //if (!CheckParallel(pipes, verticalVector))
            //{
            //    return AnnotationBuildResult.NotParallel;
            //}
            //节点计算
            //TODO entity.StartPoint 不以记录为准 以其他点位的信息来计算
            GetNodePoints(pipeAndNodePoints, entity.StartPoint + skewVector);
            pipeAndNodePoints = pipeAndNodePoints.OrderByDescending(c => c.NodePoint.Y).ToList();
            List <XYZ>            nodePoints = pipeAndNodePoints.Select(c => c.NodePoint).ToList();
            List <Pipe>           pipes      = pipeAndNodePoints.Select(c => c.Pipe).ToList();
            List <IndependentTag> tags       = pipeAndNodePoints.Select(c => c.Tag).ToList();

            //if (nodePoints.Count() == 0)
            //{
            //    return AnnotationBuildResult.NoOverlap;
            //}
            //起始点
            startPoint = nodePoints.First();
            //线 创建
            var multipleTagSymbol = PAContext.GetMultipleTagSymbol(document);

            if (!multipleTagSymbol.IsActive)
            {
                multipleTagSymbol.Activate();
            }
            //line = Document.Create.NewFamilyInstance(startPoint, MultipleTagSymbol, view);
            (line.Location as LocationPoint).Point = startPoint;
            ////线 旋转处理
            //if (verticalVector.Y != 1)//TODO 判断是否相同方向
            //{
            //    LocationPoint locationPoint = line.Location as LocationPoint;
            //    if (locationPoint != null)
            //        locationPoint.RotateByXY(startPoint, verticalVector);
            //}
            //偏移计算
            var verticalSkew = LocationHelper.GetLengthBySide(skewVector, verticalVector);
            var parallelSkew = LocationHelper.GetLengthBySide(skewVector, parallelVector);

            //线参数
            UpdateLineParameters(nodePoints, line, verticalVector);
            //标注 创建
            var nodesHeight = UnitHelper.ConvertToFoot((nodePoints.Count() - 1) * AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType);
            var lineHeight  = orientLineHeight + verticalSkew > nodesHeight ? orientLineHeight + verticalSkew : nodesHeight;
            var tagHeight   = lineHeight + nodesHeight;

            line.GetParameters(TagProperty.线高度1.ToString()).First().Set(lineHeight);
            var textSize   = PAContext.TextSize;
            var widthScale = PAContext.WidthScale;

            switch (entity.LocationType)
            {
            case MultiPipeTagLocation.OnLineEdge:
                //添加对应的单管直径标注
                line.GetParameters(TagProperty.线宽度.ToString()).First().Set(UnitHelper.ConvertToFoot(200, AnnotationConstaints.UnitType));
                var skewLength = AnnotationConstaints.SkewLengthForOffLine;
                for (int i = 0; i < pipes.Count(); i++)
                {
                    //var subTag = Document.Create.NewTag(view, pipes[i], false, TagMode.TM_ADDBY_CATEGORY, TagOrientation.Horizontal, startPoint);
                    var subTag       = tags[i];
                    var text         = subTag.TagText;
                    var textLength   = System.Windows.Forms.TextRenderer.MeasureText(text, AnnotationConstaints.Font).Width;
                    var actualLength = textLength / (textSize * widthScale);
                    subTag.TagHeadPosition = startPoint + skewLength * parallelVector + actualLength / 25.4 * parallelVector
                                             + (tagHeight + UnitHelper.ConvertToFoot(-i * AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType)) * verticalVector;
                    tags.Add(subTag);
                }
                break;

            case MultiPipeTagLocation.OnLine:
                //添加对应的单管直径标注
                line.GetParameters(TagProperty.线宽度.ToString()).First().Set(UnitHelper.ConvertToFoot(800, AnnotationConstaints.UnitType));
                skewLength = AnnotationConstaints.SkewLengthForOnLine;
                for (int i = 0; i < pipes.Count(); i++)
                {
                    //var subTag = Document.Create.NewTag(view, pipes[i], false, TagMode.TM_ADDBY_CATEGORY, TagOrientation.Horizontal, startPoint);
                    var subTag       = tags[i];
                    var text         = subTag.TagText;
                    var textLength   = System.Windows.Forms.TextRenderer.MeasureText(text, AnnotationConstaints.Font).Width;
                    var actualLength = textLength / (textSize * widthScale);
                    subTag.TagHeadPosition = startPoint + skewLength * parallelVector + actualLength / 25.4 * parallelVector
                                             + (tagHeight + UnitHelper.ConvertToFoot(-i * AnnotationConstaints.TextHeight + 0.5 * AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType)) * verticalVector;
                    tags.Add(subTag);
                }
                break;

            default:
                return(false);
            }
            entity.ViewId     = view.Id.IntegerValue;
            entity.StartPoint = startPoint;
            //entity.LineId = line.Id.IntegerValue;
            //entity.PipeIds.Clear();
            //entity.PipeIds.AddRange(pipes.Select(c => c.Id.IntegerValue));
            //entity.TagIds.Clear();
            //entity.TagIds.AddRange(tags.Select(c => c.Id.IntegerValue));
            return(true);
        }
Exemple #6
0
        /// <summary>
        /// 生成标注
        /// </summary>
        /// <param name="selectedIds"></param>
        /// <param name="entity"></param>
        /// <param name="view"></param>
        /// <returns></returns>
        AnnotationBuildResult GenerateMultipleTagSymbol(Document document, IEnumerable <ElementId> selectedIds, PipeAnnotationEntity entity, MultiPipeAnnotationSettings setting)
        {
            View                    view              = document.ActiveView;
            XYZ                     startPoint        = null;
            FamilyInstance          line              = null;
            List <PipeAndNodePoint> pipeAndNodePoints = new List <PipeAndNodePoint>();
            var                     tags              = new List <IndependentTag>();

            //管道 获取
            foreach (var selectedId in selectedIds)
            {
                pipeAndNodePoints.Add(new PipeAndNodePoint(Document.GetElement(selectedId) as Pipe));
            }
            //平行,垂直 向量
            XYZ parallelVector = null;
            XYZ verticalVector = null;

            parallelVector = ((pipeAndNodePoints.First().Pipe.Location as LocationCurve).Curve as Line).Direction;
            verticalVector = new XYZ(parallelVector.Y, -parallelVector.X, 0);
            parallelVector = LocationHelper.GetVectorByQuadrant(parallelVector, QuadrantType.OneAndFour);
            verticalVector = LocationHelper.GetVectorByQuadrant(verticalVector, QuadrantType.OneAndTwo);
            if (parallelVector.Y == 1)
            {
                verticalVector = -verticalVector;
            }
            //平行检测
            if (!CheckParallel(pipeAndNodePoints.Select(c => c.Pipe), verticalVector))
            {
                return(AnnotationBuildResult.NotParallel);
            }
            XYZ rightOfLefts; //左侧点的右边界
            XYZ leftOfRights; //右侧点的左边界

            //节点计算
            if (!GetNodePoints(pipeAndNodePoints, out rightOfLefts, out leftOfRights))
            {
                return(AnnotationBuildResult.NoOverlap);
            }
            pipeAndNodePoints = pipeAndNodePoints.OrderByDescending(c => c.NodePoint.Y).ToList();
            var pipes             = pipeAndNodePoints.Select(c => c.Pipe).ToList();
            var orderedNodePoints = pipeAndNodePoints.Select(c => c.NodePoint).ToList();

            //起始点
            startPoint = orderedNodePoints.First();
            //线 创建
            var multipleTagSymbol = PAContext.GetMultipleTagSymbol(document);

            if (!multipleTagSymbol.IsActive)
            {
                multipleTagSymbol.Activate();
            }
            line = Document.Create.NewFamilyInstance(startPoint, multipleTagSymbol, view);
            //线 旋转处理
            LocationPoint locationPoint = line.Location as LocationPoint;

            if (locationPoint != null)
            {
                locationPoint.RotateByXY(startPoint, verticalVector);
            }
            //线 参数设置
            UpdateLineParameters(orderedNodePoints, line, verticalVector);
            //标注 创建
            var textSize   = PAContext.TextSize;
            var widthScale = PAContext.WidthScale;
            //碰撞检测区域点
            XYZ avoidP1_Line1       = orderedNodePoints.Last();
            XYZ avoidP2_Line2       = null;
            XYZ avoidP3_Annotation1 = null;

            switch (entity.LocationType)
            {
            case MultiPipeTagLocation.OnLineEdge:
                //添加对应的单管直径标注
                line.GetParameters(TagProperty.线宽度.ToString()).First().Set(UnitHelper.ConvertToFoot(200, AnnotationConstaints.UnitType));
                var height = Convert.ToDouble(line.GetParameters(TagProperty.线高度1.ToString()).First().AsValueString()) + (orderedNodePoints.Count() - 1) * AnnotationConstaints.TextHeight;
                avoidP2_Line2 = avoidP1_Line1 + UnitHelper.ConvertToFoot(height, AnnotationConstaints.UnitType) * verticalVector;
                var skewLength = AnnotationConstaints.SkewLengthForOffLine;
                for (int i = 0; i < pipes.Count(); i++)
                {
                    var subTag       = Document.Create.NewTag(view, pipes[i], false, TagMode.TM_ADDBY_CATEGORY, TagOrientation.Horizontal, startPoint);
                    var text         = subTag.TagText;
                    var textLength   = System.Windows.Forms.TextRenderer.MeasureText(text, AnnotationConstaints.Font).Width;
                    var actualLength = textLength / (textSize * widthScale);
                    subTag.TagHeadPosition = startPoint + skewLength * parallelVector + UnitHelper.ConvertToInch(actualLength, VLUnitType.millimeter) * parallelVector
                                             + UnitHelper.ConvertToFoot(height - i * AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType) * verticalVector;
                    tags.Add(subTag);
                    if (i == 0)
                    {
                        avoidP3_Annotation1 = subTag.TagHeadPosition + skewLength * parallelVector + UnitHelper.ConvertToInch(actualLength, VLUnitType.millimeter) * parallelVector
                                              + UnitHelper.ConvertToFoot(0.5 * AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType) * verticalVector;
                    }
                }
                break;

            case MultiPipeTagLocation.OnLine:
                //添加对应的单管直径标注
                line.GetParameters(TagProperty.线宽度.ToString()).First().Set(UnitHelper.ConvertToFoot(800, AnnotationConstaints.UnitType));
                height        = Convert.ToDouble(line.GetParameters(TagProperty.线高度1.ToString()).First().AsValueString()) + (orderedNodePoints.Count() - 1) * AnnotationConstaints.TextHeight;
                avoidP2_Line2 = avoidP1_Line1 + UnitHelper.ConvertToFoot(height, AnnotationConstaints.UnitType) * verticalVector;
                skewLength    = AnnotationConstaints.SkewLengthForOnLine;
                for (int i = 0; i < pipes.Count(); i++)
                {
                    var subTag       = Document.Create.NewTag(view, pipes[i], false, TagMode.TM_ADDBY_CATEGORY, TagOrientation.Horizontal, startPoint);
                    var text         = subTag.TagText;
                    var textLength   = System.Windows.Forms.TextRenderer.MeasureText(text, AnnotationConstaints.Font).Width;
                    var actualLength = textLength / (textSize * widthScale);
                    subTag.TagHeadPosition = startPoint + skewLength * parallelVector + UnitHelper.ConvertToInch(actualLength, VLUnitType.millimeter) * parallelVector
                                             + UnitHelper.ConvertToFoot(height - i * AnnotationConstaints.TextHeight + 0.5 * AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType) * verticalVector;
                    tags.Add(subTag);
                    if (i == 0)
                    {
                        avoidP3_Annotation1 = subTag.TagHeadPosition + skewLength * parallelVector + UnitHelper.ConvertToInch(actualLength, VLUnitType.millimeter) * parallelVector
                                              + UnitHelper.ConvertToFoot(AnnotationConstaints.TextHeight, AnnotationConstaints.UnitType) * verticalVector;
                    }
                }
                break;

            default:
                return(AnnotationBuildResult.NoLocationType);
            }
            entity.ViewId = view.Id.IntegerValue;
            entity.LineId = line.Id.IntegerValue;
            foreach (var pipe in pipes)
            {
                entity.PipeIds.Add(pipe.Id.IntegerValue);
            }
            foreach (var tag in tags)
            {
                entity.TagIds.Add(tag.Id.IntegerValue);
            }
            entity.StartPoint = startPoint;
            //碰撞检测
            VLTriangle    triangle       = new VLTriangle(avoidP1_Line1, avoidP2_Line2, avoidP3_Annotation1);
            List <Line>   lines          = triangle.GetLines();
            AvoidData     data           = new AvoidData(document, selectedIds, entity, lines, triangle, multipleTagSymbol, parallelVector, rightOfLefts.GetLength(), leftOfRights.GetLength());
            AvoidStrategy strategty      = AvoidStrategy.MoveLeft;
            var           strategyEntity = AvoidStrategyFactory.GetAvoidStrategyEntity(strategty);

            strategyEntity.Data = data;
            while (strategyEntity.CheckCollision(strategyEntity.Data))
            {
                if (strategyEntity.TryAvoid())
                {
                    strategyEntity.Apply(data);
                    break;
                }
                else
                {
                    strategyEntity = strategyEntity.GetNextStratetyEntity();
                }
            }
            return(AnnotationBuildResult.Success);

            #region old
            //if (CheckCollision(document, view, selectedIds, line, lines, triangle, multipleTagSymbol))
            //{
            //    int offsetLength = 10;
            //    XYZ offset = null;
            //    if (rightOfLefts.GetLength() > offsetLength)
            //        offset = parallelVector * offsetLength;
            //    else if (leftOfRights.GetLength() > offsetLength)
            //        offset = -parallelVector * offsetLength;
            //    else
            //        return AnnotationBuildResult.Success;

            //    avoidP1_Line1 += offset;
            //    avoidP2_Line2 += offset;
            //    avoidP3_Annotation1 += offset;
            //    lines = GetLines(avoidP1_Line1, avoidP2_Line2, avoidP3_Annotation1);
            //    triangle = new Triangle(avoidP1_Line1, avoidP2_Line2, avoidP3_Annotation1);
            //    if (!CheckCollision(document, view, selectedIds, line, lines, triangle, multipleTagSymbol))
            //    {
            //        //TODO 偏移处理
            //        Autodesk.Revit.DB.ElementTransformUtils.MoveElement(document, new ElementId(entity.LineId), offset);
            //        foreach (var tagId in entity.TagIds)
            //        {
            //            Autodesk.Revit.DB.ElementTransformUtils.MoveElement(document, new ElementId(tagId), offset);
            //        }
            //    }
            //}
            //return AnnotationBuildResult.Success;
            #endregion
        }
Exemple #7
0
        public bool CalculateLocations()
        {
            switch (ModelType)
            {
            case PAAModelType.SinglePipe:
                #region single
                var target        = Document.GetElement(TargetId);
                var locationCurve = TargetType.GetLine(target);
                UpdateVectors(locationCurve);
                //干线起始点
                var lineBound = Line.CreateBound(BodyStartPoint, BodyEndPoint);
                if (lineBound.VL_IsIntersect(locationCurve))
                {
                    var intersectionPoints = lineBound.VL_GetIntersectedOrContainedPoints(locationCurve);
                    if (intersectionPoints.Count == 1)
                    {
                        BodyStartPoint = intersectionPoints.FirstOrDefault().ToSameZ(BodyEndPoint);    //.ToSameZ(BodyStartPoint);
                    }
                }
                else
                {
                }            //否则不改变原始坐标,仅重置
                             //支线终点
                if (TextType == PAATextType.Option2)
                {
                    if (!IsRegenerate)
                    {
                        LeafEndPoint = BodyEndPoint + LineWidth * ParallelVector;
                    }
                    //文本位置 start:(附着元素中点+线基本高度+文本高度*(文本个数-1))  end: start+宽
                    //高度,宽度 取决于文本
                    AnnotationLocation = TextType.GetTextLocation(CurrentFontHeight, VerticalVector, BodyEndPoint, LeafEndPoint);
                }
                else
                {
                    if (!IsRegenerate)
                    {
                        LeafEndPoint = BodyEndPoint + (IsReversed ? -LineWidth * ParallelVector : LineWidth * ParallelVector);
                    }
                    var bb = BodyEndPoint - BodyStartPoint;
                    var lb = (LeafEndPoint - BodyEndPoint);
                    if (lb.CrossProductByCoordinateType(bb, VLCoordinateType.XY) < 0)
                    {
                        var temp = LeafEndPoint;
                        LeafEndPoint = BodyEndPoint;
                        BodyEndPoint = temp;
                    }
                    //文本位置 start:(附着元素中点+线基本高度+文本高度*(文本个数-1))  end: start+宽
                    //高度,宽度 取决于文本
                    if (bb.CrossProductByCoordinateType(ParallelVector, VLCoordinateType.XY) < 0)
                    {
                        AnnotationLocation = TextType.GetTextLocation(CurrentFontHeight, VerticalVector, LeafEndPoint, BodyEndPoint);
                    }
                    else
                    {
                        AnnotationLocation = TextType.GetTextLocation(CurrentFontHeight, VerticalVector, BodyEndPoint, LeafEndPoint);
                    }
                }
                return(true);

                #endregion
            case PAAModelType.MultiplePipe:
                #region multiple
                PipeAndNodePoints = new List <ElementAndNodePoint>();
                if (IsRegenerate)
                {
                    for (int i = 0; i < TargetIds.Count; i++)
                    {
                        target = Document.GetElement(TargetIds[i]);
                        var annotationId = AnnotationIds[i];
                        var annotation   = Document.GetElement(annotationId);
                        if (annotation == null)
                        {
                            return(false);
                        }
                        PipeAndNodePoints.Add(new ElementAndNodePoint(target, annotation as IndependentTag));
                    }
                }
                else
                {
                    foreach (var selectedId in TargetIds)
                    {
                        PipeAndNodePoints.Add(new ElementAndNodePoint(Document.GetElement(selectedId)));
                    }
                }
                //平行,垂直 向量
                UpdateVectors(PipeAndNodePoints.First().Line);
                //重叠区间
                XYZ        rightOfLefts;
                XYZ        leftOfRights;
                XYZ        startPoint = TargetLocation;
                List <XYZ> lefts      = new List <XYZ>();
                List <XYZ> rights     = new List <XYZ>();
                if (!IsRegenerate)
                {
                    bool usingX = GetLeftsAndRights(PipeAndNodePoints, lefts, rights);
                    rightOfLefts = usingX ? lefts.First(c => c.X == lefts.Max(p => p.X)) : lefts.First(c => c.Y == lefts.Max(p => p.Y));
                    leftOfRights = usingX ? rights.First(c => c.X == rights.Min(p => p.X)) : rights.First(c => c.Y == rights.Min(p => p.Y));
                    if ((usingX && rightOfLefts.X > leftOfRights.X) || (!usingX && rightOfLefts.Y > leftOfRights.Y))
                    {
                        //TODO 提示无重叠区间
                        return(false);
                    }
                }
                else
                {
                    rightOfLefts = leftOfRights = null;
                }
                //节点计算
                XYZ firstNode;
                if (!IsRegenerate)
                {
                    firstNode = (rightOfLefts + leftOfRights) / 2;
                }
                else
                {
                    locationCurve = PipeAndNodePoints[0].Line;
                    firstNode     = locationCurve.Project(startPoint).XYZPoint;
                }
                PipeAndNodePoints[0].NodePoint = firstNode;
                //节点位置
                for (int i = 1; i < PipeAndNodePoints.Count(); i++)
                {
                    PipeAndNodePoints[i].NodePoint = PipeAndNodePoints[i].Line.Project(PipeAndNodePoints[0].NodePoint).XYZPoint;
                }
                //排序
                if (PipeAndNodePoints.Count() > 1)
                {
                    if (Math.Abs(PipeAndNodePoints[0].NodePoint.Y - PipeAndNodePoints[1].NodePoint.Y) < 0.01)
                    {
                        PipeAndNodePoints = PipeAndNodePoints.OrderBy(c => c.NodePoint.X).ToList();
                    }
                    else
                    {
                        PipeAndNodePoints = PipeAndNodePoints.OrderByDescending(c => c.NodePoint.Y).ToList();
                    }
                }
                TargetIds = PipeAndNodePoints.Select(c => c.Target.Id).ToList();
                //标注定位计算
                XYZ    offset       = GetOffSet();
                bool   overMoved    = false;//位移是否超过的最低限制
                double parallelSkew = offset.GetLengthBySide(ParallelVector);
                foreach (var PipeAndNodePoint in PipeAndNodePoints)
                {
                    PipeAndNodePoint.NodePoint += parallelSkew * ParallelVector;
                }
                TargetLocation = PipeAndNodePoints.First().NodePoint;
                if (IsRegenerate)    // && regenerateType != RegenerateType.RegenerateByPipe)
                {
                    //原始线高度+偏移数据
                    var line             = Document.GetElement(LineId);
                    var orientLineHeight = IsRegenerate ? line.GetParameters(TagProperty.线高度1.ToString()).First().AsDouble() : 0;
                    var verticalSkew     = RegenerateType == RegenerateType.ByMultipleTarget ? 0 : VLLocationHelper.GetLengthBySide(offset, VerticalVector);
                    //if (Math.Abs(VerticalVector.X) > 1 - UnitHelper.MiniValueForXYZ)
                    //    verticalSkew = -verticalSkew;
                    var nodesHeight = UnitHelper.ConvertToFoot((PipeAndNodePoints.Count() - 1) * CurrentFontHeight, VLUnitType.millimeter);
                    overMoved = orientLineHeight + verticalSkew < nodesHeight;
                    var lineHeight = orientLineHeight + verticalSkew;
                    if (overMoved)
                    {
                        lineHeight   = nodesHeight;
                        verticalSkew = nodesHeight - orientLineHeight;
                    }
                    LineHeight = lineHeight;
                }
                else
                {
                    LineHeight = CurrentFontHeight;
                }
                LineSpace = CurrentFontHeight;
                UpdateLineWidth(Document.GetElement(TargetIds.First()));
                //string text = GetFullTextForLine(Document.GetElement(TargetIds.First()));
                //var textWidth = TextRenderer.MeasureText(text, PAAContext.FontManagement.OrientFont).Width;
                //LineWidth = textWidth * PAAContext.FontManagement.CurrentFontWidthSize;
                //标注位置
                for (int i = 0; i < PipeAndNodePoints.Count(); i++)
                {
                    var start = TargetLocation + (LineHeight + i * LineSpace) * VerticalVector;
                    var end   = start + LineWidth * ParallelVector;
                    PipeAndNodePoints[PipeAndNodePoints.Count() - 1 - i].AnnotationPoint = TextType.GetTextLocation(CurrentFontHeight, VerticalVector, start, end);
                }
                #endregion
                return(true);

            default:
                throw new NotImplementedException("未支持该类型的生成");
            }
        }
        public void Execute(UpdaterData updateData)
        {
            try
            {
                var document   = updateData.GetDocument();
                var edits      = updateData.GetModifiedElementIds();
                var collection = CSAContext.GetCollection(document);
                if (CSAContext.IsEditing == true)
                {
                    CSAContext.IsEditing = false;
                    return;
                }
                List <int> movedEntities = new List <int>();
                foreach (var changeId in edits)
                {
                    CSAModel model = null;
                    if (VLConstraintsForCSA.Doc == null)
                    {
                        VLConstraintsForCSA.Doc = document;
                    }

                    #region 根据Target重新生成
                    var targetMoved = collection.Data.FirstOrDefault(c => c.TargetId.IntegerValue == changeId.IntegerValue);
                    if (targetMoved != null)
                    {
                        model = targetMoved;
                        if (movedEntities.Contains(model.TargetId.IntegerValue))
                        {
                            continue;
                        }
                        var creater = CSAContext.Creator;
                        var target  = document.GetElement(model.TargetId);//标注主体失效时删除
                        if (target == null)
                        {
                            collection.Data.Remove(model);
                            continue;
                        }
                        CSAContext.Creator.Regenerate(document, model, target, new XYZ(0, 0, 0));
                        movedEntities.Add(model.TargetId.IntegerValue);
                        CSAContext.IsEditing = true;
                    }
                    #endregion

                    #region 根据Text重新生成
                    var textMoved = collection.Data.FirstOrDefault(c => c.TextNoteIds.FirstOrDefault(p => p.IntegerValue == changeId.IntegerValue) != null);
                    if (textMoved != null)
                    {
                        model = textMoved;
                        if (movedEntities.Contains(model.TargetId.IntegerValue))
                        {
                            continue;
                        }
                        var creater = CSAContext.Creator;
                        var target  = document.GetElement(model.TargetId);//标注主体失效时删除
                        if (target == null)
                        {
                            collection.Data.Remove(model);
                            continue;
                        }
                        //文本更改处理
                        var index   = model.TextNoteIds.IndexOf(changeId);
                        var newText = (document.GetElement(changeId) as TextNote).Text;
                        if (model.Texts[index] != newText)
                        {
                            CompoundStructure compoundStructure = null;
                            HostObjAttributes hoster            = null;
                            if (target is Wall)
                            {
                                hoster            = (HostObjAttributes)((target as Wall).WallType);
                                compoundStructure = hoster.GetCompoundStructure();
                            }
                            if (target is Floor)
                            {
                                hoster            = (HostObjAttributes)((target as Floor).FloorType);
                                compoundStructure = hoster.GetCompoundStructure();
                            }
                            if (target is RoofBase)//屋顶有多种类型
                            {
                                hoster            = (HostObjAttributes)((target as RoofBase).RoofType);
                                compoundStructure = hoster.GetCompoundStructure();
                            }
                            if (compoundStructure == null)
                            {
                                throw new NotImplementedException("关联更新失败,未获取有效的CompoundStructure类型");
                            }
                            var    layers  = compoundStructure.GetLayers();
                            string pattern = @"([\d+\.]+)厚(.+)[\r]?";
                            Regex  regex   = new Regex(pattern);
                            var    match   = regex.Match(newText);
                            if (!match.Success)
                            {
                                PMMessageBox.ShowError("关联更新失败,文本不符合规范");
                                return;
                            }
                            var length       = match.Groups[1].Value;
                            var lengthFoot   = UnitHelper.ConvertToFoot(Convert.ToDouble(length), VLUnitType.millimeter);
                            var materialName = match.Groups[2].Value;
                            var material     = new FilteredElementCollector(document).OfClass(typeof(Material))
                                               .FirstOrDefault(c => c.Name == materialName);
                            if (material == null)
                            {
                                PMMessageBox.ShowError("关联更新失败,未获取到对应名称的材质");
                                return;
                            }
                            //更新
                            layers[index].Width      = lengthFoot;
                            layers[index].MaterialId = material.Id;
                            compoundStructure.SetLayers(layers);
                            IDictionary <int, CompoundStructureError> report = null;
                            IDictionary <int, int> errorMap;
                            try
                            {
                                compoundStructure.IsValid(document, out report, out errorMap);
                                hoster.SetCompoundStructure(compoundStructure);
                            }
                            catch (Exception ex)
                            {
                                PMMessageBox.ShowError("材质设置失败,错误详情:" + (report != null ? string.Join(",", report.Select(c => c.Value)) : ""));
                                throw ex;
                            }

                            ////报错This operation is valid only for non-vertically compound structures
                            //layer = layers[index];
                            //layer.MaterialId = material.Id;
                            ////compoundStructure.SetLayer(index, layer);
                        }
                        else
                        {
                            var textNote = document.GetElement(changeId) as TextNote;
                            if (model.TextNoteTypeElementId.IntegerValue != textNote.TextNoteType.Id.IntegerValue)
                            {
                                model.TextNoteTypeElementId = textNote.TextNoteType.Id;
                                CSAContext.Creator.Regenerate(document, model, target, new XYZ(0, 0, 0));
                            }
                            else
                            {
                                //文本偏移处理
                                //var index = model.TextNoteIds.IndexOf(changeId);
                                //var offset = (document.GetElement(changeId) as TextNote).Coord - model.TextLocations[index];
                                //CompoundStructureAnnotationContext.Creater.Regenerate(document, model, target, offset);
                                //CSAContext.IsEditing = true;//移动会导致偏移 从而二次触发
                            }
                        }
                        movedEntities.Add(model.TargetId.IntegerValue);
                    }
                    #endregion

                    #region 根据Line重新生成
                    var lineMoved = collection.Data.FirstOrDefault(c => c.LineId.IntegerValue == changeId.IntegerValue);
                    if (lineMoved != null)
                    {
                        model = lineMoved;
                        if (movedEntities.Contains(model.TargetId.IntegerValue))
                        {
                            continue;
                        }
                        var creater = CSAContext.Creator;
                        var target  = document.GetElement(model.TargetId);
                        if (target == null)
                        {
                            collection.Data.Remove(model);
                            continue;
                        }
                        CSAContext.Creator.Regenerate(document, model, target);
                        movedEntities.Add(model.TargetId.IntegerValue);
                        CSAContext.IsEditing = true;
                    }
                    #endregion
                }
                CSAContext.Save(document);
            }
            catch (Exception ex)
            {
                VLLogHelper.Error(ex);
            }
        }