原文链接
    外部参照的
    命令行工具: AttachXrefs
    BindXrefs
    DetachXrefs
    OpenXrefs
    ReloadXrefs
    ReloadAllXrefs
    UnloadXrefs

    1. using System;
    2. using System.IO;
    3. using System.Text;
    4. using Autodesk.AutoCAD.Runtime;
    5. using Autodesk.AutoCAD.Windows;
    6. using Autodesk.AutoCAD.EditorInput;
    7. using Autodesk.AutoCAD.Geometry;
    8. using Autodesk.AutoCAD.DatabaseServices;
    9. using Autodesk.AutoCAD.ApplicationServices;
    10. using ofdFlags = Autodesk.AutoCAD.Windows.OpenFileDialog.OpenFileDialogFlags;
    11. [assembly: ExtensionApplication(typeof(cgabriel.XrefTools))]
    12. [assembly: CommandClass(typeof(cgabriel.XrefTools))]
    13. namespace cgabriel
    14. {
    15. public class XrefTools : IExtensionApplication
    16. {
    17. #region ExtensionAppImplementation
    18. public void Initialize() { }
    19. public void Terminate() { }
    20. #endregion
    21. #region Helpers
    22. public delegate void ProcessSingleXref(BlockTableRecord btr);
    23. public delegate void ProcessMultipleXrefs(ObjectIdCollection xrefIds);
    24. public static void detachXref(BlockTableRecord btr)
    25. {
    26. Application.DocumentManager.MdiActiveDocument.Database.DetachXref(btr.ObjectId);
    27. }
    28. public static void openXref(BlockTableRecord btr)
    29. {
    30. string xrefPath = btr.PathName;
    31. if (xrefPath.Contains(".\\"))
    32. {
    33. string hostPath =
    34. Application.DocumentManager.MdiActiveDocument.Database.Filename;
    35. Directory.SetCurrentDirectory(Path.GetDirectoryName(hostPath));
    36. xrefPath = Path.GetFullPath(xrefPath);
    37. }
    38. if (!File.Exists(xrefPath)) return;
    39. Document doc = Application.DocumentManager.Open(xrefPath, false);
    40. if (doc.IsReadOnly)
    41. {
    42. System.Windows.Forms.MessageBox.Show(
    43. doc.Name + " opened in read-only mode.",
    44. "OpenXrefs",
    45. System.Windows.Forms.MessageBoxButtons.OK,
    46. System.Windows.Forms.MessageBoxIcon.Warning);
    47. }
    48. }
    49. public static void bindXrefs(ObjectIdCollection xrefIds)
    50. {
    51. Application.DocumentManager.MdiActiveDocument.Database.BindXrefs(xrefIds, false);
    52. }
    53. public static void reloadXrefs(ObjectIdCollection xrefIds)
    54. {
    55. Application.DocumentManager.MdiActiveDocument.Database.ReloadXrefs(xrefIds);
    56. }
    57. public static void unloadXrefs(ObjectIdCollection xrefIds)
    58. {
    59. Application.DocumentManager.MdiActiveDocument.Database.UnloadXrefs(xrefIds);
    60. }
    61. public static void processXrefs(string promptMessage, ProcessSingleXref process)
    62. {
    63. Editor ed = Application.DocumentManager.MdiActiveDocument.Editor;
    64. TypedValue[] filterList = { new TypedValue(0, "INSERT") };
    65. ed.WriteMessage(promptMessage);
    66. PromptSelectionResult result = ed.GetSelection(new SelectionFilter(filterList));
    67. if (result.Status != PromptStatus.OK) return;
    68. ObjectId[] ids = result.Value.GetObjectIds();
    69. Database db = Application.DocumentManager.MdiActiveDocument.Database;
    70. using (Transaction tr = db.TransactionManager.StartTransaction())
    71. {
    72. ObjectIdCollection xrefIds = new ObjectIdCollection();
    73. foreach (ObjectId id in ids)
    74. {
    75. BlockReference blockRef = (BlockReference)tr.GetObject(id, OpenMode.ForRead, false, true);
    76. ObjectId bId = blockRef.BlockTableRecord;
    77. if (!xrefIds.Contains(bId))
    78. {
    79. xrefIds.Add(bId);
    80. BlockTableRecord btr = (BlockTableRecord)tr.GetObject(bId, OpenMode.ForRead);
    81. if (btr.IsFromExternalReference)
    82. process(btr);
    83. }
    84. }
    85. tr.Commit();
    86. }
    87. }
    88. public static void processXrefs(string promptMessage, ProcessMultipleXrefs process)
    89. {
    90. Editor ed = Application.DocumentManager.MdiActiveDocument.Editor;
    91. TypedValue[] filterList = { new TypedValue(0, "INSERT") };
    92. ed.WriteMessage(promptMessage);
    93. PromptSelectionResult result = ed.GetSelection(new SelectionFilter(filterList));
    94. if (result.Status != PromptStatus.OK) return;
    95. ObjectId[] ids = result.Value.GetObjectIds();
    96. Database db = Application.DocumentManager.MdiActiveDocument.Database;
    97. using (Transaction tr = db.TransactionManager.StartTransaction())
    98. {
    99. ObjectIdCollection blockIds = new ObjectIdCollection();
    100. foreach (ObjectId id in ids)
    101. {
    102. BlockReference blockRef = (BlockReference)tr.GetObject(id, OpenMode.ForRead, false, true);
    103. blockIds.Add(blockRef.BlockTableRecord);
    104. }
    105. ObjectIdCollection xrefIds = filterXrefIds(blockIds);
    106. if (xrefIds.Count != 0)
    107. process(xrefIds);
    108. tr.Commit();
    109. }
    110. }
    111. public static void attachXrefs(string[] fileNames)
    112. {
    113. Editor ed = Application.DocumentManager.MdiActiveDocument.Editor;
    114. Array.Sort(fileNames);
    115. Database db = Application.DocumentManager.MdiActiveDocument.Database;
    116. double dimScale = db.Dimscale;
    117. foreach (string fileName in fileNames)
    118. {
    119. PromptPointOptions options = new PromptPointOptions("Pick insertion point for " + fileName + ": ");
    120. options.AllowNone = false;
    121. PromptPointResult pt = ed.GetPoint(options);
    122. if (pt.Status != PromptStatus.OK) continue;
    123. double xrefScale = getDwgScale(fileName);
    124. double scaleFactor = dimScale / xrefScale;
    125. using (Transaction tr = Application.DocumentManager.MdiActiveDocument.TransactionManager.StartTransaction())
    126. {
    127. ObjectId xrefId = db.AttachXref(fileName, Path.GetFileNameWithoutExtension(fileName));
    128. BlockReference blockRef = new BlockReference(pt.Value, xrefId);
    129. BlockTableRecord layoutBlock = (BlockTableRecord)tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite);
    130. blockRef.ScaleFactors = new Scale3d(scaleFactor, scaleFactor, scaleFactor);
    131. blockRef.Layer = "0";
    132. layoutBlock.AppendEntity(blockRef);
    133. tr.AddNewlyCreatedDBObject(blockRef, true);
    134. tr.Commit();
    135. }
    136. }
    137. }
    138. public static double getDwgScale(string fileName)
    139. {
    140. using (Database db = new Database(false, true))
    141. {
    142. db.ReadDwgFile(fileName, FileOpenMode.OpenForReadAndAllShare, false, string.Empty);
    143. return db.Dimscale;
    144. }
    145. }
    146. public static ObjectIdCollection filterXrefIds(ObjectIdCollection blockIds)
    147. {
    148. ObjectIdCollection xrefIds = new ObjectIdCollection();
    149. foreach (ObjectId bId in blockIds)
    150. {
    151. if (!xrefIds.Contains(bId))
    152. {
    153. BlockTableRecord btr = (BlockTableRecord)bId.GetObject(OpenMode.ForRead);
    154. if (btr.IsFromExternalReference)
    155. xrefIds.Add(bId);
    156. }
    157. }
    158. return xrefIds;
    159. }
    160. #endregion
    161. #region Commands
    162. [CommandMethod("XrefTools", "AttachXrefs", CommandFlags.Modal | CommandFlags.DocExclusiveLock)]
    163. public static void XrefAttach()
    164. {
    165. string initFolder = Application.DocumentManager.MdiActiveDocument.Database.Filename.ToUpper();
    166. if (initFolder.Contains("PLOT"))
    167. {
    168. initFolder = initFolder.Replace("-PLOT.DWG", "");
    169. initFolder = initFolder.Replace("PLOT\\", "");
    170. initFolder = initFolder.Replace("PLOTS\\", "");
    171. if (!Directory.Exists(initFolder))
    172. initFolder = Application.DocumentManager.MdiActiveDocument.Database.Filename;
    173. }
    174. ofdFlags flags = ofdFlags.DefaultIsFolder | ofdFlags.AllowMultiple;
    175. OpenFileDialog dlg = new OpenFileDialog("Select Drawings to Attach", initFolder, "dwg", "Select Xrefs", flags);
    176. if (dlg.ShowDialog() == System.Windows.Forms.DialogResult.OK)
    177. attachXrefs(dlg.GetFilenames());
    178. }
    179. [CommandMethod("XrefTools", "BindXrefs", CommandFlags.Modal | CommandFlags.DocExclusiveLock)]
    180. public static void XrefBind()
    181. {
    182. processXrefs("\nSelect xrefs to bind: ", XrefTools.bindXrefs);
    183. }
    184. [CommandMethod("XrefTools", "DetachXrefs", CommandFlags.Modal | CommandFlags.DocExclusiveLock)]
    185. public static void XrefDetach()
    186. {
    187. processXrefs("\nSelect xrefs to detach: ", XrefTools.detachXref);
    188. }
    189. [CommandMethod("XrefTools", "OpenXrefs", CommandFlags.Session)]
    190. public static void XrefOpen()
    191. {
    192. processXrefs("\nSelect xrefs to open: ", XrefTools.openXref);
    193. }
    194. [CommandMethod("XrefTools", "ReloadXrefs", CommandFlags.Modal | CommandFlags.DocExclusiveLock)]
    195. public static void XrefReload()
    196. {
    197. processXrefs("\nSelect xrefs to reload: ", XrefTools.reloadXrefs);
    198. }
    199. [CommandMethod("XrefTools", "ReloadAllXrefs", CommandFlags.Modal | CommandFlags.DocExclusiveLock)]
    200. public static void XrefReloadAll()
    201. {
    202. Database db = Application.DocumentManager.MdiActiveDocument.Database;
    203. using (Transaction tr = db.TransactionManager.StartTransaction())
    204. {
    205. BlockTable blockTbl = (BlockTable)tr.GetObject(db.BlockTableId, OpenMode.ForRead);
    206. ObjectIdCollection blockIds = new ObjectIdCollection();
    207. foreach (ObjectId bId in blockTbl)
    208. blockIds.Add(bId);
    209. ObjectIdCollection xrefIds = filterXrefIds(blockIds);
    210. if (xrefIds.Count != 0)
    211. db.ReloadXrefs(xrefIds);
    212. tr.Commit();
    213. }
    214. }
    215. [CommandMethod("XrefTools", "UnloadXrefs", CommandFlags.Modal | CommandFlags.DocExclusiveLock)]
    216. public static void XrefUnload()
    217. {
    218. processXrefs("\nSelect xrefs to unload: ", XrefTools.unloadXrefs);
    219. }
    220. #endregion
    221. }
    222. }