Форум пользователей Visio

Форум по вопросам применения и программирования в Visio
Текущее время: 26 сен 2023, 03:54

Часовой пояс: UTC + 3 часа [ Летнее время ]


Правила форума


При размещении файлов предпочтительным является формат vsd (а не vsdx/vsdm)
Размещая ваши вложения на форуме не используйте имена файлов содержащих кириллицу, в противном случае файл будет иметь имя .<расширение файла> !

Для форматирования ваших сообщений используйте BBCodes, описание используемых на форуме BBCodes.



Начать новую тему Ответить на тему  [ Сообщений: 9 ] 
Автор Сообщение
 Заголовок сообщения: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 10:45 
Не в сети
Новичок

Зарегистрирован: 29 янв 2010, 09:15
Сообщений: 44
Очков репутации: 20

Добавить очки репутацииУменьшить очки репутации
Прошу помощи по такому вопросу: у меня многостраничный документ (111 страниц) и мне необходимо, чтобы в конце работы все страницы шли по порядку (Page-1, Page-2, ... Page-111). При этом в процессе работы новые страницы могут вставляться не только в конец документа, но и в середину, т.е. порядок следования страниц нарушается. Сами имена страниц назначаются Визио по умолчанию и не меняются, т.е. по шаблону "Page-" & номер_очередной_страницы.
В какой-то момент у меня получилось так, что стандартная команда Визио Re-order Pages стала выдавать ошибку (в моём случае "Page-103 already in use..."), похоже, что сам внутренний алгоритм некорректен в моей версии. Я написал макрос для переименования страниц, но неожиданно оказалось, что сам процесс переименования очень медлительный и при моём количестве страниц занимает много времени. В общем, надо как-то оптимизировать код, а мне хороший алгоритм в голову что-то не приходит. Вот макрос:
Код:
Public Sub Reorder_Page_Names()
    Dim vsoPage As Visio.Page
    Dim vsoTestPage As Visio.Page
    Dim sPageName As String
    Dim Cnt As Long
    Dim I As Long
    Dim PageIndex As Long
   
    'On Error Resume Next
    Debug.Print "Start"
    For I = 1 To ActiveDocument.Pages.Count
        Set vsoPage = ActiveDocument.Pages(I)
        If Not vsoPage.Background Then
            '
            Debug.Print vsoPage.Name
            '
            PageIndex = vsoPage.Index
            sPageName = "Page-" & Format(PageIndex, "#")
            If StrComp(sPageName, vsoPage.Name, vbTextCompare) <> 0 Then
                Set vsoTestPage = Nothing
                On Error Resume Next
                Set vsoTestPage = ActiveDocument.Pages(sPageName)
                On Error GoTo 0
                If vsoTestPage Is Nothing Then ' can rename
                    vsoPage.Name = sPageName
                Else ' can not rename
                    'Debug.Print "Can't rename " & vsoPage.Name & " -> " & sPageName
                    vsoTestPage.Name = "Page__" & Format(PageIndex, "#")
                    vsoPage.Name = sPageName
                End If
            End If
        End If
        DoEvents
    Next
    Debug.Print "Finish"
End Sub


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 11:17 
Не в сети
Content manager
Content manager
Аватара пользователя

Зарегистрирован: 02 окт 2009, 01:01
Сообщений: 5006
Откуда: оттуда
Использую Visio c: 1998
Отрасль: Интеграция системных интеграторов
Должность: Дизайнер по оформлению документации
Уровнь квалификации: Форматирование документов MS Word
zhuravsky писал(а):
стандартная команда Визио Re-order Pages стала выдавать ошибку (в моём случае "Page-103 already in use..."), похоже, что сам внутренний алгоритм некорректен в моей версии
Подозреваю тут проблема локальных и универсальных имен!
zhuravsky писал(а):
что сам процесс переименования очень медлительный и при моём количестве страниц занимает много времени
Странно это!
zhuravsky в сообщении #18682 писал(а):
Я пока пробовал цикл по всем страницам с анализом имени шейпа и цикл по страницам с CreateSelection by master. Вроде, по времени разницы особо не видно...
У меня в этих случаях разницу видно, а с переименованием страниц была раз задача переименования 140 страниц. минуты за 3 управился. там был очень тяжелый файл, много больших скринов или чёрточек импортированных из AutoCAD
zhuravsky писал(а):
надо как-то оптимизировать код, а мне хороший алгоритм в голову что-то не приходит.
Я сегодня далеко от компа с Visio. Но моя пара советов
1. Добавить код по событию добавления страницы, чтоб переименование происходило сразу
Код:
Private Sub Document_PageAdded(ByVal Page As IVPage)

