Форум поддержки пользователей. LibreOffice, Apache OpenOffice, OpenOffice.org

Форум поддержки пользователей. LibreOffice, Apache OpenOffice, OpenOffice.org

15 Апрель 2021, 16:41 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
Новости: Здесь можно поблагодарить участников форума Улыбка
 
   Начало   Помощь Поиск Войти Регистрация    задать вопрос  
Страниц: 1   Вниз
  Печать  
Автор Тема: [Решено] UDF: Как сослаться на диапазон ячеек?  (Прочитано 807 раз)
0 Пользователей и 1 Гость смотрят эту тему.
eeigor
Форумчанин
***
Offline Offline

Пол: Мужской
Сообщений: 513



« Стартовое сообщение: 3 Февраль 2021, 10:54 »

User defined (custom) function
Надо работать с содержимым диапазона ячеек (с частью текста внутри ячейки), используя пользовательскую функцию на листе.
Как получить доступ к диапазону?
Судя по этой ссылке, никак, если только не использовать опцию совместимости с VBA.

Upd1: Передать ссылку в виде строки (absolute name)? Выбрать мышью, заключить в кавычки. Выполнить разбор строки?.. Статичный вариант, и если вставить столбец/строку, то всё поплывёт…

Или так:
=UDF(COLUMN(A6);ROW(A6);COLUMN(C9);ROW(C9))
« Последнее редактирование: 3 Февраль 2021, 22:59 от eeigor » Записан

Ubuntu 18.04 LTS • LO 7.1.1.2 Community
sokol92
Форумчанин
***
Offline Offline

Пол: Мужской
Сообщений: 379


WWW
« Ответ #1: 3 Февраль 2021, 17:43 »

если только не использовать опцию совместимости с VBA
А что, эта опция стала платной?  Улыбка

В стандартную библиотеку:
Код:
Option VbaSupport 1
Function Udf(arg) As Double
  Msgbox "Адрес параметра функции UDF: " & arg.Address
End Sub

В ячейку:

=UDF(A8:B16)
« Последнее редактирование: 3 Февраль 2021, 18:12 от sokol92 » Записан

Владимир.
eeigor
Форумчанин
***
Offline Offline

Пол: Мужской
Сообщений: 513



« Ответ #2: 3 Февраль 2021, 18:37 »

Сначала не хотел ради "чистоты" кода... Пока не использовал опции совместимости с VBA.
sokol92, насколько всё это стабильно работает: в смысле, не добавляет ли установка флажка каких-л. ошибок сама по себе?
И что, я должен работать (ваш пример) с моделью Excel? Или можно комбинировать код?

Upd1:
Можно, правда, "условиться" передавать левый верхний угол непрерывного диапазона, использовав минимум ссылок ( COLUMN(A2), ROW(), ... ), и ограничиться использованием листа, на котором помещена формула*, а в коде вычислить размер CurrentRegion и с работать с ним. Допустимо, как считаете? До тех пор, пока не допилят... Или переходить на модель Excel и синтаксис VBA?

* С иным листом ( SHEET(), COLUMN(A2), ROW(), ... ) могут быть тоже неведомые мне заморочки...
Код:
Function getSheet(byVal vSheet)
REM Helper for sheet functions. Get cell from sheet's name or position; cell's row-position; cell's col-position
on error goto exitErr
   select case varType(vSheet)
   case is = 8
      if thisComponent.sheets.hasbyName(vSheet) then
         getSheet = thisComponent.sheets.getByName(vSheet)
      else
         getSheet = NULL
      endif
   case 2 to 5
      vSheet = cInt(vSheet)
      'Wow! Calc has sheets with no name at index < 0,
      ' so NOT isNull(oSheet), if vSheet <= lbound(sheets) = CRASH!
      'http://www.openoffice.org/issues/show_bug.cgi?id=58796
      if(vSheet <= thisComponent.getSheets.getCount)AND(vSheet > 0) then
         getSheet = thisComponent.sheets.getByIndex(vSheet -1)
      else
         getSheet = NULL
      endif
   end select
exit function
exitErr:
getSheet = NULL
End Function
Примечание. Код выше достаточно древний.
« Последнее редактирование: 3 Февраль 2021, 19:14 от eeigor » Записан

Ubuntu 18.04 LTS • LO 7.1.1.2 Community
sokol92
Форумчанин
***
Offline Offline

