Как в реалтайме назначить функцию на кнопку?

Автор Strannik61, 20 июня 2016, 17:06

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

Strannik61

Диалог создаётся на лету. В том числе кнопки. Как к кнопке назначить функцию?
Например создаётся кнопка:
oDlgModel = CreateUnoService("com.sun.star.awt.UnoControlDialogModel")
oModel = oDlgModel.createInstance("com.sun.star.awt.UnoControlButtonModel")
oModel.setPropertyValue("Name", "Button1")
oModel.setPropertyValue("TabIndex", 1)
...

Как для кнопки правильно написать, чтобы при нажатии вызывалась функция?

economist

Надо назначить Действия для кнопки, а это задача нетривиальная, возможно нерешаемая.
Можно загружать диалог из общего места с обработчиком нажатия кнопки, но этот путь тернист.

Даже в MS Excel приходилось идти в обход - назначать макрос не на контрол, а на картинку, либо генерить код модуля построчно.

Обязательно ли нужен диалог? Может хватит обычного msgbox с 3-мя кнопками и иконками?
Руб. за сто, что Питоньяк
Любит водку и коньяк!
Потому что мне, без оных, -
Не понять его никак...

Strannik61

Да задачка стоит непростая. Переделываю пакет работы с БД.
В частности вызываются из базы данные по действиям (создание пустого файла, файла на основе шаблона, на основе существующего файла и т.д.).
И в зависимости от выбора нужно вызвать разные функции. Сами функции есть.
Вот думаю как лучше сделать. Казалось, что проще привязать действие к кнопке.
Похоже придётся обрабатывать имя нажатой кнопки и уже по нему определять нужную функцию.

rami

Надо назначить кнопке слушателя (это просто), а он уже знает что делать O0. Одной строкой кода создаётся слушатель, а второй этот слушатель назначается кнопке (всех делов). Можете написать подробней какие кнопки в диалоге и как вы его создаёте.

Strannik61

Как шаблон использую единый шаблон диалога Dialog1. Размер общий для всех диалогов (300 х 400).
На этом шаблоне 4 кнопки "На главную" - тип кнопки "Ок", "Закончить" - тип кнопки "Отмена", Две кнопки "Вперёд" и "Назад" - тип по умолчанию и на них  назначены скрипты в шаблоне.
Остальные кнопки генерируются в коде.
Кусочек кода:Sub Main
   oDlg = CreateUnoDialog(DialogLibraries.Standard.Dialog1)
oRowSet=Statement.executeQuery("SELECT xxx")
If Not IsNull(oRowSet) Then
numStep = 1
iStep = 1
j=0
while oRowSet.Next
if (iStep = maxFirm) then
iStep = 1
numStep = numStep + 1
End if
createButton(oDlgModel, iTabIndex, "Firm" +j, Array("Step", numStep,"PositionX", 50, "PositionY", 20 +j, "Width", iDlgWidth -100,_
"Height", 20, "Label", oRowSet.getString(2), "PushButtonType", com.sun.star.awt.PushButtonType.STANDARD))
j=j+25
iStep = iStep + 1
wend
End If
y = oDlg.execute()

End sub

Sub createButton(oDlgModel, index%, sName$, props())
Dim oModel
oModel = oDlgModel.createInstance("com.sun.star.awt.UnoControlButtonModel")
setProperties(oModel, props())
setProperties(oModel, Array("Name", sName$, "TabIndex", index%))
oDlgModel.insertByName(sName$, oModel)
index% = index% + 1
End Sub

Sub setProperties(oModel, props())
Dim i As Integer
For i=LBound(props()) To UBound(props()) Step 2
oModel.setPropertyValue(props(i), props(i+1))
Next
End sub

economist

#5
Создать в Диалоге все Кнопки (с кодом) заранее и просто управлять их видимостью. Для всех визардов так и делается. Контекст выполнения - определяет ветвление алгоритма.

По своему опыту знаю, что Wizard-ы пользователи проходят "на автомате" со скоростью дятла и ничего не читают. Трата времени на "красоту" и кнопочки - себя не оправдывает.

Гораздо проще сделать просто ODT, в котором разместить гиперссылки на шаблоны, переходы, справку и т.п. Дешево и сердито.
Руб. за сто, что Питоньяк
Любит водку и коньяк!
Потому что мне, без оных, -
Не понять его никак...

