方法一
如果希望 ALV 中某字段具有搜索帮助,第一种办法当然是对表中某字段的引用,设置ref_table、ref_field,将自动触发该字段所带的搜索帮助。
方法二
第二种办法就是利用自定义代码来实现 ALV 的搜索帮助,显然它的功能更强大、更灵活。
OO ALV
针对在 OO ALV 中实现搜索帮助,其主要步骤有:
1:对需要自定义搜索帮助的字段,设置其 fieldcat 时:
gs_fieldcat-f4availabl = 'X'.
2:在 ALV 的事件处理类中添加 Search Help Method,方法定义如下:
CLASS lcl_event_receiver DEFINITION.
PUBLIC SECTION.
METHODS: handle_onf4 FOR EVENT onf4 OF cl_gui_alv_grid
IMPORTING e_fieldname es_row_no er_event_data et_bad_cells sender.
ENDCLASS. "LCL_EVENT_RECEIVER DEFINITION"
CLASS lcl_event_receiver IMPLEMENTATION.
METHOD handle_onf4.
"搜索帮助参数的自定义f4检索帮助"
PERFORM f4_help_value USING e_fieldname es_row_no er_event_data sender.
"设置后,alv稳定刷新"
PERFORM refresh_table_alv.
ENDMETHOD. "HANDLE_ONF4"
ENDCLASS. "LCL_EVENT_RECEIVER IMPLEMENTATION"
DATA go_evt_receiver TYPE REF TO lcl_event_receiver.
- e_fieldname:代表用户点击了 ALV 的哪个字段来触发搜索帮助
- es_row_no:代表了当前行信息,es_row_no-row_id:就是 ALV 中内表记录的 index
- er_event_data:代表了当前用户对 ALV 进行了哪些编辑的信息。在 Method 的最后,记得加上
er_event_data->m_event_handled = 'X'.通知系统搜索事件处理完毕,这样就不会调用系统标准的Search Help。 - et_bad_cells:不正确的单元格
3:在创建 ALV 对象之后,要对需要自定义搜索帮助的字段进行注册并为其指定事件处理类。
DATA: lt_f4 TYPE lvc_t_f4,
ls_f4 TYPE lvc_s_f4.
CLEAR:lt_f4,ls_f4.
ls_f4-fieldname = 'FIELD_NAME'. "需要添加搜索帮助的内表字段"
ls_f4-register = 'X'.
ls_f4-chngeafter = 'X'.
ls_f4-getbefore = 'X'.
INSERT ls_f4 INTO TABLE lt_f4.
"事件注册"
CALL METHOD go_alv_grid->register_f4_for_fields
EXPORTING
it_f4 = lt_f4.
"事件处理类"
CREATE OBJECT go_evt_receiver.
SET HANDLER go_evt_receiver->handle_onf4 FOR go_alv_grid.
- lvc_s_f4 中的字段 getbefore 和 changeafter 代表是否触发 data_changed 事件。
4:方法代码实现
*&---------------------------------------------------------------------*
*& Form F4_HELP_VALUE
*&---------------------------------------------------------------------*
* 窗口时间参数的自定义f4检索帮助
*----------------------------------------------------------------------*
FORM f4_help_value USING p_fieldname TYPE lvc_fname
p_row_no TYPE lvc_s_roid
p_event TYPE cl_alv_event_data
p_sender TYPE REF TO cl_gui_alv_grid.
DATA: lt_return TYPE STANDARD TABLE OF ddshretval,
ls_return TYPE ddshretval.
DATA: ls_modi TYPE lvc_s_modi.
FIELD-SYMBOLS: <lv_itab> TYPE lvc_t_modi.
DATA: lt_value_tab TYPE TABLE OF XXX.
"获取搜索帮助数据 存入表LT_VALUE_TAB
CALL FUNCTION 'F4IF_INT_TABLE_VALUE_REQUEST'
EXPORTING
retfield = 'WERKS' "内表里面的字段"
dynpprog = sy-repid
dynpnr = sy-dynnr
dynprofield = 'WERKS' "画面上绑定字段"
value_org = 'S'
callback_program = sy-repid
TABLES
value_tab = lt_value_tab "需要显示帮助的值内表"
return_tab = lt_return "返回值"
EXCEPTIONS
parameter_error = 1
no_values_found = 2
OTHERS = 3.
IF sy-subrc = 0.
ASSIGN p_event->m_data->* TO <lv_itab> .
READ TABLE lt_return INTO ls_return INDEX 1.
IF sy-subrc EQ 0 .
ls_modi-row_id = p_row_no-row_id.
ls_modi-fieldname = p_fieldname.
ls_modi-value = ls_return-fieldval.
APPEND ls_modi TO <lv_itab>.
ENDIF.
ENDIF.
* Inform ALV Grid that event 'onf4' has been processed
p_event->m_event_handled = 'X'.
ENDFORM. " F4_HELP_VALUE "
*&---------------------------------------------------------------------*
*& Form REFRESH_TABLE_ALV
*&---------------------------------------------------------------------*
* 设置后,alv稳定刷新
*----------------------------------------------------------------------*
FORM refresh_table_alv .
DATA: stbl TYPE lvc_s_stbl.
stbl-row = 'X'. " 基于行的稳定刷新 "
stbl-col = 'X'. " 基于列稳定刷新 "
CALL METHOD go_alv_grid->refresh_table_display
EXPORTING
is_stable = stbl.
ENDFORM. " REFRESH_TABLE_ALV "
GRID ALV
注册事件:
DATA: gt_events TYPE slis_t_event WITH HEADER LINE,
gs_event LIKE LINE OF gt_events.
DATA: go_grid TYPE REF TO cl_gui_alv_grid.
gt_events-name = 'CALLER_EXIT'. "slis_ev_caller_exit_at_start事件"
gt_events-form = 'FRM_CALLER_EXIT'.
APPEND gt_events.
CALL FUNCTION 'REUSE_ALV_GRID_DISPLAY_LVC'
EXPORTING
it_evetns = gt_evetns[].
事件功能:
*&---------------------------------------------------------------------*
*& Form FRM_CALLER_EXIT
*&---------------------------------------------------------------------*
* text
*----------------------------------------------------------------------*
* -->E_GRID text
*----------------------------------------------------------------------*
FORM frm_caller_exit USING e_grid TYPE slis_data_caller_exit.
DATA: lt_f4 TYPE lvc_t_f4,
ls_f4 TYPE lvc_s_f4.
CLEAR ls_f4.
ls_f4-fieldname = 'WERKS'. "需要定义F4帮助按钮的字段"
ls_f4-register = 'X'.
ls_f4-getbefore = 'X'.
ls_f4-chngeafter = 'X'.
INSERT ls_f4 INTO TABLE lt_f4.
"获取 OO ALV 对象"
CALL FUNCTION 'GET_GLOBALS_FROM_SLVC_FULLSCR'
IMPORTING
e_grid = go_grid.
"事件注册"
CALL METHOD go_grid->register_f4_for_fields
EXPORTING
it_f4 = lt_f4[].
"事件处理类"
CREATE OBJECT go_evt_receiver.
SET HANDLER go_evt_receiver->handle_onf4 FOR go_grid.
ENDFORM. "frm_caller_exit"
DEMO
TYPE-POOLS: slis.
*---------------------------------------------------------------------*
* CLASS lcl_event_receiver DEFINITION
*---------------------------------------------------------------------*
CLASS lcl_event_receiver DEFINITION.
PUBLIC SECTION.
CLASS-METHODS:
handle_onf4 FOR EVENT onf4 OF cl_gui_alv_grid
IMPORTING e_fieldname es_row_no er_event_data,
on_f4 FOR EVENT onf4 OF cl_gui_alv_grid
IMPORTING sender e_fieldname e_fieldvalue es_row_no
er_event_data et_bad_cells e_display,
on_data_changed FOR EVENT data_changed OF cl_gui_alv_grid
IMPORTING e_onf4 e_onf4_before e_onf4_after er_data_changed
e_ucomm sender.
PRIVATE SECTION.
TYPES: ddshretval_table TYPE TABLE OF ddshretval.
CLASS-METHODS: my_f4
IMPORTING sender TYPE REF TO cl_gui_alv_grid
et_bad_cells TYPE lvc_t_modi
es_row_no TYPE lvc_s_roid
er_event_data TYPE REF TO cl_alv_event_data
e_display TYPE c
e_fieldname TYPE lvc_fname
EXPORTING im_lt_f4 TYPE ddshretval_table.
ENDCLASS. "lcl_event_receiver DEFINITION"
*---------------------------------------------------------------------*
* CLASS lcl_event_receiver IMPLEMENTATION
*---------------------------------------------------------------------*
CLASS lcl_event_receiver IMPLEMENTATION.
METHOD handle_onf4.
DATA: ls_modi TYPE lvc_s_modi,
lt_ret_tab TYPE TABLE OF ddshretval WITH HEADER LINE.
FIELD-SYMBOLS <modtab> TYPE lvc_t_modi.
IF e_fieldname = 'FIELD_NAME'. "我们自定义搜索的字段名"
READ TABLE gt_alv_data INDEX es_row_no-row_id.
CHECK sy-subrc = 0.
** 这里可以添加代码以对lt_hitlist内表进行填充
CALL FUNCTION 'F4IF_INT_TABLE_VALUE_REQUEST'
EXPORTING
retfield = 'HIT_FIELD'
value_org = 'S'
TABLES
value_tab = lt_hitlist
return_tab = lt_ret_tab
EXCEPTIONS
parameter_error = 1
no_values_found = 2
OTHERS = 3.
IF sy-subrc = 0.
** Update the value in ALV cell
READ TABLE lt_ret_tab INDEX 1.
IF sy-subrc = 0. " User didn't cancel "
ls_modi-row_id = es_row_no-row_id.
ls_modi-fieldname = e_fieldname.
ls_modi-value = lt_ret_tab-fieldval.
ASSIGN er_event_data->m_data->* TO <modtab>.
APPEND ls_modi TO <modtab>.
ENDIF.
ENDIF.
** Inform ALV Grid that event 'onf4' has been processed
er_event_data->m_event_handled = 'X'.
ENDIF.
ENDMETHOD. "handle_onf4"
METHOD on_f4.
DATA: ls_f4 TYPE ddshretval,
lt_f4 TYPE TABLE OF ddshretval.
FIELD-SYMBOLS: <itab> TYPE lvc_t_modi.
DATA: ls_modi TYPE lvc_s_modi.
CALL METHOD my_f4
EXPORTING
sender = sender
es_row_no = es_row_no
er_event_data = er_event_data
et_bad_cells = et_bad_cells
e_display = e_display
e_fieldname = e_fieldname
IMPORTING
im_lt_f4 = lt_f4.
ASSIGN er_event_data->m_data->* TO <itab>.
READ TABLE lt_f4 INTO ls_f4 WITH KEY fieldname = 'MTART'.
IF NOT ls_f4 IS INITIAL.
ls_modi-row_id = es_row_no-row_id.
ls_modi-fieldname = 'MTART'.
ls_modi-value = ls_f4-fieldval.
APPEND ls_modi TO <itab>.
ls_modi-row_id = es_row_no-row_id.
ls_modi-fieldname = 'VALUE'.
IF ls_f4-fieldval < 'D'.
ls_modi-value = 100.
ELSEIF ls_f4-fieldval < 'R'.
ls_modi-value = 1000.
ELSE.
ls_modi-value = 10000.
ENDIF.
APPEND ls_modi TO <itab>.
ENDIF.
READ TABLE lt_f4 INTO ls_f4 WITH KEY fieldname = 'MTBEZ'.
IF NOT ls_f4 IS INITIAL.
ls_modi-row_id = es_row_no-row_id.
ls_modi-fieldname = 'MTBEZ'.
ls_modi-value = ls_f4-fieldval.
APPEND ls_modi TO <itab>.
ENDIF.
er_event_data->m_event_handled = 'X'.
ENDMETHOD. "on_f4"
*---------------------------------------------------------------------*
* METHOD on_data_changed *
*---------------------------------------------------------------------*
METHOD on_data_changed.
ENDMETHOD. "on_data_changed"
*---------------------------------------------------------------------*
* METHOD my_f4 insert here your own f4-help *
*---------------------------------------------------------------------*
METHOD my_f4.
DATA: lw_tab LIKE LINE OF gt_data,
lt_fcat TYPE lvc_t_fcat,
ls_fieldcat TYPE lvc_s_fcat,
l_tabname TYPE dd03v-tabname,
l_fieldname TYPE dd03v-fieldname,
l_help_valu TYPE help_info-fldvalue,
lt_bad_cell TYPE lvc_t_modi,
lp_wa TYPE REF TO data.
FIELD-SYMBOLS: <l_field_value> TYPE ANY,
<ls_wa> TYPE ANY.
CALL METHOD sender->get_frontend_fieldcatalog
IMPORTING
et_fieldcatalog = lt_fcat.
READ TABLE gt_data INDEX es_row_no-row_id INTO lw_tab.
CREATE DATA lp_wa LIKE LINE OF gt_data.
ASSIGN lp_wa->* TO <ls_wa>.
<ls_wa> = lw_tab.
READ TABLE lt_fcat WITH KEY fieldname = e_fieldname INTO ls_fieldcat.
MOVE ls_fieldcat-ref_table TO l_tabname.
MOVE ls_fieldcat-fieldname TO l_fieldname.
ASSIGN COMPONENT ls_fieldcat-fieldname OF STRUCTURE lw_tab TO <l_field_value>.
WRITE <l_field_value> TO l_help_valu.
PERFORM f4_set USING sender
lt_fcat
lt_bad_cell
es_row_no-row_id
<ls_wa>.
CALL FUNCTION 'F4IF_FIELD_VALUE_REQUEST'
EXPORTING
tabname = l_tabname
fieldname = l_fieldname
display = e_display
value = l_help_valu
callback_program = 'ZTEST7'
callback_form = 'F4'
TABLES
return_tab = im_lt_f4
EXCEPTIONS
parameter_error = 1
no_values_found = 2
OTHERS = 3.
ENDMETHOD. "my_f4"
ENDCLASS. "lcl_event_receiver IMPLEMENTATION"