Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу) - Страница 145
| Правила | Регистрация | Пользователи | Сообщения за день |  Справка по форуму | Файлообменник |

Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > LISP > Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)

Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)

Ответ
Поиск в этой теме
Непрочитано 20.07.2008, 20:12 1 |
Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)
Red Nova
 
ՃԱՐՏԱՐԱԳԵՏ, տ.գ.թ.
 
Торонто
Регистрация: 23.10.2007
Сообщений: 1,990

Со школы не ладится у меня с программированием. Все предметы щелкал, а на экзамене по информатике (Visual foxpro) программку типа суммирования столбцов списал у соседа (это уже в университете).
Не смотря на эте намерен научится писать программы для Автокада на лиспе, скачал книгу Хювенена, несколько примеров создания программ, но после получасового “смотрения” таких книг мое мышление явно притормаживает.
Решил пойти другим путем.
Нашел самый короткий лисп из моей коллекции, и прошу программистов с этого форума пошагово объяснить какой символ что означает. Надеюсь на вашу помощь.


Код:
[Выделить все]
(defun c:make-blocks-explodeable (/ adoc)
  (vl-load-com)
  (vla-startundomark
    (setq adoc (vla-get-activedocument (vlax-get-acad-object)))
    ) ;_ end of vla-startundomark
  (vlax-for blk_def (vla-get-blocks adoc)
    (if (and (equal (vla-get-isxref blk_def) :vlax-false)
             (equal (vla-get-islayout blk_def) :vlax-false)
             ) ;_ end of and
      (vl-catch-all-apply '(lambda () (vla-put-explodable blk_def :vlax-true)))
      ) ;_ end of if
    ) ;_ end of vlax-for
  (vla-endundomark adoc)
  (princ)
  ) ;_ end of defun
_____________________________________________________________________________________________________________

Прошло много лет и топик теперь представляет из себя площадку для обучения азов программирования для многих начинающих.
Так что начинающие лиспогрызы приветствуются .
__________________
Блог

Последний раз редактировалось Red Nova, 12.07.2017 в 05:43.
Просмотров: 2049494
 
Непрочитано 13.02.2016, 00:10
#2881
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 40,411


Надо все-таки отдыхать иногда Замени (car x) на x.
__________________
Моя библиотека lisp-функций
---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 13.02.2016, 12:20
#2882
Inferi


 
Регистрация: 14.05.2015
Сообщений: 33


(member <выражение> <список>)
Эта функция просматривает <список> - встречается ли <выражение> и возвращает часть <списка>, начинающуюся с первого найденного <выражения>. Если в <списке> нет <выражения>, MEMBER возвращает nil.
Например:
(member 'c '(a b c d e)) возвращает (C D E)
(member 'q '(a b c d e)) возвращает nil

Работает вот так, но возвращает список имен с первого найденного выражения и до конца, а нужно пройтись по списку и выбрать только те имена которые удовлетворяют условию соответствия по ldata:
Код:
[Выделить все]
(setq list_mleader_ldata
       (vl-remove-if
         (function (lambda (x)
                     (member value (list (vlax-ldata-get (vlax-ename->vla-object x) "mleader_name_blk")))
                     ) ;_ end of lambda
                   ) ;_ end of function
         (_dwgru-conv-pickset-to-list (ssget))
         ) ;_ end of vl-remove-if
      ) ;_ end of setq

(defun _dwgru-conv-pickset-to-list (value)
  (vl-remove-if (function listp) (mapcar (function cadr) (ssnamex value)))
  ) ;_ end of defun
----- добавлено через ~1 ч. -----
Нашел решение, функция возвращает список имен примитивов с фильтрацией по ldata и его значению:
Код:
[Выделить все]
(defun lst_nameobj_ldatavalue (ldata ldatavalue)
(setq list_nameobj_ldata
       (vl-remove-if-not
         (function (lambda (x)
                     (equal ldatavalue (vlax-ldata-get (vlax-ename->vla-object x) ldata))
                     ) ;_ end of lambda
                   ) ;_ end of function
         (_dwgru-conv-pickset-to-list (ssget))
         ) ;_ end of vl-remove-if
      ) ;_ end of setq
);_ end of defun
аргументы:
ldata - строка
ldatavalue -строка
пример вызова: (lst_nameobj_ldatavalue ldata ldatavalue)

----- добавлено через ~12 ч. -----
Чего то совсем в тупик зашел, необходимо сравнить элементы списков, и объединить их, может кому не лень поломать голову
Имеем:
список 1 - (("строка1" <Имя объекта: ...>) ("строка2" <Имя объекта: ...>) ...)
список 2 - (("строка1" "номер1") ("строка2" "номер2") ...)
На выходе список - 3:
список 3 - (("строка1" <Имя объекта: ...> "номер1") ("строка2" <Имя объекта: ...> "номер2") ...)
Примечание:
Список 3, полученный объединением элементов списка 1 с строками списка 2 ("номер1", "номер2"), при условии равенства первых строк "строка1"="строка1".
Для примера два списка:
Код:
[Выделить все]
(setq lst1 '(("Отвод круглый %%C125-45%%D" <Имя объекта: 7ff7a6d07510>) ("Отвод круглый %%C125-45%%D" <Имя объекта: 7ff7a6d074c0>) ("Переход 250x150-%%C125" <Имя объекта: 7ff7a6d07280>) ("Отвод круглый %%C100-90%%D" <Имя объекта: 7ff7a6d070a0>) ("Отвод круглый %%C100-90%%D" <Имя объекта: 7ff7a6d07050>) ("Отвод круглый %%C100-90%%D" <Имя объекта: 7ff7a6d07000>) ("Отвод круглый %%C100-90%%D" <Имя объекта: 7ff7a6d04f20>))
      lst2 '(("" "Подсчет блоков на чертеже") ("Имя блока" "    ") ("Отвод круглый %%C100-90%%D" "1") ("Отвод круглый %%C125-45%%D" "2") ("Переход 250x150-%%C125" "3") ("Всего" "")))
Спасибо за внимание!
Inferi вне форума  
 
Непрочитано 21.02.2016, 12:39
#2883
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Здравствуйте Уважаемые форумчане!!! Очень нужна ваша помощь!!! Нужно сделать выборку блоков по значению атрибута. Много примерных программ, но что-то никак не получается итог.Помогите пожалуйста чем можете, За любой совет буду благодарна!!!
aaalenaaa вне форума  
 
Непрочитано 21.02.2016, 12:53
#2884
Сергей812


 
Регистрация: 10.08.2013
Сообщений: 11,499


ну так выкладывайте, что не получается)
задача сводиться к двум подзадачам:
1. Получение выборки (ssget) с чертежа с использованием фильтра: тип примитивов - вставка блока, слой - такой-то и т.д.
2. Проход по полученному списку вставок блока, и если в блоке есть указанный атрибут и значение атрибута совпадает с искомым - занести в выходной список.
Сергей812 вне форума  
 
Непрочитано 21.02.2016, 12:57
#2885
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


http://experement.spb.ru/wiki/doku.p...ickselectblock
Программка на этой странице замечательно мне подходит, но почему-то по завершению выборки не происходит(((( Помогите пожалуйста, очень нужно!!!

----- добавлено через ~7 мин. -----
http://experement.spb.ru/wiki/doku.p...ickselectblock
Ссылка, по которой можно скачать программку, котоая мне идеально подходит,но по итогу выборки не происходит без какой либо ошибки.
aaalenaaa вне форума  
 
Непрочитано 21.02.2016, 13:05
#2886
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 40,411


aaalenaaa, приведи свой код - тогда и можно будет научить. А сделать за тебя и для тебя программу - это в Поиск исполнителей.
__________________
Моя библиотека lisp-функций
---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 21.02.2016, 15:33
#2887
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


А бы очень-очень хотела научиться сама писать или хотя бы править лисп. А то у меня идей куча, чтоб свою работу в атокаде оптимизировать, а реализовать сложно. Если есть ссылки, что почитать про создание лисп - буду благодарна!!! Даже не для этого примера очень хочу разобраться, но я не программист.
А по этой теме: вот этот лисп как мне кажется должен мне подходить, только выбирать нужно все блоки с одинаковым значением атрибута, и их нужно оставлять выделенными, чтоб можно было править. И еще он почему то не работает.Почему? А то может он мне как раз подойдет. Посмотрите пожалуйста хоть работает он и что делает? Спасибо!!!

Последний раз редактировалось aaalenaaa, 21.02.2016 в 16:41.
aaalenaaa вне форума  
 
Непрочитано 21.02.2016, 15:36
#2888
Alan

CAD
 
Регистрация: 28.08.2003
Киев
Сообщений: 1,834
<phrase 1=


Цитата:
Сообщение от aaalenaaa Посмотреть сообщение
хотела научиться сама писать или хотя бы править лисп.
Используй тег Код
__________________
По теории майский жук летать не может.
Но он этого не знает. И летает...
Alan вне форума  
 
Непрочитано 21.02.2016, 16:27
#2889
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Код:
[Выделить все]
;;; (ax:FindBlockTagValue (vla-get-activedocument
;;; (vlax-get-acad-object)) "blockname" "tagname" "tagvalue")
(defun ax:FindBlockTagValue
       (doc bn tagname value / layout i atts tag sset c)
  (vlax-for layout (vla-get-layouts doc)
    (vlax-for i (vla-get-block layout)
      (if (and
            (= (vla-get-objectname i) "AcDbBlockReference")
            (= (strcase (vla-get-name i)) (strcase bn))
          )
        (if (and
              (= (vla-get-hasattributes i) :vlax-true)
              (safearray-value
                (setq atts
                       (vlax-variant-value
                         (vla-getattributes i)
                       )
                )
              )
            )
          (progn
            (foreach tag (vlax-safearray->list atts)
              (if (and
                    (= (strcase tagname)
                       (strcase (vla-get-TagString tag))
                    )
                    (= value (vla-get-TextString tag))
                  )
                (progn
                  (if (not sset)
                    (setq sset (ssadd (vlax-vla-object->ename i)))
                    (ssadd (vlax-vla-object->ename i) sset)
                  )
                )
              )
            )
          )
        )
      )
    )
  )
  (sssetfirst nil sset)
)
----- добавлено через ~29 мин. -----
Код:
[Выделить все]
// Основной модуль
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
 
using App = Autodesk.AutoCAD.ApplicationServices;
using cad = Autodesk.AutoCAD.ApplicationServices.Application;
using Db = Autodesk.AutoCAD.DatabaseServices;
using Ed = Autodesk.AutoCAD.EditorInput;
using Gem = Autodesk.AutoCAD.Geometry;
using Rtm = Autodesk.AutoCAD.Runtime;
using Gi = Autodesk.AutoCAD.GraphicsInterface;
 
namespace QuickSelect
{
    public class Commands
    {
        public static List<string> AttList = new List<string>();
        public static string AttValue = "";
        private static string Exit = "Exit";
 
        static public void ClearAttListValue()
        {
            AttValue = "";
            AttList.Clear();
            AttList.Add(Exit);
        }
 
 
        [Rtm.CommandMethod("bx_quickselect", Rtm.CommandFlags.UsePickSet  |
                                             Rtm.CommandFlags.Redraw |
                                             Rtm.CommandFlags.Modal)]
        static public void bx_quickselect()
        {
 
            // Получение текущего документа и базы данных
            App.Document acDoc = App.Application.DocumentManager.MdiActiveDocument;
            Db.Database acCurDb = acDoc.Database;
            Ed.Editor acEd = acDoc.Editor;
            ClearAttListValue();
 
            //Секция предварительного выбора
            Ed.PromptSelectionResult acSSPrompt = acEd.SelectImplied();
            Ed.SelectionSet acSSet = null;
 
            // Если статус запроса OK, объекты были выбраны перед запуском команды
            if (acSSPrompt.Status == Ed.PromptStatus.OK)
                            acSSet = acSSPrompt.Value;
 
            Dictionary<Db.ObjectId, string> ObjID_Dic = new Dictionary<Db.ObjectId, string>();
 
            Ed.PromptEntityOptions EntOpt = new Ed.PromptEntityOptions("\n Select block:");
            EntOpt.SetRejectMessage("\n Entity must be a block.");
            EntOpt.AddAllowedClass(typeof(Db.BlockReference), false);
            EntOpt.AllowObjectOnLockedLayer = true;
            Ed.PromptEntityResult EntRes = acEd.GetEntity(EntOpt);
 
            if (EntRes.Status != Ed.PromptStatus.OK)
            {
                acEd.WriteMessage("\n Cencel.");
                return;
            }
 
            String acBlockName = "0";
 
            // старт транзакции
            // Ищу истенное имя выбранного блока и читаю его атрибуты
            using (Db.Transaction acTrans = acCurDb.TransactionManager.StartOpenCloseTransaction())
            {
                // Открытие таблицы Блоков для чтения
                Db.BlockTable acBlkTbl = acTrans.GetObject(acCurDb.BlockTableId, 
                                                Db.OpenMode.ForRead) as Db.BlockTable;
                // Открытие записи таблицы Блоков пространства Модели для записи
                Db.BlockTableRecord acBlkTblRecMS = acTrans.GetObject(acBlkTbl[Db.BlockTableRecord.ModelSpace],
                                                Db.OpenMode.ForRead) as Db.BlockTableRecord;
 
 
                //Получаю выбранный блок
                Db.BlockReference acBlock = acTrans.GetObject(EntRes.ObjectId, Db.OpenMode.ForRead) as Db.BlockReference;
                //Получаю определение блока в таблице блоков
                Db.BlockTableRecord acBlkTblRec = acTrans.GetObject(acBlock.BlockTableRecord, Db.OpenMode.ForRead) 
                    as Db.BlockTableRecord;
 
 
                // Получаю определение блока в таблице динамических блоков
                // Запоминаю истинное имя блока
                acBlockName = acBlock.Name;
 
                if (acBlock.IsDynamicBlock)
                {
                    acBlkTblRec = acTrans.GetObject(acBlock.DynamicBlockTableRecord, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                    Db.BlockTableRecord blr_nam = acTrans.GetObject(acBlkTblRec.ObjectId, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                    acBlockName = blr_nam.Name;
                }
 
                if (acBlkTblRec.HasAttributeDefinitions)
                {
                    foreach (Db.ObjectId objID in acBlkTblRec)
                    {
                        Db.DBObject dbObj = acTrans.GetObject(objID, Db.OpenMode.ForRead) as Db.DBObject;
                        if (dbObj is Db.AttributeDefinition)
                        {
                            Db.AttributeDefinition acAtt = dbObj as Db.AttributeDefinition;
                            if (AttList.Contains(acAtt.Tag) != true)
                                AttList.Add(acAtt.Tag);
                        }
                    }
                }
                //Я в этой транзакции ничего не меняю, Все открываю только для чтения.
                //соответственно и вносить изменения не нужно.
                //acTrans.Commit();
            }
 
 
            if (AttList.Count == 1)
                return;
 
            QuickSelect.Form1 myform_name = new QuickSelect.Form1();
            Autodesk.AutoCAD.ApplicationServices.Application.ShowModalDialog(myform_name);
 
            if (AttValue == Exit)
                return;
 
            string AttName = AttValue;
            // Вот тут нужно очистить переменные
            ClearAttListValue();
            //// тут получить все возможние значения данного атрибута и 
            //// заполним массив AttList снова вызвать форму
            using (Db.Transaction acTrans = acCurDb.TransactionManager.StartOpenCloseTransaction())
            {
                if (acSSet == null)
                {
                    Db.TypedValue[] acTypValAr = new Db.TypedValue[1];
                    Db.TypedValue typedValue = new Db.TypedValue(0, "INSERT");
                    acTypValAr.SetValue(typedValue, 0);
                    Ed.SelectionFilter acSelFtr = new Ed.SelectionFilter(acTypValAr);
                    acSSPrompt = acEd.SelectAll(acSelFtr);
                    acSSet = acSSPrompt.Value;
                }
 
                foreach (Db.ObjectId objID in acSSet.GetObjectIds())
                {
                    // Проверка, нужно убедится в правильности полученного объекта
                    if (objID != null)
                    {
                        // Открытие объекта для
                        Db.Entity dbObj = acTrans.GetObject(objID, Db.OpenMode.ForRead) as Db.Entity;
                        if (dbObj != null)
                        {
                            if (dbObj is Db.BlockReference)
                            {
                                Db.BlockReference acBlock = dbObj as Db.BlockReference;
                                Db.BlockTableRecord acBlkTblRec;
                                acBlkTblRec = acTrans.GetObject(acBlock.BlockTableRecord, Db.OpenMode.ForRead) as Db.BlockTableRecord;
 
                                String BlockName = acBlock.Name;
                                if (acBlock.IsDynamicBlock)
                                {
                                    acBlkTblRec = acTrans.GetObject(acBlock.DynamicBlockTableRecord, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                                    Db.BlockTableRecord blr_nam = acTrans.GetObject(acBlkTblRec.ObjectId, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                                    BlockName = blr_nam.Name;
                                }
 
                                if (BlockName == acBlockName)
                                {
                                    if (acBlkTblRec.HasAttributeDefinitions)
                                    {
                                        foreach (Db.ObjectId objID_In_Block in acBlock.AttributeCollection)
                                        {
                                            Db.DBObject dbObj_In_Block = acTrans.GetObject(objID_In_Block, Db.OpenMode.ForRead) as Db.DBObject;
                                            if (dbObj_In_Block is Db.AttributeReference)
                                            {
                                                Db.AttributeReference acAtt = dbObj_In_Block as Db.AttributeReference;
                                                if (acAtt.Tag == AttName)
                                                {
                                                    ObjID_Dic.Add(acBlock.ObjectId, acAtt.TextString);
 
                                                    if (AttList.Contains(acAtt.TextString) == false)
                                                        AttList.Add(acAtt.TextString);
                                                }
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
                //Я в этой транзакции ничего не меняю, Все открываю только для чтения.
                //соответственно и вносить изменения не нужно.
                //acTrans.Commit();
            }
 
           //Выводим форму для выбора значения
            QuickSelect.Form1 myform_value = new QuickSelect.Form1();
            Autodesk.AutoCAD.ApplicationServices.Application.ShowModalDialog(myform_value);
 
            if (AttValue == Exit)
                return;
            // Добавляем в набор выбираемых объекты удовлетворяющие условию
            IEnumerable<Db.ObjectId> L = from KeyValuePair<Db.ObjectId, string> q in ObjID_Dic
                                         where q.Value.ToString() == AttValue.ToString()
                                         select q.Key;
            //Подсвечиваем объекты
            Db.ObjectId[] idarrayEmpty = L.ToArray();
            acEd.SetImpliedSelection(idarrayEmpty);
        }
    }
}
Вот это идеальная программка для меня, только по итогу выборка не происходит((( Почему-ответьте мне пожалуйста!!Очень-очень буду благодарна любой помощи!!!!Спасибо заранее!!!

Последний раз редактировалось aaalenaaa, 21.02.2016 в 16:41.
aaalenaaa вне форума  
 
Непрочитано 22.02.2016, 05:46
#2890
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Здравствуйте все!!! Опять я со своей выборкой. http://dwg.ru/dnl/9204 - Вот ссылка на лисп с этого сайта, который идеально мне подходит, но по окончанию операции выборки не происходит. В командной строке написано "выбранных объектов 0". Помогите пожалуйста!!!! Он в формате быстрозагружаемого файла, поэтому не могу открыть его для редактирования.И вот файл, в котором выборку произвожу.)Подскажите, что не так!!! Пожалуйста!!!
Вложения
Тип файла: dwg
DWG 2010
Земли.dwg (8.16 Мб, 16 просмотров)
aaalenaaa вне форума  
 
Непрочитано 22.02.2016, 10:08
#2891
gomer

строю, ломаю
 
Регистрация: 03.04.2008
Украина
Сообщений: 5,515


Цитата:
Сообщение от aaalenaaa Посмотреть сообщение
Помогите пожалуйста!!!!
обратитесь к автору сего лиспа, возможно он учтет ваши пожелания
gomer вне форума  
 
Непрочитано 22.02.2016, 11:29
#2892
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Написала автору, пока не ответил. Но мне по сути менять ничего не нужно, только чтоб работал как в описании. Он и работает, запрашивает все как нужно, а по итогу-выборки нет, и ошибки никакой не пишет-вот в чем вопрос!! Посмотрите пожалуйста, если есть возможность на прикрепленном файле - проверьте пожалуйста как работает!!!1
aaalenaaa вне форума  
 
Непрочитано 22.02.2016, 12:45
#2893
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 40,411


Цитата:
Сообщение от aaalenaaa Посмотреть сообщение
Код:
[Выделить все]
;;; (ax:FindBlockTagValue (vla-get-activedocument
;;; (vlax-get-acad-object)) "blockname" "tagname" "tagvalue")
(defun ax:FindBlockTagValue
       (doc bn tagname value / layout i atts tag sset c)
  (vlax-for layout (vla-get-layouts doc)
    (vlax-for i (vla-get-block layout)
      (if (and
            (= (vla-get-objectname i) "AcDbBlockReference")
            (= (strcase (vla-get-name i)) (strcase bn))
          )
        (if (and
              (= (vla-get-hasattributes i) :vlax-true)
              (safearray-value
                (setq atts
                       (vlax-variant-value
                         (vla-getattributes i)
                       )
                )
              )
            )
          (progn
            (foreach tag (vlax-safearray->list atts)
              (if (and
                    (= (strcase tagname)
                       (strcase (vla-get-TagString tag))
                    )
                    (= value (vla-get-TextString tag))
                  )
                (progn
                  (if (not sset)
                    (setq sset (ssadd (vlax-vla-object->ename i)))
                    (ssadd (vlax-vla-object->ename i) sset)
                  )
                )
              )
            )
          )
        )
      )
    )
  )
  (sssetfirst nil sset)
)
----- добавлено через ~29 мин. -----
Код:
[Выделить все]
// Основной модуль
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
 
using App = Autodesk.AutoCAD.ApplicationServices;
using cad = Autodesk.AutoCAD.ApplicationServices.Application;
using Db = Autodesk.AutoCAD.DatabaseServices;
using Ed = Autodesk.AutoCAD.EditorInput;
using Gem = Autodesk.AutoCAD.Geometry;
using Rtm = Autodesk.AutoCAD.Runtime;
using Gi = Autodesk.AutoCAD.GraphicsInterface;
 
namespace QuickSelect
{
    public class Commands
    {
        public static List<string> AttList = new List<string>();
        public static string AttValue = "";
        private static string Exit = "Exit";
 
        static public void ClearAttListValue()
        {
            AttValue = "";
            AttList.Clear();
            AttList.Add(Exit);
        }
 
 
        [Rtm.CommandMethod("bx_quickselect", Rtm.CommandFlags.UsePickSet  |
                                             Rtm.CommandFlags.Redraw |
                                             Rtm.CommandFlags.Modal)]
        static public void bx_quickselect()
        {
 
            // Получение текущего документа и базы данных
            App.Document acDoc = App.Application.DocumentManager.MdiActiveDocument;
            Db.Database acCurDb = acDoc.Database;
            Ed.Editor acEd = acDoc.Editor;
            ClearAttListValue();
 
            //Секция предварительного выбора
            Ed.PromptSelectionResult acSSPrompt = acEd.SelectImplied();
            Ed.SelectionSet acSSet = null;
 
            // Если статус запроса OK, объекты были выбраны перед запуском команды
            if (acSSPrompt.Status == Ed.PromptStatus.OK)
                            acSSet = acSSPrompt.Value;
 
            Dictionary<Db.ObjectId, string> ObjID_Dic = new Dictionary<Db.ObjectId, string>();
 
            Ed.PromptEntityOptions EntOpt = new Ed.PromptEntityOptions("\n Select block:");
            EntOpt.SetRejectMessage("\n Entity must be a block.");
            EntOpt.AddAllowedClass(typeof(Db.BlockReference), false);
            EntOpt.AllowObjectOnLockedLayer = true;
            Ed.PromptEntityResult EntRes = acEd.GetEntity(EntOpt);
 
            if (EntRes.Status != Ed.PromptStatus.OK)
            {
                acEd.WriteMessage("\n Cencel.");
                return;
            }
 
            String acBlockName = "0";
 
            // старт транзакции
            // Ищу истенное имя выбранного блока и читаю его атрибуты
            using (Db.Transaction acTrans = acCurDb.TransactionManager.StartOpenCloseTransaction())
            {
                // Открытие таблицы Блоков для чтения
                Db.BlockTable acBlkTbl = acTrans.GetObject(acCurDb.BlockTableId, 
                                                Db.OpenMode.ForRead) as Db.BlockTable;
                // Открытие записи таблицы Блоков пространства Модели для записи
                Db.BlockTableRecord acBlkTblRecMS = acTrans.GetObject(acBlkTbl[Db.BlockTableRecord.ModelSpace],
                                                Db.OpenMode.ForRead) as Db.BlockTableRecord;
 
 
                //Получаю выбранный блок
                Db.BlockReference acBlock = acTrans.GetObject(EntRes.ObjectId, Db.OpenMode.ForRead) as Db.BlockReference;
                //Получаю определение блока в таблице блоков
                Db.BlockTableRecord acBlkTblRec = acTrans.GetObject(acBlock.BlockTableRecord, Db.OpenMode.ForRead) 
                    as Db.BlockTableRecord;
 
 
                // Получаю определение блока в таблице динамических блоков
                // Запоминаю истинное имя блока
                acBlockName = acBlock.Name;
 
                if (acBlock.IsDynamicBlock)
                {
                    acBlkTblRec = acTrans.GetObject(acBlock.DynamicBlockTableRecord, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                    Db.BlockTableRecord blr_nam = acTrans.GetObject(acBlkTblRec.ObjectId, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                    acBlockName = blr_nam.Name;
                }
 
                if (acBlkTblRec.HasAttributeDefinitions)
                {
                    foreach (Db.ObjectId objID in acBlkTblRec)
                    {
                        Db.DBObject dbObj = acTrans.GetObject(objID, Db.OpenMode.ForRead) as Db.DBObject;
                        if (dbObj is Db.AttributeDefinition)
                        {
                            Db.AttributeDefinition acAtt = dbObj as Db.AttributeDefinition;
                            if (AttList.Contains(acAtt.Tag) != true)
                                AttList.Add(acAtt.Tag);
                        }
                    }
                }
                //Я в этой транзакции ничего не меняю, Все открываю только для чтения.
                //соответственно и вносить изменения не нужно.
                //acTrans.Commit();
            }
 
 
            if (AttList.Count == 1)
                return;
 
            QuickSelect.Form1 myform_name = new QuickSelect.Form1();
            Autodesk.AutoCAD.ApplicationServices.Application.ShowModalDialog(myform_name);
 
            if (AttValue == Exit)
                return;
 
            string AttName = AttValue;
            // Вот тут нужно очистить переменные
            ClearAttListValue();
            //// тут получить все возможние значения данного атрибута и 
            //// заполним массив AttList снова вызвать форму
            using (Db.Transaction acTrans = acCurDb.TransactionManager.StartOpenCloseTransaction())
            {
                if (acSSet == null)
                {
                    Db.TypedValue[] acTypValAr = new Db.TypedValue[1];
                    Db.TypedValue typedValue = new Db.TypedValue(0, "INSERT");
                    acTypValAr.SetValue(typedValue, 0);
                    Ed.SelectionFilter acSelFtr = new Ed.SelectionFilter(acTypValAr);
                    acSSPrompt = acEd.SelectAll(acSelFtr);
                    acSSet = acSSPrompt.Value;
                }
 
                foreach (Db.ObjectId objID in acSSet.GetObjectIds())
                {
                    // Проверка, нужно убедится в правильности полученного объекта
                    if (objID != null)
                    {
                        // Открытие объекта для
                        Db.Entity dbObj = acTrans.GetObject(objID, Db.OpenMode.ForRead) as Db.Entity;
                        if (dbObj != null)
                        {
                            if (dbObj is Db.BlockReference)
                            {
                                Db.BlockReference acBlock = dbObj as Db.BlockReference;
                                Db.BlockTableRecord acBlkTblRec;
                                acBlkTblRec = acTrans.GetObject(acBlock.BlockTableRecord, Db.OpenMode.ForRead) as Db.BlockTableRecord;
 
                                String BlockName = acBlock.Name;
                                if (acBlock.IsDynamicBlock)
                                {
                                    acBlkTblRec = acTrans.GetObject(acBlock.DynamicBlockTableRecord, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                                    Db.BlockTableRecord blr_nam = acTrans.GetObject(acBlkTblRec.ObjectId, Db.OpenMode.ForRead) as Db.BlockTableRecord;
                                    BlockName = blr_nam.Name;
                                }
 
                                if (BlockName == acBlockName)
                                {
                                    if (acBlkTblRec.HasAttributeDefinitions)
                                    {
                                        foreach (Db.ObjectId objID_In_Block in acBlock.AttributeCollection)
                                        {
                                            Db.DBObject dbObj_In_Block = acTrans.GetObject(objID_In_Block, Db.OpenMode.ForRead) as Db.DBObject;
                                            if (dbObj_In_Block is Db.AttributeReference)
                                            {
                                                Db.AttributeReference acAtt = dbObj_In_Block as Db.AttributeReference;
                                                if (acAtt.Tag == AttName)
                                                {
                                                    ObjID_Dic.Add(acBlock.ObjectId, acAtt.TextString);
 
                                                    if (AttList.Contains(acAtt.TextString) == false)
                                                        AttList.Add(acAtt.TextString);
                                                }
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
                //Я в этой транзакции ничего не меняю, Все открываю только для чтения.
                //соответственно и вносить изменения не нужно.
                //acTrans.Commit();
            }
 
           //Выводим форму для выбора значения
            QuickSelect.Form1 myform_value = new QuickSelect.Form1();
            Autodesk.AutoCAD.ApplicationServices.Application.ShowModalDialog(myform_value);
 
            if (AttValue == Exit)
                return;
            // Добавляем в набор выбираемых объекты удовлетворяющие условию
            IEnumerable<Db.ObjectId> L = from KeyValuePair<Db.ObjectId, string> q in ObjID_Dic
                                         where q.Value.ToString() == AttValue.ToString()
                                         select q.Key;
            //Подсвечиваем объекты
            Db.ObjectId[] idarrayEmpty = L.ToArray();
            acEd.SetImpliedSelection(idarrayEmpty);
        }
    }
}
Вот это идеальная программка для меня, только по итогу выборка не происходит((( Почему-ответьте мне пожалуйста!!Очень-очень буду благодарна любой помощи!!!!Спасибо заранее!!!

Во-первых, что здесь делает C#-код? Во-вторых, научить можно только если есть конкретные вопросы. А у тебя же вопрос (точнее, запрос) только один - сделайте мне программу. Проанализируй ее, пошагово пройди, проверяй значения переменных, интересуйся описаниями и параметрами вызываемых функций - тогда и станет более-менее понятно: какие вопросы задавать и по каким конкретно строкам.
__________________
Моя библиотека lisp-функций
---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 22.02.2016, 13:45
#2894
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Спасибо за ответ в любом случае!!!
Что ж вы так строго. Я разбираюсь потихоньку по более простым программам, сравниваю похожие, нахожу где что заменили, что на что влияет.
А в конкретном примере программа на сайте есть, менять ее не надо, просто итог ее я не вижу- вот в чем вопрос-запрос -просьба. Мне не нужно, чтоб кто-то ее менял, просто скажите, у вас она работает и в моем примере она может работать? Все запросы она делает верно, и выборку замечательно проводит- а итог Нет выбранных объектов. пока только в этом вопрос! Если эт сложно проверить - так и скажите. Буду дальше искать решение. Спасибо!!!
aaalenaaa вне форума  
 
Непрочитано 22.02.2016, 14:05
#2895
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 40,411


Проверь функцию sssetfirst и ее параметры.
__________________
Моя библиотека lisp-функций
---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 22.02.2016, 14:11
#2896
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Спасибо, посмотрю сейчас!

----- добавлено через ~20 ч. -----
Здравствуйте уважаемые!!! Я все с выборкой - программа по выборке работает хорошо на других файлах, кроме необходимого мне. Я так понимаю проблема в том, что у меня атрибут имеет в названии два слова и между ними пробел, а первое слово входит в состав всех остальных атрибутов. При указании слова для фильтра нужно похоже заменить чем то пробел - подскажите пожалуйста, чем можно заменить пробел??? И правильно ли я определила проблему??
Не судите строго, я только разбираюсь во всем этом)))
aaalenaaa вне форума  
 
Непрочитано 27.02.2016, 16:56
#2897
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Здравствуйте уважаемые!!! Помогите пожалуйста!!! Программа по ссылке http://dwg.ru/dnl/9204 работает прекрасно со всеми моими чертежами, кроме того, который нужен. Нужный мне файл я выгружаю из геокада,через мапинфо. Атрибуты им заданы автоматом. Из них нужно производить выборку по Категории земель, их виды (значения атрибутов) следующие: Земли лесного фонда; Земли сельскохозяйственного назначения и т.п. Так вот, при запуске программы по выборке, она запрашивает блок, спрашивает по какому атрибуту производить выбор и какое значение атрибута искать. Все указываю, нажимаю применить, итог - выбран 1 объект, который я указывала как исходный(((. Ну что не так? Программа в файле, типа *.fas, открыть его я не могу, чтобы посмотреть код. В справке к программе по ссылке есть символы, для обозначения различных знаков, что можно было пыталась вставить вместо пробела в значении атрибута, типа Земли?лесного?фонда, нет итога и все. ((( Или уже скажите мне,чтоб я отстала от этого файла*.fas!!!
Вложения
Тип файла: dwg
DWG 2010
Земли.dwg (8.16 Мб, 9 просмотров)
aaalenaaa вне форума  
 
Непрочитано 27.02.2016, 17:49
#2898
gomer

строю, ломаю
 
Регистрация: 03.04.2008
Украина
Сообщений: 5,515


Цитата:
Сообщение от aaalenaaa Посмотреть сообщение
Или уже скажите мне,чтоб я отстала от этого файла*.fas!!!
еще раз, пишите автору, только у него есть исходник, при запуске команды в командной строке можно увидеть мейл, куда надо стучаться
gomer вне форума  
 
Непрочитано 27.02.2016, 19:44
#2899
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,996


Цитата:
Сообщение от aaalenaaa Посмотреть сообщение
Или уже скажите мне,чтоб я отстала от этого файла*.fas!!!
попробуй поискать в этой теме Выбор блоков по значению атрибутов.
__________________
Как использовать код на Лиспе читаем здесь
VVA вне форума  
 
Непрочитано 28.02.2016, 13:33
#2900
aaalenaaa


 
Регистрация: 06.01.2016
Сообщений: 12


Огромное вем спасибо за ответы-советы.
Подскажите еще,если можете, как запустить вот этот лисп.
Код:
[Выделить все]
;;; (ax:FindBlockTagValue (vla-get-activedocument
;;; (vlax-get-acad-object)) "blockname" "tagname" "tagvalue")
(defun ax:FindBlockTagValue
       (doc bn tagname value / layout i atts tag sset c)
  (vlax-for layout (vla-get-layouts doc)
    (vlax-for i (vla-get-block layout)
      (if (and
            (= (vla-get-objectname i) "AcDbBlockReference")
            (= (strcase (vla-get-name i)) (strcase bn))
          )
        (if (and
              (= (vla-get-hasattributes i) :vlax-true)
              (safearray-value
                (setq atts
                       (vlax-variant-value
                         (vla-getattributes i)
                       )
                )
              )
            )
          (progn
            (foreach tag (vlax-safearray->list atts)
              (if (and
                    (= (strcase tagname)
                       (strcase (vla-get-TagString tag))
                    )
                    (= value (vla-get-TextString tag))
                  )
                (progn
                  (if (not sset)
                    (setq sset (ssadd (vlax-vla-object->ename i)))
                    (ssadd (vlax-vla-object->ename i) sset)
                  )
                )
              )
            )
          )
        )
      )
    )
  )
  (sssetfirst nil sset)
)
----- добавлено через ~2 мин. -----
Огромное всем спасибо за ответы-советы!
Подскажите еще,если можете, как запустить вот этот лисп:
Код:
[Выделить все]
;;; (ax:FindBlockTagValue (vla-get-activedocument
;;; (vlax-get-acad-object)) "blockname" "tagname" "tagvalue")
(defun ax:FindBlockTagValue
       (doc bn tagname value / layout i atts tag sset c)
  (vlax-for layout (vla-get-layouts doc)
    (vlax-for i (vla-get-block layout)
      (if (and
            (= (vla-get-objectname i) "AcDbBlockReference")
            (= (strcase (vla-get-name i)) (strcase bn))
          )
        (if (and
              (= (vla-get-hasattributes i) :vlax-true)
              (safearray-value
                (setq atts
                       (vlax-variant-value
                         (vla-getattributes i)
                       )
                )
              )
            )
          (progn
            (foreach tag (vlax-safearray->list atts)
              (if (and
                    (= (strcase tagname)
                       (strcase (vla-get-TagString tag))
                    )
                    (= value (vla-get-TextString tag))
                  )
                (progn
                  (if (not sset)
                    (setq sset (ssadd (vlax-vla-object->ename i)))
                    (ssadd (vlax-vla-object->ename i) sset)
                  )
                )
              )
            )
          )
        )
      )
    )
  )
  (sssetfirst nil sset)
)
Заранее большое спасибо!!!
aaalenaaa вне форума  
Ответ
Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > LISP > Научите лиспу на примере (или как kpblc, VVA и компания пытаются обучить чайника лиспу)



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
LISP. Вставка в таблицу поля, соотвествующего площади примитива Profan Готовые программы 272 06.06.2021 23:12
Сейсмозащита и сейсмоизоляция существующих, построенных зд. IANationalInformAgentstvo Прочее. Архитектура и строительство 216 20.01.2015 16:51
Мониторы LCD CRT Разное 94 17.06.2008 10:51
ЮМОР 2006 =) Perezz!! Разное 1122 04.01.2007 00:46