Объединить два макроса

Автор dziglo, 2 июня 2023, 08:44

0 Пользователи и 1 гость просматривают эту тему.

dziglo

Добрый день.
Подскажите пожалуйста, как объединить два макроса.
Один макрос я взял здесь на форуме, другой — я создал путем записи действий в OpenOffice.

Вот они:

sub Zamena

dim document   as object
dim dispatcher as object
rem ----------------------------------------------------------------------
rem get access to the document
document   = ThisComponent.CurrentController.Frame
dispatcher = createUnoService("com.sun.star.frame.DispatchHelper")

rem ----------------------------------------------------------------------
dim args1(0) as new com.sun.star.beans.PropertyValue
args1(0).Name = "Language"
args1(0).Value = 1059

dispatcher.executeDispatch(document, ".uno:Language", "", 0, args1())

end sub

sub Main
rem ----------------------------------------------------------------------
rem define variables
dim document   as object
dim dispatcher as object
rem ----------------------------------------------------------------------
rem get access to the document
document   = ThisComponent.CurrentController.Frame
dispatcher = createUnoService("com.sun.star.frame.DispatchHelper")

rem ----------------------------------------------------------------------
dim args1(18) as new com.sun.star.beans.PropertyValue
args1(0).Name = "SearchItem.StyleFamily"
args1(0).Value = 2
args1(1).Name = "SearchItem.CellType"
args1(1).Value = 0
args1(2).Name = "SearchItem.RowDirection"
args1(2).Value = true
args1(3).Name = "SearchItem.AllTables"
args1(3).Value = false
args1(4).Name = "SearchItem.Backward"
args1(4).Value = false
args1(5).Name = "SearchItem.Pattern"
args1(5).Value = false
args1(6).Name = "SearchItem.Content"
args1(6).Value = false
args1(7).Name = "SearchItem.AsianOptions"
args1(7).Value = false
args1(8).Name = "SearchItem.AlgorithmType"
args1(8).Value = 1
args1(9).Name = "SearchItem.SearchFlags"
args1(9).Value = 65536
args1(10).Name = "SearchItem.SearchString"
args1(10).Value = "'|'|'"
args1(11).Name = "SearchItem.ReplaceString"
args1(11).Value = "ʼ"
args1(12).Name = "SearchItem.Locale"
args1(12).Value = 255
args1(13).Name = "SearchItem.ChangedChars"
args1(13).Value = 2
args1(14).Name = "SearchItem.DeletedChars"
args1(14).Value = 2
args1(15).Name = "SearchItem.InsertedChars"
args1(15).Value = 2
args1(16).Name = "SearchItem.TransliterateFlags"
args1(16).Value = 1280
args1(17).Name = "SearchItem.Command"
args1(17).Value = 3
args1(18).Name = "Quiet"
args1(18).Value = true

dispatcher.executeDispatch(document, ".uno:ExecuteSearch", "", 0, args1())


end sub

economist

Проще всего добавить в один макрос (в конце) - одну строку с явным вызовом другого макроса (он должен быть в этом же файле или библиотеке макросов):

Call YourMacroName 
Руб. за сто, что Питоньяк
Любит водку и коньяк!
Потому что мне, без оных, -
Не понять его никак...

dziglo

Цитата: economist от  2 июня 2023, 10:44Проще всего добавить в один макрос (в конце) - одну строку с явным вызовом другого макроса (он должен быть в этом же файле или библиотеке макросов):

Call YourMacroName 

Я хочу объединить два макроса, чтобы поместить его потом в oxt-файл. Call может помочь?

gabix

Поскольку у Вас два однородных макроса, в которых всю работу делает диспетчер, попробуйте объединить самым простым образом:

sub Zamena

dim document   as object
dim dispatcher as object

rem ----------------------------------------------------------------------
rem get access to the document
document   = ThisComponent.CurrentController.Frame
dispatcher = createUnoService("com.sun.star.frame.DispatchHelper")

rem ----------------------------------------------------------------------
dim args1(0) as new com.sun.star.beans.PropertyValue
args1(0).Name = "Language"
args1(0).Value = 1059