2. Проводить перебор страниц не с начала, а с конца
For I = 1 To ActiveDocument.Pages.Count
до вновь добавленной
Код:
Private Sub Document_PageAdded(ByVal Page As IVPage)
Dim RSP As Integer ' rename start position
RSP = Page.Index

For i = ActiveDocument.Pages.Count To RSP Step -1 ' страницы до вставленной не трогаем !

Next

_________________
База знаний ShapeSheet
Мой Youtube-канал @surrogate-tm
Мои трафареты


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 11:37 
Не в сети
Content manager
Content manager
Аватара пользователя

Зарегистрирован: 02 окт 2009, 01:01
Сообщений: 5006
Откуда: оттуда
Использую Visio c: 1998
Отрасль: Интеграция системных интеграторов
Должность: Дизайнер по оформлению документации
Уровнь квалификации: Форматирование документов MS Word
Surrogate писал(а):
Подозреваю тут проблема локальных и универсальных имен!
Не так! Новой странице по умолчанию добавляется максимальный индекс, начинаете пересортицу и в какой-то момент встречается уже задействованное имя. Тут не помогает перебор страниц в обратном порядке, т.е. крайняя справа страница должна иметь максимальный номер. А у вас последняя добавленная имеет такой же. Новую страницу переименовывать сначала в tmp, а после перебора страниц она получит свое порядковое имя :mrgreen:
Код:
Private Sub Document_PageAdded(ByVal Page As IVPage)
Dim RSP As Integer ' rename start position
RSP = Page.Index
Page.Name = "temp"
For i = ActiveDocument.Pages.Count To RSP Step -1
Set pg = ActiveDocument.Pages(i)
pg.Name = "Page-" & i
Next
End Sub

_________________
База знаний ShapeSheet
Мой Youtube-канал @surrogate-tm
Мои трафареты


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 11:39 
Не в сети
Administrator

Зарегистрирован: 30 авг 2009, 11:02
Сообщений: 2205
Очков репутации: 100623

Добавить очки репутацииУменьшить очки репутации
Цитата:
что сам процесс переименования очень медлительный и при моём количестве страниц занимает много времени
Странно это!

А почему странно-то? Ведь в формулах шейп-листа могут быть ссылки на другой лист. Значит Visio обязан проверить все формулы на предмет - не встречается ли в них старое имя страницы и, если встречается, заменить его на новое. Если шейпов много, то это длинная проверка.
Похоже, время должно зависеть не только от количества страниц, но и от количества шейпов на них.


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 12:53 
Не в сети
Administrator

Зарегистрирован: 30 авг 2009, 11:02
Сообщений: 2205
Очков репутации: 100623

Добавить очки репутацииУменьшить очки репутации
Цитата:
Новую страницу переименовывать сначала в tmp

