ABAP Thinking


Инкремент шестнадцатеричных чисел на ABAP

Друзья, всем известен способ ведения генерации порядковых номеров документов для номеров
с десятеричными цифрами. В транзакции SNRO ведутся диапазоны номеров, а с помощью
функционального модуля NUMBER_GET_NEXT можно получить следующий порядковый номер из диапазона.
В этом очерке описываю, генератор номеров с шестнадцатеричными цифрами на ABAP,
представляю небольшую подпрограмму, увеличивающую шестнадцатеричное число на единицу.
Подпрограмма получает на вход шестнадцатеричное число и увеличивает его на единицу.
*&---------------------------------------------------------------------*
*&      Form  INCREASE_KEY
*&---------------------------------------------------------------------*
*       text
*----------------------------------------------------------------------*
*  -->  p1        text
*  <--  p2        text
*----------------------------------------------------------------------*
FORM INCREASE_KEY  CHANGING pv_key type wanid.
  CONSTANTS:

     c_transl  type text100 value

               '0112233445566778899AABBCCDDEEFFGGHHIIJJKKLLMMNNOOPPQQRRSSTTUUVVWWXXYYZZ0'.

  TRANSLATE pv_key+2(1)  USING c_transl.

  IF pv_key+2(1) = '0'.

    TRANSLATE pv_key+1(1)  USING c_transl.

    IF pv_key+1(1) = '0'.

      TRANSLATE pv_key+0(1)  USING c_transl.

    ENDIF.

  ENDIF.

ENDFORM.                    " INCREASE_KEY
добавлено: 21 сен 18 просмотры: 838, комментарии: 1



Сохранение данных таблицы в запрос настройки

Друзья, хочу опубликовать код, позволяющий сохранять записи таблицы словаря в транспортный запрос настройки для переноса в другие системы на примере небольшой подпрограммы:
FORM PUT_TO_TRANSPORT TABLES lt_wanid TYPE tty_wanid.

  DATA: l_order LIKE e070-trkorr,
            l_task  LIKE e070-trkorr.

 "Внутренние таблицы с ключами строк таблицы словаря, помещаемыми в запрос
  DATA: lt_e071  TYPE e071  OCCURS 4  WITH HEADER LINE,
            lt_e071k TYPE e071k OCCURS 25 WITH HEADER LINE.
  DATA: lv_wanid type wanid,
            ls_tvwa type tvwa.
  ranges: lr_wanid for tvwa-wanid.
* >>> Формирование данных для включения записей в транспортный запрос -&
  DEFINE mac__add_table. "Макрос для заполнения 
    clear lt_e071.
    lt_e071-pgmid    = 'R3TR'.
    lt_e071-object   = 'TABU'.
    lt_e071-obj_name = &1.
    lt_e071-objfunc  = 'K'.
    append lt_e071.
    lt_e071k-pgmid      = 'R3TR'.
    lt_e071k-object     = 'TABU'.
    lt_e071k-objname    = &1.
    lt_e071k-mastertype = 'TABU'.
    lt_e071k-mastername = &1.
    lt_e071k-tabkey    = sy-mandt. "Первая часть ключа у таблиц - мандант
    case &1.
      when 'TVWA'.  " В запрос помещается содержимое 2х таблиц TVWA и TVWAТ
        lt_e071k-tabkey+3  = lv_wanid. "Вторая часть ключа для таблицы  TVWA
     when 'TVWAT'.
        lt_e071k-tabkey+3 =  sy-langu. "Вторая часть ключа для таблицы  TVWAT - язык
        lt_e071k-tabkey+4  = lv_wanid. "Третья часть ключа для таблицы  TVWAT 
    endcase.
    append lt_e071k.
  END-OF-DEFINITION.
* <<< -----------------------------------------------------------------*
  loop at lt_wanid into lv_wanid.
    select SINGLE * from tvwa into ls_tvwa WHERE wanid = lv_wanid.
    
* Формирование данных присвоения
    mac__add_table: 'TVWA',
                    'TVWAT'.

  endloop.
  if lt_e071[] is NOT INITIAL and lt_e071k[] is NOT INITIAL.