Strannik61

Этот способ с созданием диалога не прокатит. Причина банальна.
Я показал только первый этап диалога.
В дальнейшем он используется ещё не раз и количество кнопок неизвестно. Точнее оно определяется количеством записей в БД.
Оптимальным является создание слушателя и последующее действие по обработке нажатой кнопки.
Осталось понять как создать слушателя. :)

rami

Цитата: Strannik61 от 21 июня 2016, 09:12
Этот способ с созданием диалога не прокатит. Причина банальна.
Я показал только первый этап диалога.
В дальнейшем он используется ещё не раз и количество кнопок неизвестно. Точнее оно определяется количеством записей в БД.
Оптимальным является создание слушателя и последующее действие по обработке нажатой кнопки.
Осталось понять как создать слушателя. :)
Для меня сложно было понять как вам это объяснить, слишком много неопределённостей. Решил просто создать абстрактный образец на базе вашего кода. Вызывайте диалог и жмите на кнопки, учтите, что последние кнопки не уместились в диалоге, но их тоже можно "нажать" переключая фокус стрелкой вниз или клавишей "TAB"

economist

Strannik61 - а не проще ли использовать не Диалог, а Форму, раз идет зависимость от числа записей в БД?

Формой может быть не только объект BASE, но и отдельный ODT и даже ODS - файл. У меня пользователи отлично рисуют визарды на листах Calc, уменьшая число кода раза в два с помощью формул, функций, проверки данных, выпдающих списков итп - все средствами Calc. Макросы делают только >> и <<. 
Руб. за сто, что Питоньяк
Любит водку и коньяк!
Потому что мне, без оных, -
Не понять его никак...

Strannik61

Цитата: rami от 21 июня 2016, 07:53Для меня сложно было понять как вам это объяснить, слишком много неопределённостей. Решил просто создать абстрактный образец на базе вашего кода. Вызывайте диалог и жмите на кнопки, учтите, что последние кнопки не уместились в диалоге, но их тоже можно "нажать" переключая фокус стрелкой вниз или клавишей "TAB"
Появились вопросы:
1. При первом нажатии на кнопку выскакивает ошибка в строке oDlg = CreateUnoDialog(DialogLibraries.Standard.Dialog1)
При повторном нажатии все работает. До закрытия документа.
2. Как создана "Кнопка вызова диалога".
Что-то я сегодня конкретно туплю.)

Сейчас буду пробовать. Два дня времени не хватало.(

rami

Цитата: Strannik61 от 22 июня 2016, 16:281. При первом нажатии на кнопку выскакивает ошибка в строке oDlg = CreateUnoDialog(DialogLibraries.Standard.Dialog1)
При повторном нажатии все работает. До закрытия документа.
А мы так не договаривались 8-) я обещал две строчки кода: создание и назначение слушателя, но так как ваш код был "вырван" из другого большего кода, то пришлось закомментировать нерабочие "остатки", и добавить цикл. Для работы при первом открытии документа нужно добавить загрузку библиотеки (в самое начало макроса):DialogLibraries.LoadLibrary("Standard")
Цитата: Strannik61 от 22 июня 2016, 16:282. Как создана "Кнопка вызова диалога".
На панели инструментов "Элементы управления" нажать "Режим разработки", выбрать "Кнопку" и нарисовать её в документе, открыть редактирование свойств, назначить кнопке макрос.

Strannik61

Спасибо.)
Сейчас пишу макрос. Как будет готов - выложу на суд общественности. Может кому пригодится. Или кусочки из него  :beer:

Strannik61

Мдя. "Чем дальше влез, тем больше тараканов".
Очередная проблема.
После того как создал диалог и выполняю его показываются ВСЕ кнопки независимо от Step.
И как с этим бороться???
После перехода на следующую страницу всё начинает работать, но при старте нет.

rami

Цитата: Strannik61 от 22 июня 2016, 19:12После того как создал диалог и выполняю его показываются ВСЕ кнопки независимо от Step.
Свойство Step работает правильно, значит назначается не правильно.

Strannik61

Начал было писать, что ничего не работает.
В пример подпрограмму вставил. И только потом заметил, что действительно сам дурак.)
Забыл для модели диалога Step задать.
Для кнопок задал, а диалогу нет.
Спасибо, что наталкиваете на умные мысли.)))