随着产业日渐成熟,客户对於需求也越来困难,ABAPER 为了生存不可避免也必须不断精进自我,而这篇文章也是自己在学习路上的一份积累。
报表程序是 ABAP 中最常开发的功能之一,其中 ALV 报表必是ABAPER 无法避免的课题,在使用者没有要求时,大多会CALL Function 来呈现,下方列出部分常用 ALV fcnction:
然而在部分需求中,如:搜寻条件要与 ALV 报表在相同介面时,此时便须要ALV-OO 才能达成目的
实现介面如下
在开始介绍范例程序时,会运用到下方观念
TYPE-POOLS:abap.
DATA: lt_table LIKE TABLE OF dntab,
ls_table TYPE dntab,
d_ref TYPE REF TO data,
lt_comp TYPE abap_component_tab,
lt_alv_cat TYPE TABLE OF lvc_s_fcat,
ls_alv_cat LIKE LINE OF lt_alv_cat,
gv_noinput TYPE c,
gv_modify TYPE c.
*----- For Dialog Program Logic flow
FIELD-SYMBOLS <gv_screen_no> TYPE any ."VALUE '1000'.
DATA ok_code LIKE sy-ucomm.
*----- Field Symbol
FIELD-SYMBOLS: <dyn_table> TYPE STANDARD TABLE ,
<dyn_tmp_struc> TYPE any,
<dyn_wa> TYPE any ,
<dyn_tmp_table> TYPE table.
*-------- For ALV
DATA: g_container TYPE scrfname VALUE 'ALV_P',
g_container_1 TYPE scrfname VALUE 'ALV_P2',
grid1 TYPE REF TO cl_gui_alv_grid,
grid2 TYPE REF TO cl_gui_alv_grid,
gs_print TYPE lvc_s_prnt,
gs_print_1 TYPE lvc_s_prnt,
gs_layout TYPE lvc_s_layo,
gs_layout_1 TYPE lvc_s_layo,
g_custom_container_ma TYPE REF TO cl_gui_custom_container,
g_custom_container TYPE REF TO cl_gui_custom_container,
lt_fieldcat TYPE slis_t_fieldcat_alv WITH HEADER LINE,
ir_data_changed TYPE REF TO cl_alv_changed_data_protocol.
*----Excel open
DATA: lv_rc TYPE i.
DATA: lt_file_table TYPE filetable.
**SEREEN **
SELECTION-SCREEN BEGIN OF SCREEN 1100 AS SUBSCREEN.
PARAMETERS: p_tab_n LIKE tabname .
PARAMETERS: p_infile TYPE localfile DEFAULT 'C:\temp\upload.xlsx' .
SELECTION-SCREEN BEGIN OF BLOCK lc_2 WITH FRAME TITLE TEXT-002 .
PARAMETERS: r_ins TYPE c RADIOBUTTON GROUP g1.
PARAMETERS: r_mod TYPE c RADIOBUTTON GROUP g1.
SELECTION-SCREEN END OF BLOCK lc_2.
SELECTION-SCREEN END OF SCREEN 1100 .
CALL SCREEN 1000.
AT SELECTION-SCREEN ON VALUE-REQUEST FOR p_infile.
CALL METHOD cl_gui_frontend_services=>file_open_dialog
EXPORTING
window_title = '打开文件'
CHANGING
file_table = lt_file_table
rc = lv_rc.
IF sy-subrc = 0.
READ TABLE lt_file_table INTO DATA(wa_file_table) INDEX 1.
p_infile = wa_file_table-filename.
ENDIF.
FROM and MODULE
*&---------------------------------------------------------------------*
*& Form authorization_check
*&---------------------------------------------------------------------*
*& Begin Date : 2021/02/02
*& Author : Kevin Yu
*& Description : 权限及输入条件确认及卡控
*----------------------------------------------------------------------*
*& Version :
*----------------------------------------------------------------------*
FORM authorization_check.
" UNASSIGN <dyn_table>.
" UNASSIGN <dyn_tmp_struc>.
IF p_tab_n IS INITIAL OR p_infile IS INITIAL.
MESSAGE 'Table or Path cannot be null!!' TYPE 'I' DISPLAY LIKE 'E'.
ELSE.
SELECT SINGLE dd02l~tabname FROM dd02l INTO @DATA(lv_tabname)
WHERE dd02l~tabname EQ @p_tab_n.
IF sy-subrc EQ 0.
PERFORM get_dynamic_itab.
PERFORM excel_upload TABLES <dyn_table> .
"CHECK <dyn_table> IS NOT INITIAL.
PERFORM display_data USING <dyn_table> .
IF r_ins EQ 'X' AND r_mod EQ ''.
ELSEIF r_mod EQ 'X' AND r_ins EQ ''.
ENDIF.
ELSE.
MESSAGE 'Table Not Active, Please check!!' TYPE 'I' DISPLAY LIKE 'E'.
ENDIF.
ENDIF.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form get_dynamic_itab
*&---------------------------------------------------------------------*
*& Begin Date : 2021/02/02
*& Author : Kevin Yu
*& Description : 依输入 TABLE 名产出对应栏位
*----------------------------------------------------------------------*
*& Version :
*----------------------------------------------------------------------*
FORM get_dynamic_itab.
*取出结构字段目录
CALL FUNCTION 'NAMETAB_GET'
EXPORTING
langu = sy-langu
tabname = p_tab_n
TABLES
nametab = lt_table.
IF sy-subrc NE 0.
MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno
WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4.
ENDIF.
*依字段目录产出参考目录
CLEAR lt_alv_cat.
LOOP AT lt_table ASSIGNING FIELD-SYMBOL(<fs_table>).
ls_alv_cat-fieldname = ls_alv_cat-ref_field = <fs_table>-fieldname.
ls_alv_cat-ref_table = p_tab_n.
APPEND ls_alv_cat TO lt_alv_cat.
CLEAR: <fs_table>,ls_alv_cat.
ENDLOOP.
UNASSIGN <fs_table>.
CALL METHOD cl_alv_table_create=>create_dynamic_table
EXPORTING
it_fieldcatalog = lt_alv_cat
IMPORTING
ep_table = d_ref.
IF sy-subrc NE 0.
MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno
WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4.
ENDIF.
ASSIGN d_ref->* TO <dyn_table>.
ASSIGN d_ref TO <dyn_tmp_struc>.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form excel_upload
*&---------------------------------------------------------------------*
*& Begin Date : 2021/02/02
*& Author : Kevin Yu
*& Description : 将 Excel data 从本地端传至宣告的 Table 中
*----------------------------------------------------------------------*
*& Version :
*----------------------------------------------------------------------*
FORM excel_upload TABLES table.
DATA: lt_data_in_file TYPE TABLE OF zalsmex_tabline,
ls_data_in_file TYPE zalsmex_tabline,
lv_count TYPE i,
lv_count_2 TYPE i.
DATA truxs_t_text_data(4096) TYPE c OCCURS 0. "不影响回传资料,仅因 FUNCTION 需求而设
"DATA: gt_data TYPE alsmex_tabline OCCURS 0 WITH HEADER LINE."不影响回传资料,仅因 FUNCTION 需求而设
CLEAR table.
CALL FUNCTION 'TEXT_CONVERT_XLS_TO_SAP'
EXPORTING
* I_FIELD_SEPERATOR =
i_line_header = 'X'
i_tab_raw_data = truxs_t_text_data
i_filename = p_infile
TABLES
i_tab_converted_data = table
EXCEPTIONS
conversion_failed = 1
OTHERS = 2
.
IF sy-subrc NE 0.
MESSAGE ID sy-msgid TYPE sy-msgty NUMBER sy-msgno
WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4.
ENDIF.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form display_data
*&---------------------------------------------------------------------*
*& Begin Date : 2021/02/02
*& Author : Kevin Yu
*& Description : 呈现 Excel 上传至 table 中的资料 --OO ALV
*----------------------------------------------------------------------*
*& Version :
*----------------------------------------------------------------------*
FORM display_data USING table.
"如要再 PAI 做 OO ALV 跳转时,要REFRESH ALV 物件及 GUI
" refresh_table_display & SAPGUI_SET_FUNCTIONCODE
IF grid1 IS INITIAL.
g_custom_container = NEW cl_gui_custom_container( g_container ).
grid1 = NEW cl_gui_alv_grid( g_custom_container ).
CALL METHOD grid1->set_table_for_first_display
EXPORTING i_structure_name = p_tab_n
is_print = gs_print
is_layout = gs_layout
CHANGING it_outtab = table.
CALL METHOD grid1->refresh_table_display
EXCEPTIONS
finished = 1
OTHERS = 2.
ELSE.
CALL METHOD grid1->set_table_for_first_display
EXPORTING i_structure_name = p_tab_n
is_print = gs_print
is_layout = gs_layout
CHANGING it_outtab = table.
CALL METHOD grid1->refresh_table_display
EXCEPTIONS
finished = 1
OTHERS = 2.
ENDIF.
IF sy-subrc <> 0.
* Implement suitable error handling here
ENDIF.
CALL FUNCTION 'SAPGUI_SET_FUNCTIONCODE' " 人为触发 PBO
EXPORTING
functioncode = 'REFRESH'
EXCEPTIONS
function_not_supported = 1
OTHERS = 2.
ENDFORM.
*&---------------------------------------------------------------------*
*& Module PBO OUTPUT
*&---------------------------------------------------------------------*
*&
*&---------------------------------------------------------------------*
MODULE pbo OUTPUT.
SET PF-STATUS 'STANDARD'.
IF gv_noinput EQ cl_abap_typedescr=>true.
ASSIGN '1200' TO <gv_screen_no>.
ELSE.
ASSIGN '1100' TO <gv_screen_no>.
ENDIF.
CHECK grid1 IS NOT INITIAL.
* IF gv_modify EQ 'X'.
* PERFORM alv_modify.
* ENDIF.
CALL METHOD grid1->refresh_table_display
EXCEPTIONS
finished = 1
OTHERS = 2.
ENDMODULE.
*&---------------------------------------------------------------------*
*& Module PAI INPUT
*&---------------------------------------------------------------------*
* text
*----------------------------------------------------------------------*
MODULE pai INPUT.
"CALL METHOD cl_gui_cfw=>dispatch. "人为触发 PAI
CLEAR gv_noinput.
CASE ok_code.
WHEN 'ENDE' OR 'ECAN'.
PERFORM exit_program.
WHEN 'EXE' OR 'ONLI' .
PERFORM authorization_check.
WHEN 'GET'.
PERFORM exit_program.
WHEN 'E'.
IF gs_layout-edit EQ cl_abap_typedescr=>true. "'X'.
gs_layout-edit = cl_abap_typedescr=>false.
PERFORM authorization_check.
ENDIF.
WHEN 'CHANGE_MODE'.
CHECK grid1 IS NOT INITIAL.
gv_noinput = cl_abap_typedescr=>true. "X"
gv_modify = cl_abap_typedescr=>true. "X"
PERFORM alv_modify TABLES <dyn_table>.
WHEN 'SPOS'.
PERFORM alv_modify TABLES <dyn_table>.
WHEN 'ENTRY_DATA'.
PERFORM data_entry.
ENDCASE.
CLEAR ok_code.
ENDMODULE.
FORM exit_program.
* CALL METHOD G_CUSTOM_CONTAINER->FREE.
* CALL METHOD CL_GUI_CFW=>FLUSH.
LEAVE TO SCREEN 0.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form alv_modify
*&---------------------------------------------------------------------*
*& Begin Date : 2021/02/03
*& Author : Kevin Yu
*& Description :
*----------------------------------------------------------------------*
*& Version :
*----------------------------------------------------------------------*
FORM alv_modify TABLES pt_list .
IF gs_layout-edit = cl_abap_typedescr=>true.
gs_layout-edit = cl_abap_typedescr=>false.
ELSE.
gs_layout-edit = cl_abap_typedescr=>true.
ENDIF.
CALL METHOD grid1->register_edit_event
EXPORTING i_event_id = cl_gui_alv_grid=>mc_evt_enter.
CALL METHOD grid1->set_table_for_first_display
EXPORTING i_structure_name = p_tab_n
is_print = gs_print
is_layout = gs_layout
CHANGING it_outtab = <dyn_table>.
CALL METHOD grid1->refresh_table_display
EXCEPTIONS
finished = 1
OTHERS = 2.
ENDFORM.
首先为了使Selection Screen 与 ALV 呈现在相同介面
必须要先自制自己的 Screen,并将ALV 包入物件中,并使用Custom Control 来呈现 ALV 物件
而为了使介面呈现Selection Screen 的部分,在PBO 及 PAI 皆要调用其作为subscreen,如此便可让两者同时
存在於同一画面中
而接着便是创建 ALV 相关物件
可参照程序TOP做宣告类型 ,运用宣告类型如下
g_container TYPE scrfname VALUE 'ALV_P'
grid1 TYPE REF TO cl_gui_alv_grid
gs_print TYPE lvc_s_prnt
gs_layout TYPE lvc_s_layo
g_custom_container TYPE REF TO cl_gui_custom_container
物件创建如下
g_custom_container = NEW cl_gui_custom_container( g_container ).
grid1 = NEW cl_gui_alv_grid( g_custom_container ).
准备好相关参数後接着调用 Method->set_table_for_first_display
便可在所设计的custom control 位置中呈现 alv
CALL METHOD grid1->set_table_for_first_display
EXPORTING i_structure_name = p_tab_n
is_print = gs_print
is_layout = gs_layout
CHANGING it_outtab = <dyn_table>.
而其中要注意的便是 alv 刷新问题
通常在刷新 alv 会调用Method->refresh_table_display
CALL METHOD grid1->refresh_table_display
EXCEPTIONS
finished = 1
OTHERS = 2.
然而因此范例并非再 PBO 处理,故要自行触发PBO 刷新 GUI 介面
CALL FUNCTION 'SAPGUI_SET_FUNCTIONCODE' " 人为触发 PBO
EXPORTING
functioncode = 'REFRESH'
EXCEPTIONS
function_not_supported = 1
OTHERS = 2.
至於其他细节就提供给各位看官自行研究啦~
<<: 做一份与众不同的简历 (Create a Compelling CV)
>>: 番外篇(2)一起来做 To Do List!- 实作篇(1)
2021 铁人赛 DAY10 昨天介绍了eventrouter收集k8s丛集中的event,今天则是...
AND和&&是相同的意思 AND运算子是左右两边结果为1,就回传1,否则回传0 Ti...
Q: 说好的文字Loading呢? A: 客倌这里上菜罗~ 前几篇的Loading都是以图案循环为...
# -*- coding: utf-8 -*- import numpy as np import ...
-什麽是风险? 选项B提供了最佳视角,但正确的版本应为“剩余风险低於董事会的风险承受能力。” 基於...