dispatcher.executeDispatch(document, ".uno:Language", "", 0, args1())

dim args2(18) as new com.sun.star.beans.PropertyValue
args2(0).Name = "SearchItem.StyleFamily"
args2(0).Value = 2
args2(1).Name = "SearchItem.CellType"
args2(1).Value = 0
args2(2).Name = "SearchItem.RowDirection"
args2(2).Value = true
args2(3).Name = "SearchItem.AllTables"
args2(3).Value = false
args2(4).Name = "SearchItem.Backward"
args2(4).Value = false
args2(5).Name = "SearchItem.Pattern"
args2(5).Value = false
args2(6).Name = "SearchItem.Content"
args2(6).Value = false
args2(7).Name = "SearchItem.AsianOptions"
args2(7).Value = false
args2(8).Name = "SearchItem.AlgorithmType"
args2(8).Value = 1
args2(9).Name = "SearchItem.SearchFlags"
args2(9).Value = 65536
args2(10).Name = "SearchItem.SearchString"
args2(10).Value = "'|'|'"
args2(11).Name = "SearchItem.ReplaceString"
args2(11).Value = "ʼ"
args2(12).Name = "SearchItem.Locale"
args2(12).Value = 255
args2(13).Name = "SearchItem.ChangedChars"
args2(13).Value = 2
args2(14).Name = "SearchItem.DeletedChars"
args2(14).Value = 2
args2(15).Name = "SearchItem.InsertedChars"
args2(15).Value = 2
args2(16).Name = "SearchItem.TransliterateFlags"
args2(16).Value = 1280
args2(17).Name = "SearchItem.Command"
args2(17).Value = 3
args2(18).Name = "Quiet"
args2(18).Value = true

dispatcher.executeDispatch(document, ".uno:ExecuteSearch", "", 0, args2())

end sub

dziglo

Цитата: gabix от  3 июня 2023, 21:09попробуйте объединить самым простым образом:

Почему-то первая часть объединенного макроса не сработала — не был назначен белорусский язык.

economist

Цитата: dziglo от  2 июня 2023, 13:20Я хочу объединить два макроса, чтобы поместить его потом в oxt-файл. Call может помочь?

Да, в расширение *.oxt попадет целая библиотека (из "папки" Мои макросы или Макросы LibreOffice), макросы из нее могут вызывать друг друга методом Call. Если нужно вызвать макрос из другой библиотеки/расширения/документа - нужно его указать до имени, через точку: Call LibNameM.MacroN()

Это эффективный паттерн (шаблон) программирования - разбивать большое на части - модули, макросы, UDF-функции/процедуры. "Части" ломаются так же часто, как и "целое", но благодаря тому что они маленькие - решить в них проблему гораздо проще (меньше контекст, условие задачи). А при добавлении нового функционала - часто легче добавить новую "часть", чем переделывать "целое".

Принятие того что код программы может и должен выполняться нелинейно, "кусочками" (прыжками между UDF и процедурами) дается непросто. Но потом становится все на свои места, и программирование начинает приносить удовольствие.
Руб. за сто, что Питоньяк
Любит водку и коньяк!
Потому что мне, без оных, -
Не понять его никак...

gabix

#6
Цитата: dziglo от  4 июня 2023, 23:28Почему-то первая часть объединенного макроса не сработала

У меня работает. Собственно, что Вы хотите добиться этим макросом?

gabix

Цитата: economist от  5 июня 2023, 08:25то эффективный паттерн (шаблон) программирования - разбивать большое на части

В целом да, это разумный подход, но в данном конкретном случае разбивать нечего, кода мало, выполняется линейно, последовательно.

gabix

Да, чтобы показать, когда и как стоит разбивать код, вот такое моё творчество (не хвастаюсь, лишь в попытке помочь dziglo):