Немного про имена.
Межстраничные ссылки используют универсальное имя страницы. А внизу листа пользователь наблюдает локальное имя. И переименовывает только локальноее имя. Во всех последующих случаях кроме первого. А вот первое переименование действует сразу и на локальное, и на универсальное. Вот такая каша...
Получается, если один раз зафиксировать универсальное имя, то потом с локальным можно делать что угодно: добавлять буковки, убирать их и т.д. То есть Page-1 можно заменить на Page-1tmp, а вторым проходом Page-1tmp заменить на Page-5. Так можно обходить ошибки типа "страница уже существует". Хотя, на скорость это не повлияет :(


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 16:59 
Не в сети
Новичок

Зарегистрирован: 29 янв 2010, 09:15
Сообщений: 44
Очков репутации: 20

Добавить очки репутацииУменьшить очки репутации
Пришёл в итоге вот к такому алгоритму:
Код:
Public Sub Reorder_Page_Names()
    Dim vsoPage As Visio.Page
    Dim vsoTestPage As Visio.Page
    Dim sPageName As String
    Dim I As Long
    Dim J As Long
    Dim Count As Long
    Dim timeStart As Single
    Dim timeDuration As Long
    Dim lngUndoScopeID As Long
   
    On Error Resume Next
    lngUndoScopeID = Application.BeginUndoScope("Pages rename")
    Debug.Print "Start"
    timeStart = Timer
    I = 1
    Count = ActiveDocument.Pages.Count
    sPageName = "Page-" & Format(I, "#")
    Set vsoPage = ActiveDocument.Pages(I)
    While StrComp(ActiveDocument.Pages(I).Name, "Page-" & Format(I, "#"), vbTextCompare) = 0
        I = I + 1
    Wend
    '
    While ActiveDocument.Pages(Count).Background
        Count = Count - 1
    Wend
    '
    While StrComp(ActiveDocument.Pages(Count).Name, "Page-" & Format(Count, "#"), vbTextCompare) = 0
        Count = Count - 1
    Wend
    For J = Count To I Step -1
        sPageName = "Page-" & Format(J, "#")
        Debug.Print ActiveDocument.Pages(J); "  --->  "; "Page-" & Format(J, "#"), "try if "; sPageName; " exists... ";
        Set vsoTestPage = Nothing
        Set vsoTestPage = ActiveDocument.Pages(sPageName)
        If Not (vsoTestPage Is Nothing) Then
            vsoTestPage.Name = "_Temp_" & J
            'vsoTestPage.NameU = "_Temp_" & J
            Debug.Print "Exists, renaming to "; "_Temp_" & J
        Else
            Debug.Print "does not exist."
        End If
        ActiveDocument.Pages(J).Name = sPageName
        'ActiveDocument.Pages(J).NameU = sPageName
        '
        DoEvents
    Next J
    '
    Application.EndUndoScope lngUndoScopeID, True
    timeDuration = Round(Timer - timeStart, 0)
    Debug.Print timeDuration; " seconds elapsed."
    Debug.Print "Finish"
End Sub


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 18:00 
Не в сети
Ветеран

Зарегистрирован: 26 авг 2019, 21:07
Сообщений: 243
Использую Visio c: 2019
Очков репутации: 10

Добавить очки репутацииУменьшить очки репутации
Tumanov писал(а):
Получается, если один раз зафиксировать универсальное имя, то потом с локальным можно делать что угодно: добавлять буковки, убирать их и т.д.
Делал также
Изображение
Первое переименование Name фиксирует NameU, и пользователь уже не может навредить.

_________________
САПР-АСУ
https://github.com/gtfox/
YouTube


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 20:07 
Не в сети
Ветеран
Аватара пользователя

Зарегистрирован: 28 апр 2013, 14:03
Сообщений: 943
Откуда: Вена, Австрия
Использую Visio c: 1998
Очков репутации: 100613

Добавить очки репутацииУменьшить очки репутации
Что-то я не понял в чем смысл двойного переименования? NameU фиксируется, как только появляется хоть какое-то имя:
Код:
Set p = ActiveDocument.Pages.Add

Debug.Print p.Name, p.NameU         -> Page2, Page-2  (нет имени)

p.Name = "A"
Debug.Print p.Name, p.NameU         -> A, A (имя появилось, инициализировались Name и NameU)

p.Name = "B"
Debug.Print p.Name, p.NameU         -> B A  (поменялось только Name)

p.Name = "C"
Debug.Print p.Name, p.NameU         -> C, A (снова поменялось только Name)

Set p = ActiveDocument.Pages.Add

Debug.Print p.Name, p.NameU           -> Page-3, Page-3 (новая страница)

p.Name = "A"
Debug.Print p.Name, p.NameU           -> ОШИБКА, "А" уже существует, хотя его не видно в интерфейсе (для второй страницы показывается "C")

Для того чтобы исправить исходный код, скорее всего достаточно было просто изменять оба имени (Name и NameU).
К сожалению для этого надо было знать о том что существует такая "подлянка" как NameU.

vsoPage.Name = sPageName
vsoPage.NameU = sPageName

Но это раньше. Теперь документ там наверняка превратился в кашу.
Так что сначала Name и NameU надо синхронизовать, т.е. чтобы они совпадали.

_________________
Полезные инструменты для создания диаграмм Visio:
https://unmanagedvisio.com/


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
 Заголовок сообщения: Re: Алгоритм переименования страниц
СообщениеДобавлено: 24 авг 2023, 20:45 
Не в сети
Administrator

Зарегистрирован: 30 авг 2009, 11:02
Сообщений: 2205
Очков репутации: 100623

Добавить очки репутацииУменьшить очки репутации
Цитата:
Что-то я не понял в чем смысл двойного переименования?

Да это просто прием, чтобы избежать ошибки "имя уже существует". Типа, сначала перейти на другую систему нумерации, потом вернуться обратно, но уже с новыми именами. Конечно, это не единственный вариант.


Пожаловаться на это сообщение
Вернуться к началу
 Профиль  
Ответить с цитатой  
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 9 ] 

Часовой пояс: UTC + 3 часа [ Летнее время ]



Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 2


Вы можете начинать темы
Вы можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  
cron
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
Вы можете создать форум бесплатно PHPBB3 на Getbb.Ru, Также возможно сделать готовый форум PHPBB2 на Mybb2.ru
Русская поддержка phpBB