Объектная модель AutoCAD
Данное издание подготовлено в качестве ознакомительного материала объектной модели AutoCAD. В вкратце, для непосвящённых, объектная модель AutoCAD - это структура объектов: приложения AutoCAD, его документов (открытых чертежей), объектов черчения (точки, линии и т.п.), словарей (смотри документацию по AutoLisp), их свойств и методов. Все эти объекты описаны в системе COM и предоставлены любым языкам программирования. Описание объектной модели осуществлено в файлах с расширением tlb (type library - библиотека типов), а доступ к объёктам и их свойствам описано в реестре. В данном издании все примеры будут строиться для языка программирования Delphi (точнее для его версии Delphi 7). Для самостоятельного ознакомления с объектной моделью AutoCAD желательно транслировать в Delphi библиотеку типов AutoCAD. Для AutoCAD 2004 - это файл acax16enu.tlb, для более ранних версий - acad.tlb. Для этого в меню project выберете пункт меню Import Type Library. Появится окно для выбора прописанных в системном реестре библиотек типов. Может так случиться, что нужной нам библиотеки мы не найдём. Тогда щёлкните на кнопку Add (добавить) и вручную добавьте один из указанных выше файлов. В указанном примере я создал отдельную станицу (Palette Page) для объектов AutoCAD. В результате у вас должно появиться три новых компонента: AcadDocument, AcadDatabase, AcadLayerStateManager. Основным из них является первый компонент AcadDocument. Теперь можете с ним поэкспериментировать. Рекомендую, так же, просмотреть файл AutoCAD_TLB.pas, который был создан при импорте библиотеки типов. В нём вы найдёте много информации по объектной модели AutoCAD, доступной в среде Delphi. Сразу оговорюсь. Наиболее подробное руководство по объектной модели AutoCAD представлено в книге "AutoCAD 2004. Разработка приложений и адаптация. Наиболее полное руководство" Николая Полещука. В этой книге помимо полного обзора объектной модели AutoCAD представлены основные положения по программированию на Delphi AutoCAD (5-ая глава). Помимо того, что можно использовать библиотеку типов, можно, имея уже достаточный опыт программирования для системы AutoCAD, осуществлять соединение с AutoCAD через переменную типа Variant, вызывая функцию GetActiveOleObject или CreateOleObject. Дело в том, что при подключении к AutoCAD первым способом, создаётся обращение только к новому или запущенному документу (напрямую отследить переключение документов не возможно: к сожалению метод OnDocumentActivate не работает так как во встроенном Visual Basic). В следующей главе мы рассмотрим оба способа связи с AutoCAD и метод обхода несоответствия типов в COM и Visual Basic for AutoCAD. Часто возникает вопрос, какими средствами лучше пользоваться для программирования под AutoCAD. И однозначно ответить на этот вопрос для человека, не работающего в Си++ достаточно сложно. Конечно, лучшим средством для программирования пол AutoCAD является Object ARX - среда, разработанная для языка программирования Си++, которая позволяет помимо черчения и отслеживания данных в AutoCAD так же создавать новые типы примитивов (с новыми свойствами и методами). Далее следует вопрос, а что, собственно, вы хотите запрограммировать? Если задача стоит всего лишь в передаче графических данных от вашей программы в AutoCAD и дальнейшее их редактирование, то лучше использовать язык программирования, на котором написана основная часть вашей программы, не прибегая к использованию технологии Object ARX (даже если вы используете Си++). Кстати говоря, все недостатки объектной модели AutoCAD, предоставляемой вашему компилятору, легко (или не совсем) компенсируются встроенными в AutoCAD средами Visual Basic, Visual Lisp.На протяжении всего изложения кода я буду нередко прибегать к использованию этих языков программирования. Далее немного оговорюсь о технической направленности излагаемого материала. Будучи инженером-проектировщиком в транспортном строительстве, я конечно же имел целью автоматизировать свою работу в AutoCAD, поэтому в основном далее будут предлагаться задачи именно по этому направлению. Но я уверен, что специалистам и в других областях будет интересно познакомиться с предлагаемым материалом. Присоединяемся к AutoCAD из Delphi.doc_3783_p2.zip [ZIP / 0 байт]Материалы к этой главе (432,268 байт).[/file] В нашем первом примере будем использовать библиотеку типов AutoCAD_TLB, подгружая её вручную без использования компонентов TAcadDocument. Для примера простого приложения для AutoCAD создадим в Delphi обычное приложение (File>New>Application). В разделе uses вручную допишем модуль AutoCAD_TLB, ComObj. Далее напишем функцию, которая будет отвечать за связь с AutoCAD. Function GetAcadApplication(Visible: Boolean): IAcadApplication; Функция возвращает интерфейс приложения AutoCAD, объявленный в модуле AutoCAD_TLB.pas. Стоит отметить, что почти на каждом шагу нам придётся работать с переменными типа OleVariant и постоянно заниматься преобразованием типов. Теперь можно в любом месте программы присоединиться к запущенной копии AutoCAD или запустить новую. unit Unit1;
interface uses type var implementation {$R *.dfm} Function GetAcadApplication(Visible: Boolean): IAcadApplication; procedure TForm1.FormCreate(Sender: TObject); procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction); procedure TForm1.Button1Click(Sender: TObject); end. Всё работает замечательно. При нажатии кнопки в заголовке нашего приложения отображается наименование текущего чертежа. В Visual Basic for AutoCAD всё гораздо проще - у объекта AcadDocument существует метод Activate, который срабатывает при переключении документов (чертежей) в приложении. В СОМ-структуре AutoCAD почему-то одноимённый метод так не работает. В принципе, он может и не пригодится, когда, например, нам необходимо просто что-то нарисовать в одном чертеже и забыть про все остальные открытые файлы. Но, всё же, проблема актуальна и требует решения. В таком случае может пригодиться следующая методика. На нашу форму в Delphi поместим компонент Timer. Зададим не очень короткий и не очень длинный интервал (например, 150) и в методе OnTimer запишем код проверки текущего чертежа, например, по названию. При этом можно использовать компонент AcadDocument со всеми объявленными в нём методами. В предыдущем примере этих методов у нас не было. Рассмотрим код такой программы. unit Unit1;
interface uses type var implementation {$R *.dfm} procedure TForm1.FormCreate(Sender: TObject); procedure TForm1.Timer1Timer(Sender: TObject); // обработчик на создание нового объекта в текущем чертеже пишет end. Данный код приводит в соответствие класс TAcadDocument в СОМ модели AutoCAD к соответствующему классу в Visual Basic for AutoCAD. По-видимому, требуется небольшое пояснение по поводу "очень тихой проверки имени документа". Такое количество блоков try except end объясняется тем, что при событии, когда пользователь переключит чертежи, по нашему сценарию происходит отсоединение переменной AcadDocument1 от AutoCAD. Дальше всё зависит от промежутка времени, через которое произойдёт очередная попытка проверить имя текущего чертежа. Бедный пользователь замучается закрывать окошки с ошибками (J). На первый взгляд можно было бы и не заниматься играми с таймером, тем более что есть такое свойство как AcadDocument1.Application.ActiveDocument. Однако, ActiveDocument - это свойство, а не класс (то есть без своих или унаследованных методов), и, самое главное, ссылки на функции и процедуры этого свойства (ActiveDocument: IActiveDocument) не относятся к действительно активному чертежу. В итоге - COM модель "ругается" по каждому вашему действию после переключения документа. В следующих главах мы рассмотрим некоторые приёмы черчения примитивов в AutoCAD. Техника черчения в AutoCAD из Delphi.doc_3783_p3.zip [ZIP / 0 байт]Материалы к этой главе (217,174 байт).[/file] При черчении всех примитивов используются основные функции с приставкой add, объявлённые в специальных коллекциях: ModelSpace (контейнер объектов в пространстве модели), PaperSpace (контейнер объектов в пространстве текущего листа), Block (именованный набор объектов). По способу создания объектов их можно разделить на простые и сложные. Простые объекты создаются напрямую одной функцией с заранее подготовленными координатами узловых точек. Сложные объекты, такие, как регионы (Region), твердотельные тела (solid) создаются в СОМ модели поэтапно. Сначала создаются простые примитивы, объединяемые потом в одно сложное. Заранее извинюсь за применение в изложении материала слов на английском языке, но это необходимо из-за того, что чаще всего программисту и пользователю приходится обращаться к зарубежным справочным материалам. Дело в том, что определённый в Delphi и некоторых других языках программирования тип Variant может не распознаваться в некоторых операционных средах или при передачи такого типа по протоколам электронных сетей. Тип OleVariant разработан специально для межплатформенной передачи данных. Однако, не стоит пугаться, учить этот язык для работы с библиотеками типов не придётся. Все языки программирования, поддерживающие СОМ-модели, распознают этот язык автоматически и генерируют файлы с его помощью автоматически, обрабатывая код на вашем "родном" языке программирования. Однако, чтобы поближе разобраться с разработкой СОМ-моделью, можно обратиться к многочисленным источникам, написанным специально для освещения этого достаточно объёмного вопроса. Я же вернусь к этому вопросу в следующих главах при разработке своих собственных серверов автоматизации для AutoCAD. Сейчас же вернёмся непосредственно к созданию примитивов в AutoCAD. Я сразу приведу код небольшой программки, поясняя написанное по-месту. Для составления всех последующих программ я буду пользоваться шаблоном предыдущей программы. unit Unit1;
interface uses type var implementation {$R *.dfm} procedure TForm1.FormCreate(Sender: TObject); procedure TForm1.Timer1Timer(Sender: TObject); procedure TForm1.AcadDocObjectAdded(ASender: TObject; procedure TForm1.Button1Click(Sender: TObject); end. Разберёмся подробнее, что происходит при нажатии кнопки "Начертить от точки". Для задания линии необходимо иметь координаты двух точек. Важное правило: при задании координат узловых точек любых примитивов обязательно указываются все три координаты, даже если чертится двухмерный объект. Это правило диктует СОМ-модель AutoCAD. Для задания первой точки в примере я воспользовался функцией опроса пользователя GetPoint, возвращающей массив координат указанной пользователем точки в интерактивном режиме. Координаты конечной точки отрезка я вычислил через приращения, задаваемые пользователем в соответствующих строчках диалогового окна. Конечно, приведённый выше код достаточно сырой. На практике необходимо осуществить достаточную проверку на возможные ошибки ввода чисел. Так же каждое действие, связанное с переменной документа AutoCAD, необходимо заключать в блок try except end на случай, если пользователь во время ваших действий или запросов решит заняться в AutoCAD чем-нибудь другим или просто отменит вашу команду. При этом нужно осторожно производить все последующие вычисления, связанные с полученными данными из AutoCAD. Большинство функций добавления объектов возвращают интерфейсы добавляемых объектов, поэтому дальнейшее редактирование таких объектов не предоставляет трудностей. Необходимо только помнить, что не все свойства, объявленные в интерфейсе примитива AutoCAD могут быть использованы в версиях AutoCAD, отличных от той, в которой вы работаете. Так, например, в AutoCAD 2004 добавлено свойство TrueColor, позволяющее применять цвета к объектам в формате RGB (Red Green Blue - красный зелёный синий). Если ваша программа использует это свойство, то необходимо понимать, что в более ранних версиях AutoCAD ваша программа работать не сможет. Примеры построения простых примитивов, таких, как точка, окружность, эллипс можно посмотреть в справочной литературе по Visual Basic for AutoCAD. Все эти примеры легко переносятся на любой язык программирования. Следующий пример покажет, как можно выполнять такие построения. Обратите внимание на немаловажные детали, такие, как развёртывание окна AutoCAD, если оно свёрнуто, когда вы делаете запрос пользователю (всё-таки терпение пользователя нужно уважать J). При написании кода построения примитивов в AutoCAD часто приходится задавать координаты узловых точек через переменную типа OleVariant. Для упрощения для этого я внёс небольшую функцию, делающую код программы менее громоздким и более читабельным. Function GetPoint(X, Y, Z: double): OleVariant; Построение примитивов в AutoCADdoc_3783_p4.zip [ZIP / 0 байт]Материалы к этой главе (284,864 байт).[/file] В этой главе будет разобран пример, в котором мы разберём построение всех основных примитивов AutoCAD. При этом, постараемся разобрать новые свойства примитивов, введённых в AutoCAD 2004.
Страница сайта http://silicontaiga.ru
Оригинал находится по адресу http://silicontaiga.ru/home.asp?artId=6495 |