Sub ReplaceFoo(SString As String, RString As String)
dim document   as object
dim dispatcher as object
document   = ThisComponent.CurrentController.Frame
dispatcher = createUnoService("com.sun.star.frame.DispatchHelper")
dim args1(18) as new com.sun.star.beans.PropertyValue
args1(0).Name = "SearchItem.StyleFamily"
args1(0).Value = 2
args1(1).Name = "SearchItem.CellType"
args1(1).Value = 0
args1(2).Name = "SearchItem.RowDirection"
args1(2).Value = true
args1(3).Name = "SearchItem.AllTables"
args1(3).Value = false
args1(4).Name = "SearchItem.Backward"
args1(4).Value = false
args1(5).Name = "SearchItem.Pattern"
args1(5).Value = false
args1(6).Name = "SearchItem.Content"
args1(6).Value = false
args1(7).Name = "SearchItem.AsianOptions"
args1(7).Value = false
args1(8).Name = "SearchItem.AlgorithmType"
args1(8).Value = 1
args1(9).Name = "SearchItem.SearchFlags"
args1(9).Value = 65536
args1(10).Name = "SearchItem.SearchString"
args1(10).Value = SString
args1(11).Name = "SearchItem.ReplaceString"
args1(11).Value = RString
args1(12).Name = "SearchItem.Locale"
args1(12).Value = 255
args1(13).Name = "SearchItem.ChangedChars"
args1(13).Value = 2
args1(14).Name = "SearchItem.DeletedChars"
args1(14).Value = 2
args1(15).Name = "SearchItem.InsertedChars"
args1(15).Value = 2
args1(16).Name = "SearchItem.TransliterateFlags"
args1(16).Value = 1280
args1(17).Name = "SearchItem.Command"
args1(17).Value = 3
args1(18).Name = "Quiet"
args1(18).Value = true

dispatcher.executeDispatch(document, ".uno:ExecuteSearch", "", 0, args1())

End Sub


sub ReplaceFooNoReg(SString As String, RString As String)
dim document   as object
dim dispatcher as object
document   = ThisComponent.CurrentController.Frame
dispatcher = createUnoService("com.sun.star.frame.DispatchHelper")
dim args1(18) as new com.sun.star.beans.PropertyValue
args1(0).Name = "SearchItem.StyleFamily"
args1(0).Value = 2
args1(1).Name = "SearchItem.CellType"
args1(1).Value = 0
args1(2).Name = "SearchItem.RowDirection"
args1(2).Value = true
args1(3).Name = "SearchItem.AllTables"
args1(3).Value = false
args1(4).Name = "SearchItem.Backward"
args1(4).Value = false
args1(5).Name = "SearchItem.Pattern"
args1(5).Value = false
args1(6).Name = "SearchItem.Content"
args1(6).Value = false
args1(7).Name = "SearchItem.AsianOptions"
args1(7).Value = false
args1(8).Name = "SearchItem.AlgorithmType"
args1(8).Value = 0
args1(9).Name = "SearchItem.SearchFlags"
args1(9).Value = 65536
args1(10).Name = "SearchItem.SearchString"
args1(10).Value = SString
args1(11).Name = "SearchItem.ReplaceString"
args1(11).Value = RString
args1(12).Name = "SearchItem.Locale"
args1(12).Value = 255
args1(13).Name = "SearchItem.ChangedChars"
args1(13).Value = 2
args1(14).Name = "SearchItem.DeletedChars"
args1(14).Value = 2
args1(15).Name = "SearchItem.InsertedChars"
args1(15).Value = 2
args1(16).Name = "SearchItem.TransliterateFlags"
args1(16).Value = 1280
args1(17).Name = "SearchItem.Command"
args1(17).Value = 3
args1(18).Name = "Quiet"
args1(18).Value = true

dispatcher.executeDispatch(document, ".uno:ExecuteSearch", "", 0, args1())

end sub

