Получение из AutoCAD снимков с экрана

Дата публикации: 11 апреля 2010
Дата редактирования: 11 апреля 2010
Состояние статьи: завершена

Написал класс, позволяющий производить снимки как с целого экрана, так и с определённой его области. Статью о самом классе, исходники и откомпилированную версию библиотеки можно найти здесь

Зачем мне это понадобилось в AutoCAD? 

А вот зачем: 

В базе данных на сервере у меня будет размещаться информация о том, в каких dwg-файлах корпоративной библиотеки хранятся описания каких блоков. Для каждого определения блока должно храниться и его изображение, дабы можно было визуально увидеть блок, не открывая чертёж. Для данной задачи и использую указанную мною выше библиотеку. Т.е. пользователь будет добавлять в библиотеку нужный блок, снабжая его текстовым описанием, а так же формируя его растровое изображение для превьюшки.

Ниже привожу код, демонстрирующий один из девяти возможных вариантов получения скрина с экрана монитора из командной строки AutoCAD:

   1:  using System;
   2:  using System.Collections.Generic;
   3:  using System.Linq;
   4:  using System.Text;
   5:  //AutoCAD
   6:  using acad = Autodesk.AutoCAD.ApplicationServices.Application;
   7:  using Autodesk.AutoCAD.ApplicationServices;
   8:  using Autodesk.AutoCAD.DatabaseServices;
   9:  using Autodesk.AutoCAD.EditorInput;
  10:  using Autodesk.AutoCAD.Runtime;
  11:  using Bushman.Screens;
  12:  using System.Drawing;
  13:  using System.Drawing.Imaging;
  14:  using System.IO;
  15:   
  16:  namespace AcadScreenBlock
  17:  {
  18:      public class Class1
  19:      {
  20:          const string ns = "hwd";
  21:          Document dwg;
  22:          Database db;
  23:          Editor ed;
  24:   
  25:          public Class1()
  26:          {
  27:              dwg = acad.DocumentManager.MdiActiveDocument;
  28:              ed = dwg.Editor;
  29:              db = dwg.Database;
  30:          }
  31:   
  32:          [CommandMethod(ns, "www", CommandFlags.Modal)]
  33:          public void Test()
  34:          {
  35:              ScreenManager.RectangleBrush = System.Windows.Media.Brushes.Red;
  36:              ScreenManager.RectangleLineWeigth = 2;
  37:              Bitmap bitmap = ScreenManager.GetBitmapFromScreenManually(ImageFormat.Png);
  38:              bitmap.Save(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments), "123.png"));            
  39:          }
  40:      }
  41:  }

Пусть до запуска команды www мы имеем перед собой на экране следующее изображение:


В результате работы кода, после запуска команды www, и указания мышью интересующего нас для сохранения фрагмента скрина, мы  в каталоге "Мои Документы" получим новый файл, с именем "123.png", 
содержащий в себе скрин указанной нами мышью области, например такой:


Как видим - сложного ничего нет. Остальные восемь способов приводить не буду, т.к. в указанной мною ссылке и так всё подробно разжёвано.

В AutoCAD имеется возможность просмотра изображения блока, без создания его вхождения. Свойство PreviewIcon экземпляра BlockTableRecord возвращает объект Bitmap, инкапсулирующий в себе превьюшку, однако, как оказалось, она очень маленькая, почти как иконка. В этом можно убедиться запустив такой код:


   1:  using System;
   2:  using System.Collections.Generic;
   3:  using System.Linq;
   4:  using System.Text;
   5:  //Acad
   6:  using acad = Autodesk.AutoCAD.ApplicationServices.Application;
   7:  using Autodesk.AutoCAD.ApplicationServices;
   8:  using Autodesk.AutoCAD.DatabaseServices;
   9:  using Autodesk.AutoCAD.EditorInput;
  10:  using Autodesk.AutoCAD.Runtime;
  11:  using System.IO;
  12:  using System.Drawing;
  13:   
  14:   
  15:  namespace AcadBlockManager
  16:  {
  17:      
  18:      public class Class1
  19:      {
  20:          const string ns = "hwd";
  21:          Document dwg;
  22:          Database db;
  23:          Editor ed;
  24:   
  25:          public Class1()
  26:          {
  27:              dwg = acad.DocumentManager.MdiActiveDocument;
  28:              db = dwg.Database;
  29:              ed = dwg.Editor;
  30:          }
  31:   
  32:          [CommandMethod(ns, "ShowBlock", CommandFlags.Modal)]
  33:          public void ShowBlocks()
  34:          {
  35:              using (Transaction tr = dwg.TransactionManager.StartTransaction())
  36:              {
  37:                  BlockTable blockTable = tr.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;
  38:                  List<BlockTableRecord> records = new List<BlockTableRecord>();
  39:                  foreach (ObjectId item in blockTable)
  40:                  {
  41:                      BlockTableRecord record = tr.GetObject(item, OpenMode.ForRead) as BlockTableRecord;
  42:                      string path = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments), "screens");
  43:                      Bitmap img = record.PreviewIcon;
  44:                      try
  45:                      {
  46:                          img.Save(string.Format(@"{0}\{1}.png", path, record.Name));
  47:                      }
  48:                      catch (System.Exception ex)
  49:                      {
  50:                          ed.WriteMessage(string.Format("\n{0}", ex.Message));
  51:                      }
  52:                  }
  53:              } 
  54:          }
  55:      }
  56:  }

В результате работы кода, в каталоге screen (предварительно созданном мною в "Моих Документах") получаю ряд графических файлов. Ниже показан один из них:


Такой размер изображения на предварительном просмотре меня не устраивает, значит встроенные средства AutoCAD для этого дела не подойдут - буду использовать свою библиотеку.

Comments