Экспорт нарисованных линиями таблиц из AutoCAD в Excel

Моим пользователям часто присылают чертежи, в которых таблицы нарисованы линиями, а текст в ячейках выполнен однострочным текстом. Однако эти таблицы им нужны в Excel. 
Количество столбцов и строк может быть произвольным. Сразу обозначаю важный момент: данное решение ориентировано на таблицы, не имеющие в своём составе объединённых ячеек и при этом каждая ячейка должна содержать текст (т.е. не являться пустой).

Поскольку Excel свободно читает текстовые файлы, содержимое которых разделено табуляторами, то не мудрствуя лукаво этим и воспользуюсь.

Присылаемые таблицы (выполненные линиями и однострочным текстом) выглядят так:


Результат можно открыть в Блокноте:


А можно сразу открыть в Excel:



Далее приведён код, решающий данную задачу:

C# 3.0 & .Net Framework 3.5 SP1


   1:  using System;
   2:  using System.Collections.Generic;
   3:  using System.Linq;
   4:  using System.Text;
   5:  using acad = Autodesk.AutoCAD.ApplicationServices.Application;
   6:  using Autodesk.AutoCAD.ApplicationServices;
   7:  using Autodesk.AutoCAD.DatabaseServices;
   8:  using Autodesk.AutoCAD.EditorInput;
   9:  using Autodesk.AutoCAD.Runtime;
  10:  using System.IO;
  11:   
  12:   
  13:  namespace ConvertTable
  14:  {
  15:      /// <summary>
  16:      /// Класс, содержащий в себе единственный метод, который и выполняет конвертацию нарисованной таблицы в разделённый табуляторами
  17:      /// текстовый файл.
  18:      /// </summary>
  19:      public class Program
  20:      {
  21:          const string ns = "hwd";
  22:   
  23:          Document dwg;
  24:          Editor ed;
  25:          Database db;
  26:   
  27:          public Program()
  28:          {
  29:              dwg = acad.DocumentManager.MdiActiveDocument;
  30:              ed = dwg.Editor;
  31:              db = dwg.Database;
  32:          }
  33:   
  34:          /// <summary>
  35:          /// Экспортировать простую нарисованную линиями таблицу в Excel.
  36:          /// Расчитано на то, что в таблице нет объединённых строк или столбцов.
  37:          /// Программа запрашивает количество столбцов, которые должна иметь новая таблица, 
  38:          /// а затем, для каждого столбца просит выбрать все текстовые объекты. Порядок
  39:          /// выбора объектов в рамках столбца роли не играет.
  40:          /// В результате работы, в том же каталоге где размещён файл чертежа, создаётся одноимённый текстовый файл,
  41:          /// в котором размещаются экспортированные данные, разделённые табулятором (т.о. файл можно
  42:          /// открыть в Excel - тот его нормально распознает).
  43:          /// </summary>
  44:          [CommandMethod(ns, "GarbageToTxt", CommandFlags.Modal)]
  45:          public void GarbageToTxt()
  46:          {
  47:              TypedValue[] tv = new TypedValue[1];
  48:              tv.SetValue(new TypedValue((int)DxfCode.Start, "TEXT"), 0);
  49:              PromptIntegerResult columnsCountResult;
  50:              string[] rows = null;
  51:              columnsCountResult = ed.GetInteger("Количество колонок");
  52:              if (columnsCountResult.Status == PromptStatus.OK)
  53:              {
  54:                  for (int i = 0; i < columnsCountResult.Value; i++)
  55:                  {
  56:                      ed.WriteMessage("Выберите записи в составе колонки № " + (i+1).ToString());
  57:                      SelectionFilter filter = new SelectionFilter(tv);
  58:                      PromptSelectionResult result;
  59:                      result = ed.GetSelection(filter);
  60:                      if (result.Status == PromptStatus.OK)
  61:                      {
  62:                          using (Transaction trs = dwg.TransactionManager.StartTransaction())
  63:                          {
  64:                              SelectionSet acSSet = result.Value;
  65:                              List<DBText> txt = new List<DBText>();
  66:                              foreach (SelectedObject item in acSSet)
  67:                              {
  68:                                  DBText text = trs.GetObject(item.ObjectId, OpenMode.ForRead) as DBText;
  69:                                  txt.Add(text);
  70:                              }
  71:                              if (i == 0)
  72:                              {
  73:                                  rows = txt.OrderBy(n => n.Position.Y).Select(n => n.TextString).ToArray();
  74:                              }
  75:                              else
  76:                              {
  77:                                  string[] column = txt.OrderBy(n => n.Position.Y).Select(n => n.TextString).ToArray();
  78:                                  int m = 0;
  79:                                  foreach (string ttt in column)
  80:                                  {
  81:                                      rows[m] = rows[m] + "\t" + column[m];
  82:                                      m++;
  83:                                  }
  84:                              }
  85:                          }
  86:                      }
  87:                  }
  88:                  string fileName = dwg.Name.Substring(0, dwg.Name.Length-3) + "txt";
  89:                  try
  90:                  {                    
  91:                      StreamWriter sw = new StreamWriter(fileName, false, Encoding.Default);
  92:                      foreach (string item in rows.Reverse())
  93:                      {
  94:                          sw.WriteLine(item);
  95:                      }
  96:                      sw.Close();
  97:                  }
  98:                  catch (System.Exception ex)
  99:                  {
 100:                      ed.WriteMessage(ex.Message);
 101:                  }
 102:                  ed.WriteMessage(string.Format("Результат экспорта находится в файле '{0}'.", fileName));
 103:              }          
 104:          }
 105:      }
 106:  }

Откомпилированный модуль здесь.
Исходники здесь.

Для работы библиотеки, на компьютере должен быть установлен .Net Framework 3.5 SP1, который можно бесплатно скачать с сайта Майкрософт. Код написан для AutoCAD 2009 SP3 Enu.

Команда, выполняющая конвертацию: GarbageToTxt
Comments