Sub ReplaceFooUskl(SString As String, RString As String)
dim document   as object
dim dispatcher as object
document   = ThisComponent.CurrentController.Frame
dispatcher = createUnoService("com.sun.star.frame.DispatchHelper")
dim args1(18) as new com.sun.star.beans.PropertyValue
args1(0).Name = "SearchItem.StyleFamily"
args1(0).Value = 2
args1(1).Name = "SearchItem.CellType"
args1(1).Value = 0
args1(2).Name = "SearchItem.RowDirection"
args1(2).Value = true
args1(3).Name = "SearchItem.AllTables"
args1(3).Value = false
args1(4).Name = "SearchItem.Backward"
args1(4).Value = false
args1(5).Name = "SearchItem.Pattern"
args1(5).Value = false
args1(6).Name = "SearchItem.Content"
args1(6).Value = false
args1(7).Name = "SearchItem.AsianOptions"
args1(7).Value = false
args1(8).Name = "SearchItem.AlgorithmType"
args1(8).Value = 1
args1(9).Name = "SearchItem.SearchFlags"
args1(9).Value = 65536
args1(10).Name = "SearchItem.SearchString"
args1(10).Value = SString
args1(11).Name = "SearchItem.ReplaceString"
args1(11).Value = RString
args1(12).Name = "SearchItem.Locale"
args1(12).Value = 255
args1(13).Name = "SearchItem.ChangedChars"
args1(13).Value = 2
args1(14).Name = "SearchItem.DeletedChars"
args1(14).Value = 2
args1(15).Name = "SearchItem.InsertedChars"
args1(15).Value = 2
args1(16).Name = "SearchItem.TransliterateFlags"
args1(16).Value = 1024
args1(17).Name = "SearchItem.Command"
args1(17).Value = 3
args1(18).Name = "Quiet"
args1(18).Value = true

dispatcher.executeDispatch(document, ".uno:ExecuteSearch", "", 0, args1())

End Sub

sub ReplaceFooNoRegUskl(SString As String, RString As String)
dim document   as object
dim dispatcher as object
document   = ThisComponent.CurrentController.Frame
dispatcher = createUnoService("com.sun.star.frame.DispatchHelper")
dim args1(18) as new com.sun.star.beans.PropertyValue
args1(0).Name = "SearchItem.StyleFamily"
args1(0).Value = 2
args1(1).Name = "SearchItem.CellType"
args1(1).Value = 0
args1(2).Name = "SearchItem.RowDirection"
args1(2).Value = true
args1(3).Name = "SearchItem.AllTables"
args1(3).Value = false
args1(4).Name = "SearchItem.Backward"
args1(4).Value = false
args1(5).Name = "SearchItem.Pattern"
args1(5).Value = false
args1(6).Name = "SearchItem.Content"
args1(6).Value = false
args1(7).Name = "SearchItem.AsianOptions"
args1(7).Value = false
args1(8).Name = "SearchItem.AlgorithmType"
args1(8).Value = 0
args1(9).Name = "SearchItem.SearchFlags"
args1(9).Value = 65536
args1(10).Name = "SearchItem.SearchString"
args1(10).Value = SString
args1(11).Name = "SearchItem.ReplaceString"
args1(11).Value = RString
args1(12).Name = "SearchItem.Locale"
args1(12).Value = 255
args1(13).Name = "SearchItem.ChangedChars"
args1(13).Value = 2
args1(14).Name = "SearchItem.DeletedChars"
args1(14).Value = 2
args1(15).Name = "SearchItem.InsertedChars"
args1(15).Value = 2
args1(16).Name = "SearchItem.TransliterateFlags"
args1(16).Value = 1024
args1(17).Name = "SearchItem.Command"
args1(17).Value = 3
args1(18).Name = "Quiet"
args1(18).Value = true

dispatcher.executeDispatch(document, ".uno:ExecuteSearch", "", 0, args1())

end sub

Эти макросики делают массовую замену, причём так:
ReplaceFoo — с регулярками и без учёта регистра;
ReplaceFooNoReg — без регулярок и без учёта регистра;
ReplaceFooUskl — с регулярками и с учётом регистра:
ReplaceFooNoRegUskl — без регулярок и с учётом регистра.

Теперь когда мне нужно быстро сделать макрос для поиска-замены того на сё, шила на мыло и пятого на десятое, я просто их вызываю, как мне нужно. Типа так:

Enlingven
ReplaceFoo(" : ", ": ")
ReplaceFoo("<", "<<")
ReplaceFoo(">", ">>")
ReplaceFoo(".$", "")
ReplaceFoo("/a ", "a\n\t")
ReplaceFoo("/e ", "e\n\t")
ReplaceFoo("/i ", "i\n\t")
ReplaceFoo("/o ", "o\n\t")
ReplaceFoo("/oj ", "oj\n\t")
ReplaceFoo("; ", "\n")
ReplaceFoo("1.: ", "1. ")
ReplaceFoo(" 2.: ", "\n\t2. ")
ReplaceFoo(" 3.: ", "\n\t3. ")
ReplaceFoo(" 4.: ", "\n\t4. ")
ReplaceFoo(" 5.: ", "\n\t5. ")
ReplaceFoo(" 6.: ", "\n\t6. ")
ReplaceFoo(" 7.: ", "\n\t7. ")
ReplaceFoo(": ", "\n\t")
ReplaceFoo(" 1. ", "\n\t1. ")
ReplaceFooNoReg("(", "[com][i](")
ReplaceFooNoReg(")", ")[/i][/com]")
ReplaceFooNoReg("[com][i](ad)[/i][/com]", "(ad)")
ReplaceFooNoReg("[com][i](ec)[/i][/com]", "(ec)")
MsgBox "Finite :)"
End Sub

dziglo

ЦитироватьСобственно, что Вы хотите добиться этим макросом?

В конечном итоге я хочу в одном oxt-файле поместить:
а) установку проверки орфографии для определенного языка
б) установку нескольких простых макросов с кнопкой на панели LibreOffice, нажатие которой бы приводило к выполнению этих макросов.

Но так как я ещё не понял как мне совместить установщик проверки орфографии и макрос на Бейсике, то пока решил понять как можно объединить вместе несколько бейсик-макросов.

dziglo

Цитата: gabix от  5 июня 2023, 20:47Теперь когда мне нужно быстро сделать макрос...

А как сделать максимально лаконичный макрос замены с применением регулярки? Ведь когда я записываю действия, и OpenOffice собирает их в макрос, то там кажется и лишний код появляется.
А как написать макрос, ищущий:
€|£
и заменяющий его на:
¢

bigor

Цитата: dziglo от  7 июня 2023, 08:23максимально лаконичный

Sub ReplaceVal
oReplace = ThisComponent.createReplaceDescriptor()
oReplace.SearchRegularExpression = true
oReplace.SearchString = "(€|£)"
oReplace.ReplaceString = "¢"
ThisComponent.replaceAll(oReplace)
msgbox "Обработка завершена"
End Sub
Поддержать разработчиков LibreOffice можно можно тут, а наш форум вот тут

dziglo

Цитата: bigor от  7 июня 2023, 10:34Sub ReplaceVal
А как можно подправить, чтобы поиск и замена происходили в выделенной части текста, если часть выделена, и во всем тексте документа, если выделений в тексте нет?

economist

selString = ThisComponent.CurrentController.getViewCursor().getString()
Макросы в LO гораздо сложнее чем VBA, читать книги Питоньяка и Форумы придется постоянно, даже для самых простых вещей. За вас это никто делать не будет. Без чтения не обойтись в силу того что, скажем, в строке выше, где считывается текст из выделения - нет и близко слова selection. И наоборот - там где оно есть, оно будет сложным объектом, у которых нет простого метода getText или getString. Поэтому нужно приготовиться к длительной борьбе. Когда меня спрашивают почему так все сложно - я всегда валю все на немцев (StarOffice, прародитель LO) - они в 90-х слишком основательно подошли к делу.
Руб. за сто, что Питоньяк
Любит водку и коньяк!
Потому что мне, без оных, -
Не понять его никак...

dziglo

Цитата: economist от  9 июня 2023, 11:01selString = ThisComponent.CurrentController.getViewCursor().getString()
читать книги Питоньяка и Форумы придется постоянно, даже для самых простых вещей. За вас это никто делать не будет.

Согласен, это я понимаю.

Но вроде в LO можно писать макросы на Python, но я не встречал такие макросы.