* Выбор запроса на перенос (запрос инструментальных средств)
    CALL FUNCTION 'TR_ORDER_CHOICE_CORRECTION'
      EXPORTING
        iv_category = 'SYST'                                "#EC NOTEXT
      IMPORTING
        ev_order    = l_order
        ev_task     = l_task
      EXCEPTIONS
        OTHERS      = 1.
    IF sy-subrc <> 0.
      exit.
    ENDIF.
* Присвоение данных запросу
    CALL FUNCTION 'TR_APPEND_TO_COMM_OBJS_KEYS'
      EXPORTING
        wi_trkorr = l_task
      TABLES
        wt_e071   = lt_e071
        wt_e071k  = lt_e071k
      EXCEPTIONS
        OTHERS    = 1.
    IF sy-subrc <> 0.
*   MSG: ошибка присвоения данных запросу
    ENDIF.
  endif.

ENDFORM.                    " PUT_TO_TRANSPORT
добавлено: 10 авг 18 просмотры: 1074, комментарии: 0



Перевод количества в другие единицы измерения (БЕИ в АЕИ).

Только что возникла задачка конвертации количества на складе из базовых единиц измерения в альтернативные.
Сначала думал что лучше использовать коэффициент из таблицы MARM,
но затем, был найден замечательный и простой функциональный модуль для конвертации
UNIT_CONVERSION_SIMPLE.

DATA: lv_iwert    type p decimals 3.
 .......
 call function 'UNIT_CONVERSION_SIMPLE'
            exporting
              input      = lv_iwert  " количество "
              round_sign = '3'
              unit_in    = <fs_mara>-gewei " ЕИ из "
              unit_out   = 'TO'                    " ЕИ в "
            importing
              output     = gs_data-mengeall
            exceptions
              others     = 0.
добавлено: 20 ноя 12 просмотры: 4324, комментарии: 0



Селекционный экран - скрытие полей в зависимости от radiobutton.

В этом блоге опишу возможности обработки события от radiobutton и возможность скрытия
других полей селекционного экрана взависимости от положения радиокнопки.
Все просто как дважды два.
1) Обявляются переменные селекционного экрана:

selection-screen begin of block b1 with frame title text-003.
parameters : rb1 radiobutton group opr modif id r1 user-command go default 'X',
rb2 radiobutton group opr modif id r2.
selection-screen end of block b1.

Не стоит забывать про ИД модификации у radiobutton group: modif id r1 - иначе не будет возникать события при
смене положения радиокнопок

selection-screen begin of block b2 with frame title text-001.
parameters so_werks type t001w-werks obligatory memory id wrk modif id sc1.
selection-screen end of block b2.

Здесь тоже нужен modif id для возможности обращения к полю в цикле Loop at Screen

2) Обработчик события первоначальной проресовки экрана
at selection-screen output.
loop at screen.
elseif screen-group1 = 'SC1' and rb2 ne space.
screen-active = '0'.
modify screen.
endif.
endloop.
Если элемент экрана имеет признак в группе 1 равный SC1 - элемент скрывается.

3) Обработчик события смены положения радиокнопок. Содержимое обработчика такое же как и у
предшествующего.
at selection-screen on radiobutton group opr.
loop at screen.
elseif screen-group1 = 'SC1' and rb2 ne space.
screen-active = '0'.
modify screen.
endif.
endloop.

Полный текст программы:
report ZRBEVENT.


selection-screen begin of block b1  with frame title  text-003.
parameters : rb1 radiobutton group opr modif id r1 user-command go default 'X',
             rb2 radiobutton group opr modif id r2.
selection-screen end of block b1.

selection-screen begin of block b2  with frame title  text-001.
	parameters so_werks type t001w-werks obligatory memory id wrk modif id sc1.
selection-screen end of block b2.


at selection-screen output.
  loop at screen.
    elseif screen-group1 = 'SC1' and rb2 ne space.
      screen-active = '0'.
      modify screen.
    endif.
  endloop.

at selection-screen on radiobutton group opr.
  loop at screen.
    elseif screen-group1 = 'SC1' and rb2 ne space.
      screen-active = '0'.
      modify screen.
    endif.
  endloop.
добавлено: 01 ноя 12 просмотры: 6160, комментарии: 2



POPUP окно с вводимыми полями