Пол: Мужской
Сообщений: 379


WWW
« Ответ #3: 3 Февраль 2021, 19:41 »

насколько всё это стабильно работает
Я использую опцию совместимости с Excel только в тех случаях, когда нет соответствующих "родных" конструкций (как, например, для задачи из данной темы форума). Еще пример - функция InStrRev.

Конструкция из #1 представляется стабильной. В этом случае в качестве параметра UDF-функции формируется объект с Implementation Name = SvVbaRange, поддерживающий сервис ooo.vba.excel.Range. Этот объект реализует значительное количество свойств и методов объекта Range Excel - насколько качественно и эффективно я не проверял, поскольку, как уже упомянуто, предпочитаю "родные" методы.

Кроме адреса диапазона ячеек можно еще получить, например,  имя листа:

Код:
 Msgbox "Адрес параметра функции UDF: " & arg.Address & " лист " & arg.Worksheet.Name
« Последнее редактирование: 3 Февраль 2021, 19:51 от sokol92 » Записан

Владимир.
eeigor
Форумчанин
***
Offline Offline

Пол: Мужской
Сообщений: 513



« Ответ #4: 3 Февраль 2021, 20:57 »

Возвращается объект SvVbaRange
Option VBASupport 1
'Option Compatible

Function UDF(oVbaRange As Range, ...)
    For Each oCell In oVbaRange.CellRange .queryContentCells(nCellFlags).Cells

Upd1:
Разбираюсь, не всё так однозначно. При помещении функции на лист начались проблемы. Отпишусь...
Upd2:
Теперь работает (выше). Особенность одна: свойство CellRange возвращает UNO-объект ScCellRange даже для одной ячейки. И дальше весь код пошёл "нативный", то есть родной. Таким образом, степень вмешательства VBA кода минимальна.

« Последнее редактирование: 3 Февраль 2021, 22:57 от eeigor » Записан

Ubuntu 18.04 LTS • LO 7.1.1.2 Community
economist
Форумчанин
***
Offline Offline

Сообщений: 1 421


« Ответ #5: 3 Февраль 2021, 22:36 »

Более полный набор флагов совместимости для UDF:
Код:
Option VBASupport 1
Option Compatible
'----------------------------------
Sub RunOnceVBASupport
ThisComponent.BasicLibraries.VBACompatibilityMode=true  
End sub
Записан

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

Пол: Мужской
Сообщений: 513



« Ответ #6: 3 Февраль 2021, 22:58 »

@sokol92, @economist, спасибо за помощь.
Записан

Ubuntu 18.04 LTS • LO 7.1.1.2 Community
eeigor
Форумчанин
***
Offline Offline

Пол: Мужской
Сообщений: 513



« Ответ #7: 26 Февраль 2021, 07:49 »

Отписываюсь, как обещал.
Работа пользовательской функции со ссылкой на диапазон Excel в режиме совместимости нареканий не вызывает. Ни одной ошибки. Как родной!
Как, вообще, без этого можно?..
Записан

Ubuntu 18.04 LTS • LO 7.1.1.2 Community
economist
Форумчанин
***
Offline Offline

Сообщений: 1 421


« Ответ #8: 26 Февраль 2021, 08:18 »

Вчера буквально провел анализ последствий личного отказа в LO от VBA в пользу "чистоты" API. Проекты удлинились по срокам реализации в 2 раза, код - увеличился в 3-4 раза. Это слишком высокая цена, и граничит с садомазо.

Принял решение в каждом крупном проекте собирать VBA код в один "жертвенный" модуль с опциями совместимости, обвесить его тестами при запуске и мысленно готовиться к его отваливанию из-за регрессии, что уже наблюдал за 7 лет дважды, версии не записал, но по моему они все были релизы с нулем после первой точки. Причем проблемы были даже с portable LO (тот выходит всегда позже на месяцы и вроде д.б. "вылизан").

Так что можно, но нельзя. Слишком многое теряется. Хотя я не показателен, много кодю в Excel, на чистом VBA.      
Записан

Руб. за сто, что Питоньяк
Любит водку и коньяк!
Потому что мне, без оных, -
Не понять его никак...
Страниц: 1   Вверх
  Печать  
 
Перейти в:  

Powered by MySQL Powered by PHP Powered by SMF 1.1.21 | SMF © 2006-2009, Simple Machines Valid XHTML 1.0! Valid CSS!