Re: Обновить вхождение блока

Hwd пишет:

См. строку 113 кода - получаю идентификаторы всех анонимных блоков

Метода GetAnonymousBlockIds() в 2008 тоже нет  :D
Но это не проблема, их я получаю.

Re: Обновить вхождение блока

Hwd пишет:

всё, я понял тебя. Да, это наверное был бы самый оптимальный вариант.

Спасибо, за понимание. Хотя тебя это не должно волновать, т.к. в 2009 есть эта функция UpdateAnonymousBlocks. :D
Блин, давно хочу, научиться пользоваться утилиткой ArxDbg. В таких исследованиях, как работа команды _AttSync, она наверно незаменима. Все покажет, что создается, что меняется, назначается. Повод еще раз взятсься за освоение этой тулзы.

(изменено: Вильдар, 20 октября 2011г. 19:08:02)

Re: Обновить вхождение блока

Попытка реализации UpdateAnonymousBlocks
...новая версия, работает  :D

      public static void UpdateAnonymousBlocksRefs(ObjectId idBtrDyn, Transaction tr)
      {
         var btrDyn = (BlockTableRecord)tr.GetObject(idBtrDyn, OpenMode.ForRead); 
         if (!btrDyn.IsDynamicBlock) return;
         
         List<BlockReference> brCol = GetDynBlockRefList(btrDyn, tr);
         foreach (var br in brCol) {
            ObjectId idBr = br.ObjectId;
            var btr = (BlockTableRecord)tr.GetObject(br.BlockTableRecord, OpenMode.ForRead);
            if (!btr.IsAnonymous) continue;            
            
            //сохраняем дин.параметры
            List<DynProp> dynParams = GetDynParam(br);
            //сброс блока
            br.Close();
            using (Transaction tr2 = tr.TransactionManager.StartTransaction()) {
               var br2 = (BlockReference)tr2.GetObject(idBr, OpenMode.ForWrite); 
               br2.BlockTableRecord = br2.DynamicBlockTableRecord;
               //br2.ResetBlock();//эффект вроде тот же самый, что и от предыдущей строки
               tr2.Commit();
            }
            var br3 =(BlockReference) tr.GetObject(idBr, OpenMode.ForWrite); 
            //устанавливаем дин.параметры
            SetDynParam(br3, dynParams);            
         }
      }

Вхождению анонимного блока назначается ссылка на дин.блок (сброс блока), а потом устанавливаются дин.параметры. Все, имеем обновленный блок.
Пробовал ResetBlock, эффект тот же самый. А что это функция еще делает, кроме установки вхождению ссылки на дин.блок?
Но, сброс блока срабатывает только после tr.Commit(), поэтому приходиться открывать вторую транзакцию.

update Черт, не работает! При повторном выполнении функции для одних и тех же блоков, в одной сессии, они сбрасываются в начальное положение. Что-то я упустил.

update2 Сдаюсь. Перехожу к запасному плану - замене блоков. С этим проблем нет.

Re: Обновить вхождение блока

Синхронизации атрибутов. Форматирование многострочных атрибутов
При обновление вхождений блока, делаем синхронизацию атрибутов.
Цель: Сделать атрибут соответствующим определению атрибута, но с сохранением нужных свойств.
Вопрос: Управление форматированием многострочного атрибута?

Мои предположения. Нужно парсить строку Mtext.Contents. Т.к. соответствующих свойств, по-моему, нет.
Строка вида:

\W0.6000;\pxl0.33333,r0.33333,b0.66667,a0.66667,sm0.8,qc;{\fArial|b1|i1|c204|p34;\Q-14;\W0.6;\T1.3;\L\OТекст атрибута}

Возможно, не все свойства учел.

Пока, есть решение, только для сохранения текста:

      //установка текста с сохранением форматирования
      MText mt = arDest.MTextAttribute;
      string content = mt.Contents;
      int index = content.IndexOf(arDest.TextString);
      content = content.Remove(index, arDest.TextString.Length);
      content = content.Insert(index, arSource.TextString);
      mt.Contents = content;
      arDest.MTextAttribute = mt;

Здесь, arDest атрибут со свойствами определения атрибута (получен из SetAttributeFromBlock); arSource атрибут до операции обновления блоков.