Для того сделать popup окно с полями для ввода значений не обязательно рисовать для этого целый экран.
Есть замечательный функциональный модуль POPUP_GET_VALUES, позволяющий решить ту же задачу буквально за 5 минут.
Одним из параметров функционального модуля является внутренняя таблица, основанная на структуре, в которую помещаются
названия пар типа таблица-поле для ввода, плюс значение по умолчанию, если необходимо а так же признак обязательности поля.
После того как пользователь ввёл данные и закрыл окно, производится считывание введенных значений.

  sval-fieldtext = 'Склад'(085).
  sval-field_obl = space.
  sval-value = sp_lgort-low.
  append sval to t_fields.
  sval-tabname = 'RESB'.
  sval-fieldname = 'UMLGO'.
  sval-fieldtext = 'Принимающий склад'(086).
  sval-field_obl = space. sval-value = space.
  append sval to t_fields.
  sval-tabname = 'MSEG'.
  sval-fieldname = 'BWART'.
  sval-fieldtext = 'Вид движения'(087).
  sval-field_obl = 'X'.
  sval-value = sp_bwart-low.
  append sval to t_fields. " Вызываем функциональный модуль "
  call function 'POPUP_GET_VALUES'
    exporting
      popup_title     = 'Передать на О/Х'(088)
    importing
      returncode      = retcode
    tables
      fields          = t_fields
    exceptions
      error_in_fields = 1
      others          = 2.
  if retcode = 'A' or sy-subrc <> 0.
    l_error = 'X'. exit.
  else. " Если PUPUP окно закрыто по кнопке ОК - считываем введенные пользователем значения. " read
    table t_fields index 1 into sval. lv_konnr = sval-value.
  endif.
добавлено: 25 окт 12 просмотры: 2606, комментарии: 0



Преобразование чисел и цифр в числительные

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


Следующий участок кода выведет "Двенадцать"
CALL FUNCTION 'SPELL_AMOUNT'
   EXPORTING
     amount = 12
   IMPORTING 
      in_words = spell
   EXCEPTIONS
     not_fount  = 1
     too_large  = 2
     OTHER      = 3.
  write: / spell.
добавлено: 03 авг 12 просмотры: 2833, комментарии: 1



ABAP: Путь к папке Windows 'Мои Документы'

Если ставится задача загрузки/выгрузки файла на локальный компьютер пользователя, при вызове диалога выбора места загрузки/сохранения, можно не напрягать пользователя от C:\ поиском папки "Мои Документы" а сразу открыть диалог в этой папке.

Для этого требуется прочитать регистр Windows с помощью статического метода

класса:

CL_GUI_FRONTEND_SERVICES=>REGISTRY_GET_VALUE

Например так:

CALL METHOD CL_GUI_FRONTEND_SERVICES=>REGISTRY_GET_VALUE
    EXPORTING
        ROOT         = CL_GUI_FRONTEND_SERVICES=>HKEY_CURRENT_USER
        KEY          =  'Software\Microsoft\Windows\CurrentVersion\Explorer\User Shell Folders'
        VALUE        = 'Personal'
    IMPORTING
         REG_VALUE   = my_documents_path
     EXCEPTIONS
         GET_REGVALUE_FAILED  = 1
         CNTL_ERROR           = 2
         ERROR_NO_GUI         = 3
         NOT_SUPPORTED_BY_GUI = 4
         others               = 5.



P.S. параметр KEY должен быть следующим:

'Software\Microsoft\Windows\CurrentVersion\Explorer\User Shell Folders' ))D
добавлено: 11 июл 12 просмотры: 2090, комментарии: 3



ABAP: узнать последний день месяца

В процессе работы часто возникают задачи по определению последнего дня месяца.

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

DEFINE LAST_DAY.
   &1+6(2) = '01'.
   &1 = &1 + 31.
   &1+6(2) = '01'.
   &1 = &1 - 1.
END-OF-DEFINITION.





Вызов макроса:

data:
  lf_date type d. 

lf_date = sy-datum.
last_day lf_date.

write: / lf_date. 




Макрос отлично справляется с 29м февраля високосного года.
добавлено: 11 июл 12 просмотры: 2389, комментарии: 0