Application Development Blog Posts
Learn and share on deeper, cross technology development topics such as integration and connectivity, automation, cloud extensibility, developing at scale, and security.
cancel
Showing results for 
Search instead for 
Did you mean: 
jrgkraus
Active Contributor

The idea



I got the idea for this when I was working with the web dynpro view editor. I noticed there was something ALV like which was used instead of a classical dynpro to enter values on several fields:

 



 

I was wondering if I could use the ALV grid control for simple input areas in my own applications.

 

The implementation


 

I created a subclass to CL_GUI_ALV_GRID to achieve this. It uses a fixed output table structure containing a column for the label, one for the value (can be editable), and one for a field description (if we input on a field with domain values).

 

At the end of this blog, you will find the coding for the sample program.

To get the program running, create a GUI status 0001 with function code END on the SHIFT+F3 button. Create also a GUI title 0001 saying "Test program" or something similar.

 

Now, if you run the program, you should see something like this:

 



 

P_RDONLY starts the input in read only mode, otherwise the edit mode is active

P_SIMPLE: in read only mode, P_SIMPLE activates a simpler display with no key coloring.

 

Edit mode screen:

 



 

The demo class LCL_APP calls the input control with the structur ADDR1_VAL. As you see, you get a complete input for this structure using the call:

 

        create object go_input
           exporting
             iv_structure_name = 'ADDR1_DATA'
             io_parent         = go_container
             iv_max_outlen     = 30
             iv_readonly       = p_rdonly
             iv_simplex        = p_simple
             iv_max_outlen_d   = 30


 

In the demo program, I used the table parameter it_fieldattr to set the first two fields to read only.

 

Reusing the code


 


If you want to reuse the coding, you should extract the following classes from the provided source. Remember to do a find/replace for the class names transforming each "LCL_ICTRL" into "ZCL_ICTRL" and "LIF_ICTRL" into "ZCL_ICTRL" in the codings to get the classes working.


 

  • lif_ictrl_input_check: This interface is useful if you want to code own input checks in your application. Implement it in your application class and pass the object reference to the main class. The interface method input_validate will be called for each input in the table. 

  • lif_ictrl_types: This interface is needed for the necessary structure and table types.

  • lcl_ictrl_alv : The main working class

  • lcx_ictrl_fatal: Exception class used in the coding


 

Comments and hints


 

Since the coding "lives" in a standard super class, I decided to use a prefix ZICTRL_ for all objects I created in order to not interfer with further inserted attributes and methods in future releases of CL_GUI_ALV_GRID.

 

The work data structure is accessed by the caller via reference. You can set the reference using method ZICTRL_SET_DATA_BY_REF. In the demo application, a structure GS_DATA is kept as an instance attribute and the ICTRL_ALV class has the reference to it. As soon as GS_DATA is changed, just call ZICTRL_REFRESH to display the new data.

 

Use case example


 

I use this class frequently. It is very good in saving space in complex dialogue applications. Here is a screenshot of a productive GUI application:

 



 

If you try to put this information on a classical dynpro, you will occupy much more space on the screen.

 

Another advantage is that this control fits much better in an OO application than classical dynpros.

 

Disadvantages


 

Unfortunately there is one problem, which I did not resolve yet: Input fields in ALV grids do not have a frontend history. In some cases, when this is very important for the users, I had to refuse using it.

 

Conclusion


 

Feel free to post your comments. Bug annotations are always welcome!

 

All the best!

Jörg

Sample program


Report source


*&---------------------------------------------------------------------*
*& Report ZP_ICTRL_DEMO
*&
*&---------------------------------------------------------------------*
*&
*&
*&---------------------------------------------------------------------*
report zp_ictrl_demo.

interface lif_ictrl_input_check.
methods input_validate
importing
iv_fieldname type dfies-lfieldname
iv_value type any
raising
cx_static_check .
endinterface.

class lcx_ictrl definition inheriting from cx_static_check.
public section.

interfaces if_t100_message.
data mv_handle type balloghndl .

methods constructor
importing
textid like textid optional
previous like previous optional
t100key type scx_t100key optional
mv_message_v1 type symsgv
mv_message_v2 type symsgv
mv_message_v3 type symsgv
mv_message_v4 type symsgv.
endclass.


interface lif_ictrl_main.

constants: cv_long_descr type char1 value 'L',
cv_medium_descr type char1 value space,
cv_short_descr type char1 value 'S'.

data: mv_readonly type abap_bool,
mr_data type ref to data,
mv_title type lvc_title,
mv_width_value type i,
mv_width_descr type i,
mo_input_check type ref to lif_ictrl_input_check,
mv_descr_len type char1.


events: user_command
exporting value(ev_ucomm) type ui_func,
enter_pressed ,
data_has_changed ,
link_clicked
exporting
value(ev_fieldname) type fieldname
value(ev_value) type any,
double_clicked
exporting
value(ev_fieldname) type fieldname
value(ev_value) type any.

methods:
set_data
changing cs_data type any
raising lcx_ictrl,
display
importing iv_optimized type abap_bool optional
raising lcx_ictrl,
set_readonly
importing iv_in type abap_bool default abap_true
raising lcx_ictrl,
hide_field
importing iv_in type lvc_fname,
show_field
importing iv_in type lvc_fname,
refresh
raising lcx_ictrl.

endinterface.

class lcl_ictrl_alv definition
inheriting from cl_gui_alv_grid
final
create public .

public section.

interfaces lif_ictrl_main.
*"* public components of class lcl_ictrl_alv
*"* do not include other source files here!!!
methods constructor
importing
io_parent type ref to cl_gui_container
iv_appl_events type abap_bool optional
raising
lcx_ictrl .

private section.

types: begin of gty_s_output,
fieldlabel type scrtext_l,
fieldvalue type text128,
fielddescr type text128,
ref_field type lvc_rfname,
ref_table type lvc_rtname,
style type lvc_style,
maxlen type int4,
t_styles type lvc_t_styl,
t_colors type lvc_t_scol,
end of gty_s_output,

gty_t_output type standard table of gty_s_output
with default key,

begin of gty_s_fieldattr,
fieldname type fieldname,
hotspot type lvc_hotspt,
readonly type crmt_bsp_readonly,
description_field type fieldname,
no_display type abap_bool,
no_label type abap_bool,
end of gty_s_fieldattr,

gty_t_fieldattr type standard table of gty_s_fieldattr
with default key.

aliases:
cv_long_descr for lif_ictrl_main~cv_long_descr,
cv_medium_descr for lif_ictrl_main~cv_medium_descr,
cv_short_descr for lif_ictrl_main~cv_short_descr,
mv_width_value for lif_ictrl_main~mv_width_value,
mv_width_descr for lif_ictrl_main~mv_width_descr,
mv_readonly for lif_ictrl_main~mv_readonly ,
mr_data for lif_ictrl_main~mr_data ,
mv_title for lif_ictrl_main~mv_title ,
mo_input_check for lif_ictrl_main~mo_input_check,
mv_descr_len for lif_ictrl_main~mv_descr_len.


data: zictrl_mv_optimized type abap_bool,
zictrl_mo_input_check type ref to lif_ictrl_input_check,
zictrl_mv_error type abap_bool,
zictrl_mt_fieldattr type gty_t_fieldattr,
zictrl_mt_fieldcat type lvc_t_fcat,
zictrl_mt_fields type dd03ttyp,
zictrl_mv_structure_name type ddobjname,
zictrl_mv_title type lvc_title,
zictrl_mt_inputs type gty_t_output.

methods:
zictrl_set_fieldattr
importing iv_fieldname type c
iv_attrib type c
iv_value type c,
zictrl_fieldcat_build,
zictrl_error
raising lcx_ictrl,
zictrl_put_log_dch
importing
io_data_changed type ref to cl_alv_changed_data_protocol
is_good type lvc_s_modi ,
zictrl_hotspot_clicked
for event hotspot_click of lcl_ictrl_alv
importing
e_row_id
e_column_id
es_row_no ,
zictrl_f4
for event onf4 of lcl_ictrl_alv
importing
e_fieldname
e_fieldvalue
es_row_no
er_event_data
et_bad_cells
e_display ,
zictrl_double_click
for event double_click of lcl_ictrl_alv
importing
e_row
e_column
es_row_no ,
zictrl_description_fill_forkey
importing
is_field type dd03p
iv_fn_d type fieldname
is_screen type any
changing
cs_input type gty_s_output ,
zictrl_description_fill
importing
is_field type dd03p
iv_value type any
changing
cs_input type gty_s_output
raising lcx_ictrl,
zictrl_after_refresh
for event after_refresh of lcl_ictrl_alv ,
zictrl_convert_input
importing
is_good type lvc_s_modi
io_data_changed type ref to cl_alv_changed_data_protocol
iv_currency type waers
is_field type dd03p
exporting
ev_value type any
ev_error type flag ,
zictrl_convert_output
importing
iv_value type any
iv_currency type waers
iv_unit type meins
returning
value(rv_res) type text128 ,
zictrl_data_changed
for event data_changed of lcl_ictrl_alv
importing
er_data_changed
e_onf4
e_onf4_before
e_onf4_after
e_ucomm ,
zictrl_screen_to_input
importing
iv_refresh type abap_bool default abap_true
raising lcx_ictrl,
zictrl_data_changed_late
for event data_changed_finished of cl_gui_alv_grid
importing
e_modified
et_good_cells ,
zictrl_get_field_ref
importing
is_field type dd03p
io_data_changed type ref to cl_alv_changed_data_protocol optional
is_screen type any
exporting
ev_curr_ref type waers
ev_unit_ref type meins ,
zictrl_input_error
importing
io_data_changed type ref to cl_alv_changed_data_protocol
is_good type lvc_s_modi ,
zictrl_set_style ,
zictrl_build_toolbar_exclude
exporting
et_tab type ui_functions ,
zictrl_input_table_create
raising
lcx_ictrl .
endclass.

class lcl_app definition.

public section.
methods main.
methods controls_init.

private section.

methods:
fill_data_from_outside
raising lcx_ictrl,
toggle_change_edit
raising lcx_ictrl,
user_command for event user_command of lif_ictrl_main
importing ev_ucomm,
hotspot for event link_clicked of lif_ictrl_main
importing ev_fieldname ev_value.

data: mo_alv type ref to lcl_ictrl_alv,
mo_container type ref to cl_gui_custom_container,
mo_input type ref to lif_ictrl_main,
ms_data type addr1_val,
mv_readonly type abap_bool.


endclass.

data: go_app type ref to lcl_app,
gv_ucomm type syucomm.

parameters: p_rdonly as checkbox.

start-of-selection.

create object go_app.
go_app->main( ).

class lcx_ictrl implementation.
method constructor.
call method super->constructor
exporting
textid = textid
previous = previous.
if_t100_message~t100key = t100key.
endmethod.
endclass.

class lcl_app implementation.

method hotspot.

field-symbols <lv_f> type any.

assign component ev_fieldname of structure ms_data to <lv_f>.

message i000(0k)
with 'Clicked on' ev_fieldname ', value' <lv_f>.

endmethod.

* method toolbar.
* data: ls_toolbar type stb_button.
*
**... Normal Button
* clear ls_toolbar.
* ls_toolbar-function = 'FILL'.
* ls_toolbar-icon = icon_generate.
* ls_toolbar-text = 'Fill data'. "#EC NOTEXT
* append ls_toolbar to e_object->mt_toolbar.
*
**... Normal Button
* clear ls_toolbar.
* ls_toolbar-function = 'EDIT_TOGGLE'.
* ls_toolbar-icon = icon_toggle_display_change.
* ls_toolbar-text = 'change/display'. "#EC NOTEXT
* append ls_toolbar to e_object->mt_toolbar.
* endmethod.

method user_command.

try.
case ev_ucomm.
when 'FILL'.
fill_data_from_outside( ).
when 'TOGGLE'.
toggle_change_edit( ).
endcase.
catch lcx_ictrl.
message 'something went wrong' type 'S' display like 'E'.
endtry.

endmethod.

method main.

" for demonstration, fill readonly fields
ms_data = value #( date_from = '20010101'
date_to = '99991231' ).

call screen 1.

endmethod.

method toggle_change_edit.

translate mv_readonly using ' XX '.

mo_input->set_readonly( mv_readonly ).
endmethod.

method fill_data_from_outside.

" fill some data
ms_data = value #( name1 = 'John Doe' title = '0002' ).
mo_input->set_data( changing cs_data = ms_data ).
" refresh the alv display
mo_input->refresh( ).

endmethod.

method controls_init.
try.
if mo_container is bound.
exit.
endif.

create object mo_container
exporting
container_name = 'CTRL_ALL'.

mo_input = new lcl_ictrl_alv( mo_container ).
mo_input->mv_readonly = p_rdonly.
mo_input->mv_width_value = 30.
mo_input->mv_width_descr = 30.

set handler user_command for mo_input.
set handler hotspot for mo_input.

mo_input->set_data( changing cs_data = ms_data ).
mo_input->display( ).

catch lcx_ictrl.
message 'FATAL ERROR' type 'E'.
endtry.

endmethod.

endclass.

class lcl_ictrl_alv implementation.

method lif_ictrl_main~hide_field.

zictrl_set_fieldattr( iv_fieldname = iv_in
iv_attrib = 'NO_DISPLAY'
iv_value = abap_true ).

endmethod.

method lif_ictrl_main~show_field.

zictrl_set_fieldattr( iv_fieldname = iv_in
iv_attrib = 'NO_DISPLAY'
iv_value = abap_false ).

endmethod.

method zictrl_set_fieldattr.
read table zictrl_mt_fieldattr assigning field-symbol(<ls_attr>)
with key fieldname = iv_fieldname.
if sy-subrc <> 0.
append value #( fieldname = iv_fieldname ) to zictrl_mt_fieldattr assigning <ls_attr>.
endif.
assign component iv_attrib of structure <ls_attr> to field-symbol(<lv_val>).
<lv_val> = iv_value.

endmethod.

method constructor.

super->constructor(
exporting
i_parent = io_parent
i_appl_events = iv_appl_events
exceptions
error_cntl_create = 1
error_cntl_init = 2
error_cntl_link = 3
error_dp_create = 4
others = 5
).

if sy-subrc <> 0.
message e000(0k) with 'ERROR creating ALV' into sy-msgli.
zictrl_error( ).

endif.

mv_width_value = 30.
mv_width_descr = 30.


set handler zictrl_data_changed for me.
set handler zictrl_data_changed_late for me.
set handler zictrl_after_refresh for me.
set handler zictrl_double_click for me.
set handler zictrl_hotspot_clicked for me.

mv_descr_len = cv_medium_descr.

register_f4_for_fields( value #( ( fieldname = 'FIELDVALUE'
getbefore = abap_true
register = abap_true
chngeafter = abap_true ) ) ).

set handler zictrl_f4 for me.
me->register_edit_event( mc_evt_enter ).

endmethod.

method lif_ictrl_main~set_data.

data(lv_init) = abap_true.

if mr_data is not initial.
assign mr_data->* to field-symbol(<ls_data>).
if cl_abap_typedescr=>describe_by_data( <ls_data> )->get_relative_name( ) <>
cl_abap_typedescr=>describe_by_data( cs_data )->get_relative_name( ).
message e000(0k) with 'invalid data structure' into sy-msgli.
zictrl_error( ).
endif.
lv_init = abap_false.
endif.

get reference of cs_data into mr_data.

if lv_init = abap_true.
zictrl_mv_structure_name = cl_abap_typedescr=>describe_by_data_ref(
mr_data )->get_relative_name( ).

zictrl_input_table_create( ).

zictrl_fieldcat_build( ).
endif.

endmethod.

method zictrl_after_refresh.
zictrl_set_style( ).
endmethod.

method zictrl_build_toolbar_exclude.

append: cl_gui_alv_grid=>mc_fc_auf to et_tab, " '&AUF', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_average to et_tab, " '&AVERAGE', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_back_classic to et_tab, " '&F03', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_abc to et_tab, " '&ABC', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_chain to et_tab, " '&BEBN', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_crbatch to et_tab, " '&CRBATCH', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_crweb to et_tab, " '&CRWEB', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_lineitems to et_tab, " '&BEB1', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_master_data to et_tab, " '&BEB2', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_more to et_tab, " '&BEB3', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_report to et_tab, " '&BEB9', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_xint to et_tab, " '&XINT', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_call_xxl to et_tab, " '&XXL', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_check to et_tab, " '&CHECK', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_col_invisible to et_tab, " '&COL_INV', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_col_optimize to et_tab, " '&OPTIMIZE', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_count to et_tab, " '&COUNT', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_current_variant to et_tab, " '&COL0', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_data_save to et_tab, " '&DATA_SAVE', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_delete_filter to et_tab, " '&DELETE_FILTER', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_deselect_all to et_tab, " '&SAL', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_detail to et_tab, " '&DETAIL', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_excl_all to et_tab, " '&EXCLALLFC', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_expcrdata to et_tab, " '&CRDATA', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_expcrdesig to et_tab, " '&CRDESIG', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_expcrtempl to et_tab, " '&CRTEMPL', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_expmdb to et_tab, " '&MDB', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_extend to et_tab, " '&EXT', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_f4 to et_tab, " '&F4', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_filter to et_tab, " '&FILTER', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_find to et_tab, " '&FIND', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_fix_columns to et_tab, " '&CFI', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_graph to et_tab, " '&GRAPH', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_help to et_tab, " '&HELP', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_html to et_tab, " '&HTML', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_info to et_tab, " '&INFO', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_load_variant to et_tab, " '&LOAD', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_append_row to et_tab, " '&LOCAL&', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_copy to et_tab, " '&LOCAL&COPY', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_copy_row to et_tab, " '&LOCAL&COPY_ROW', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_cut to et_tab, " '&LOCAL&CUT', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_delete_row to et_tab, " '&LOCAL&DELETE_ROW', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_insert_row to et_tab, " '&LOCAL&INSERT_ROW', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_move_row to et_tab, " '&LOCAL&MOVE_ROW', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_paste to et_tab, " '&LOCAL&PASTE', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_paste_new_row to et_tab, " '&LOCAL&PASTE_NEW_ROW', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_loc_undo to et_tab, " '&LOCAL&UNDO', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_maintain_variant to et_tab, " '&MAINTAIN', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_maximum to et_tab, " '&MAXIMUM', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_minimum to et_tab, " '&MINIMUM', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_pc_file to et_tab, " '&PC', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_print to et_tab, " '&PRINT', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_print_back to et_tab, " '&PRINT_BACK', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_print_prev to et_tab, " '&PRINT_BACK_PREVIEW', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_refresh to et_tab, " '&REFRESH', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_reprep to et_tab, " '&REPREP', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_save_variant to et_tab, " '&SAVE', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_select_all to et_tab, " '&ALL', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_send to et_tab, " '&SEND', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_separator to et_tab, " '&&SEP', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_sort to et_tab, " '&SORT', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_sort_asc to et_tab, " '&SORT_ASC', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_sort_dsc to et_tab, " '&SORT_DSC', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_subtot to et_tab, " '&SUBTOT', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_sum to et_tab, " '&SUMC', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_to_office to et_tab, " '&ML', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_to_rep_tree to et_tab, " '&SERP', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_unfix_columns to et_tab, " '&CDF', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_url_copy_to_clipboard to et_tab, " '&URL_COPY_TO_CLIPBOARD', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_variant_admin to et_tab, " '&VARI_ADMIN', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_views to et_tab, " '&VIEW', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_view_crystal to et_tab, " '&VCRYSTAL', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_view_excel to et_tab, " '&VEXCEL', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_view_grid to et_tab, " '&VGRID', "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_view_lotus to et_tab, " '&VLOTUS'. "#EC NOTEXT
cl_gui_alv_grid=>mc_fc_word_processor to et_tab. " '&AQW'. "#EC NOTEXT


endmethod.

method zictrl_convert_input.
data ls_tabfield type tabfield.
ls_tabfield-tabname = zictrl_mv_structure_name.
ls_tabfield-fieldname = is_field-fieldname.

call function 'RS_CONV_EX_2_IN'
exporting
input_external = is_good-value
table_field = ls_tabfield
currency = iv_currency
* NO_TCURX = ' '
importing
output_internal = ev_value
exceptions
input_not_numerical = 1
too_many_decimals = 2
more_than_one_sign = 3
ill_thousand_separator_dist = 4
too_many_digits = 5
sign_for_unsigned = 6
too_large = 7
too_small = 8
invalid_date_format = 9
invalid_date = 10
invalid_time_format = 11
invalid_time = 12
invalid_hex_digit = 13
unexpected_error = 14
invalid_fieldname = 15
field_and_descr_incompatible = 16
input_too_long = 17
no_decimals = 18
invalid_float = 19
conversion_exit_error = 20
others = 21.
if sy-subrc <> 0.
zictrl_input_error( io_data_changed = io_data_changed is_good = is_good ).
ev_error = abap_true.
endif.
endmethod.

method zictrl_convert_output.
if iv_currency is not initial.
write iv_value to rv_res currency iv_currency.
elseif iv_unit is not initial.
write iv_value to rv_res unit iv_unit.
else.
write iv_value to rv_res.
endif.
condense rv_res.
endmethod.

method zictrl_data_changed.
data: ls_good type lvc_s_modi,
lv_error_in_data type flag,
lv_row_id type int4,
ls_fail type ddfkeyrc,
lt_fail type table of ddfkeyrc,
lv_fn type dfies-lfieldname,
ls_fieldattr_group type gty_s_fieldattr,
ls_fieldattr type gty_s_fieldattr,
lv_value type text128,
lv_curr_ref type waers,
lv_unit_ref type meins.
field-symbols <ls_screen> type any.
field-symbols <ls_input> type gty_s_output.
field-symbols <ls_input_ref> type gty_s_output.
field-symbols <ls_field> type dd03p.
field-symbols <lv_value> type any.
field-symbols <lv_value_group> type any.

assign mr_data->* to <ls_screen>.

lv_error_in_data = space.
zictrl_mv_error = abap_false.
loop at er_data_changed->mt_good_cells into ls_good.

read table zictrl_mt_inputs assigning <ls_input> index ls_good-row_id.
read table zictrl_mt_fields assigning <ls_field> with key fieldname = <ls_input>-ref_field.
assign component <ls_field>-fieldname of structure <ls_screen> to <lv_value>.
read table zictrl_mt_fieldattr into ls_fieldattr with key fieldname = <ls_input>-ref_field.

zictrl_get_field_ref(
exporting
is_field = <ls_field> " DD-Schnittstelle: Tabellenfelder für DDIF_FIELDINFO_GET
* io_data_changed = " Message Protokoll für Dataentry
is_screen = <ls_screen>
importing
ev_curr_ref = lv_curr_ref " Währungsschlüssel
ev_unit_ref = lv_unit_ref " Basismengeneinheit
).

zictrl_convert_input(
exporting
is_good = ls_good
io_data_changed = er_data_changed
iv_currency = lv_curr_ref
is_field = <ls_field>
importing
ev_value = <lv_value>
ev_error = lv_error_in_data
).
if lv_error_in_data = abap_false.
lv_fn = <ls_field>-fieldname.
call function 'DDUT_INPUT_CHECK'
exporting
tabname = <ls_field>-tabname
fieldname = lv_fn
value_list = <ls_screen>
value = <lv_value>
importing
msgid = sy-msgid " ggf. Nachrichtenklasse der Fehlermeldung
msgty = sy-msgty " ggf. Schwere der Fehlermeldung
msgno = sy-msgno " ggf. Nummer der Fehlermeldung
msgv1 = sy-msgv1 " ggf. erster Parameter für die Fehlermeldung
msgv2 = sy-msgv2 " ggf. zweiter Parameter für die Fehlermeldung
msgv3 = sy-msgv3 " ggf. dritter Parameter für die Fehlermeldung
msgv4 = sy-msgv4 " ggf. vierter Parameter für die Fehlermeldung
value_internal = <lv_value>
exceptions
forkey_not_defined = 1
table_not_active = 2
field_unknown = 3
others = 4.

if sy-msgty ca 'EAF'.
zictrl_put_log_dch( io_data_changed = er_data_changed is_good = ls_good ).
lv_error_in_data = abap_true.
endif.

if zictrl_mo_input_check is bound.
try.
zictrl_mo_input_check->input_validate(
iv_fieldname = lv_fn
iv_value = <lv_value> ).
catch cx_static_check.
zictrl_put_log_dch( io_data_changed = er_data_changed is_good = ls_good ).
lv_error_in_data = abap_true.
endtry.
endif.
endif.

endloop.

* §7.Display application log if an error has occured.
if lv_error_in_data = abap_true.
zictrl_mv_error = abap_true.
call method er_data_changed->display_protocol.
endif.
endmethod.

method zictrl_data_changed_late.

check zictrl_mv_error = abap_false.
try.
if e_modified = abap_true.

zictrl_screen_to_input( ).

raise event lif_ictrl_main~data_has_changed.
clear m_eventid.

else.
if m_eventid = evt_enter.
data lo_control type ref to cl_gui_control.
cl_gui_control=>get_focus(
importing
control = lo_control " Control
exceptions
cntl_error = 1
cntl_system_error = 2
others = 3
).
if sy-subrc = 0.
if lo_control = me.
raise event lif_ictrl_main~enter_pressed.
endif.
endif.
endif.
endif.
catch lcx_ictrl into data(lo_err).
endtry.
endmethod.

method zictrl_screen_to_input.
field-symbols: <lv_value_screen> type any,
<ls_field_refd> type dd03p,
<ls_field> type dd03p,
<ls_input> type gty_s_output,
<ls_input_refd> type gty_s_output,
<lv_value_out> type any,
<ls_screen> type any,
<ls_fa> type gty_s_fieldattr.
data: ls_good type lvc_s_modi,
lv_curr_ref type waers,
lv_unit_ref type meins,
lr_value_out type ref to data,
lv_value type text128,
ls_stable type lvc_s_stbl.

assign mr_data->* to <ls_screen>.

loop at zictrl_mt_fields assigning <ls_field>.

read table zictrl_mt_inputs assigning <ls_input> with key ref_field = <ls_field>-fieldname.
check sy-subrc = 0.
assign component <ls_field>-fieldname of structure <ls_screen> to <lv_value_screen>.
check sy-subrc = 0.

create data lr_value_out like <lv_value_screen>.
assign lr_value_out->* to <lv_value_out>.

<lv_value_out> = <lv_value_screen>.

zictrl_get_field_ref(
exporting
is_field = <ls_field> " DD-Schnittstelle: Tabellenfelder für DDIF_FIELDINFO_GET
* io_data_changed = " Message Protokoll für Dataentry
is_screen = <ls_screen>
importing
ev_curr_ref = lv_curr_ref " Währungsschlüssel
ev_unit_ref = lv_unit_ref " Basismengeneinheit
).

case <ls_field>-datatype.

when 'CURR'.
write <lv_value_out> currency lv_curr_ref to <ls_input>-fieldvalue.

when 'QUAN'.
write <lv_value_out> unit lv_unit_ref to <ls_input>-fieldvalue.

when others.
write <lv_value_out> unit lv_unit_ref to <ls_input>-fieldvalue.
endcase.
shift <ls_input>-fieldvalue left deleting leading space.

if mv_width_descr > 0 and
<ls_field>-domname <> 'XFELD'.
zictrl_description_fill( exporting is_field = <ls_field>
iv_value = <lv_value_screen>
changing cs_input = <ls_input> ).

read table zictrl_mt_fieldattr assigning <ls_fa> with key
fieldname = <ls_field>-fieldname.
if sy-subrc = 0.
if <ls_fa>-description_field is not initial.
zictrl_description_fill_forkey(
exporting is_field = <ls_field>
iv_fn_d = <ls_fa>-description_field
is_screen = <ls_screen>
changing cs_input = <ls_input> ).
endif.
endif.
endif.
endloop.

if iv_refresh = abap_true.
ls_stable-row = abap_true.
ls_stable-col = abap_true.

if zictrl_mv_optimized = abap_true.

data ls_layo type lvc_s_layo.
get_frontend_layout(
importing
es_layout = ls_layo " Layout
).

ls_layo-cwidth_opt = abap_true.

set_frontend_layout( ls_layo ).
endif.
refresh_table_display(
exporting
is_stable = ls_stable " zeilen-/spaltenstabil
i_soft_refresh = abap_true " Ohne Sortierung, Filter, etc.
).
endif.
endmethod.

method zictrl_description_fill.
data: lv_desc type string.
* local data
data:
lo_typedescr type ref to cl_abap_elemdescr,
ls_flddescr type dfies,
lt_values type dd07v_tab.
* get type description of field!
lo_typedescr ?= cl_abap_elemdescr=>describe_by_data( iv_value ).

assert lo_typedescr is bound.
* must be a DDIC object!!
if lo_typedescr->is_ddic_type( ) = abap_false.
return.
endif.

ls_flddescr = lo_typedescr->get_ddic_field( ).
* get name of domain

call function 'DDUT_DOMVALUES_GET'
exporting
name = ls_flddescr-domname
langu = sy-langu
texts_only = abap_false
tables
dd07v_tab = lt_values
exceptions
illegal_input = 1
others = 2.
if sy-subrc <> 0.
return.
endif.

read table lt_values assigning field-symbol(<ls_value>)
with key domvalue_l = iv_value.
if sy-subrc = 0.
cs_input-fielddescr = <ls_value>-ddtext.
endif.
endmethod.

method zictrl_description_fill_forkey.

data: lt_cond_tab type table of ddwherecnd,
lt_selection type table of char200,
lt_t type table of ddwherecnd-checktable,
lr_data type ref to data,
lt_fail type table of ddfkeyrc.
field-symbols: <ls_struc> type any,
<lv_result> type any.

check is_field-checktable is not initial.
clear cs_input-fielddescr.
check not cs_input-fieldvalue = space.

call function 'DDUT_FORKEY_CHECK'
exporting
tabname = is_field-tabname
fieldname = is_field-fieldname
value_list = is_screen
tables
cond_tab = lt_cond_tab
failure_tab = lt_fail.

check lt_fail is initial.

loop at lt_cond_tab assigning field-symbol(<ls_cond>).
append <ls_cond>-line to lt_selection.
collect <ls_cond>-checktable into lt_t.
endloop.

if lt_selection is not initial and lines( lt_t ) = 1.

create data lr_data type (is_field-checktable).
assign lr_data->* to <ls_struc>.

select single * from (is_field-checktable) into <ls_struc> where (lt_selection).

assign component iv_fn_d of structure <ls_struc>
to <lv_result>.

cs_input-fielddescr = <lv_result>.
endif.
endmethod.

method lif_ictrl_main~display.

data ls_layout type lvc_s_layo.
data lt_toolbar_exclude type ui_functions.

ls_layout = value #( edit = cond #( when mv_readonly = abap_false then abap_true )
stylefname = cond #( when mv_readonly = abap_false then 'T_STYLES' )
no_headers = abap_true
sel_mode = 'A'
no_rowins = abap_true
no_rowmark = abap_true
grid_title = zictrl_mv_title
smalltitle = abap_true
ctab_fname = 'T_COLORS'
cwidth_opt = iv_optimized ).

zictrl_mv_optimized = iv_optimized.

zictrl_screen_to_input( abap_false ).

zictrl_build_toolbar_exclude( importing et_tab = lt_toolbar_exclude ).

set_table_for_first_display(
exporting
is_layout = ls_layout " Layout
it_toolbar_excluding = lt_toolbar_exclude " excludierte Toolbarstandardfunktionen
changing
it_outtab = zictrl_mt_inputs " Ausgabetabelle
it_fieldcatalog = zictrl_mt_fieldcat " Feldkatalog
exceptions
invalid_parameter_combination = 1
program_error = 2
too_many_lines = 3
others = 4
).
if sy-subrc <> 0.
message e000(0k) with 'ERROR displaying table' into sy-msgli.
zictrl_error( ).
endif.

endmethod.

method zictrl_double_click.

assign mr_data->* to field-symbol(<ls_screen>).

read table zictrl_mt_inputs assigning field-symbol(<ls_input>) index es_row_no-row_id.
check sy-subrc = 0.
assign component <ls_input>-ref_field of structure <ls_screen> to field-symbol(<lv_value>).
check sy-subrc = 0.

raise event lif_ictrl_main~double_clicked exporting
ev_fieldname = <ls_input>-ref_field
ev_value = <lv_value>.

endmethod.

method zictrl_f4.

data lt_return type hrreturn_tab.
field-symbols <lt_modcell> type lvc_t_modi.

read table zictrl_mt_inputs assigning field-symbol(<ls_input>) index es_row_no-row_id.

call function 'F4IF_FIELD_VALUE_REQUEST'
exporting
tabname = <ls_input>-ref_table
fieldname = <ls_input>-ref_field
tables
return_tab = lt_return.

read table lt_return assigning field-symbol(<ls_return>) index 1.
if sy-subrc <> 0.
assign er_event_data->m_data->* to <lt_modcell>.
append initial line to <lt_modcell> assigning field-symbol(<ls_modcell>).
<ls_modcell>-row_id = es_row_no-row_id.
<ls_modcell>-fieldname = e_fieldname.
<ls_modcell>-value = <ls_return>-fieldval.
endif.

er_event_data->m_event_handled = abap_true.

endmethod.

method zictrl_fieldcat_build.

clear zictrl_mt_fieldcat.

zictrl_mt_fieldcat =
value #( ( fieldname = 'FIELDLABEL'
rollname = 'SCRTEXT_L'
key = abap_true
outputlen = 15
style = mc_style_disabled )
( fieldname = 'FIELDVALUE'
rollname = 'TEXT128'
edit = cond #( when mv_readonly = abap_false then abap_true )
outputlen = mv_width_value )
( fieldname = 'FIELDDESCR'
rollname = 'TEXT128'
outputlen = mv_width_descr
style = mc_style_disabled ) ).
endmethod.

method zictrl_get_field_ref.
field-symbols <lv_value_ref> type c.
data lr_ref type ref to data.

clear: ev_curr_ref, ev_unit_ref.

if is_field-reftable = is_field-tabname.
if is_field-reffield is not initial.
read table zictrl_mt_fields assigning field-symbol(<ls_field_ref>)
with key fieldname = is_field-reffield.
if sy-subrc = 0.
create data lr_ref type (<ls_field_ref>-rollname).
assign lr_ref->* to <lv_value_ref>.
if io_data_changed is bound.
read table io_data_changed->mt_good_cells assigning field-symbol(<ls_good>) with key
fieldname = <ls_field_ref>-fieldname.
if sy-subrc = 0.
create data lr_ref type (<ls_field_ref>-rollname).
assign lr_ref->* to <lv_value_ref>.
<lv_value_ref> = <ls_good>-value.
else.
assign component <ls_field_ref>-fieldname of structure is_screen to <lv_value_ref>.
endif.
else.
assign component <ls_field_ref>-fieldname of structure is_screen to <lv_value_ref>.
endif.

if <ls_field_ref>-datatype = 'CUKY'.
ev_curr_ref = <lv_value_ref>.
elseif <ls_field_ref>-datatype = 'UNIT'.
ev_unit_ref = <lv_value_ref>.
endif.
endif.

endif.
endif.
endmethod.

method zictrl_hotspot_clicked.
field-symbols <ls_screen> type any.
field-symbols <lv_value> type any.

assign mr_data->* to <ls_screen>.

read table zictrl_mt_inputs assigning field-symbol(<ls_input>) index es_row_no-row_id.
check sy-subrc = 0.
assign component <ls_input>-ref_field of structure <ls_screen> to <lv_value>.
check sy-subrc = 0.

raise event lif_ictrl_main~link_clicked exporting
ev_fieldname = <ls_input>-ref_field
ev_value = <lv_value>.

endmethod.

method zictrl_input_error.
call method io_data_changed->add_protocol_entry
exporting
i_msgid = sy-msgid
i_msgno = sy-msgno
i_msgty = sy-msgty
i_msgv1 = sy-msgv1 "Flugzeugtyp
i_msgv2 = sy-msgv2 "Flugzeugtyp
i_msgv3 = sy-msgv3 "Flugzeugtyp
i_msgv4 = sy-msgv4 "Flugzeugtyp
i_fieldname = is_good-fieldname
i_row_id = is_good-row_id.
endmethod.

method zictrl_input_table_create.

data: ls_style type lvc_s_styl,
ls_scol type lvc_s_scol,
lt_domvalues type dd07v_tab.

clear zictrl_mt_inputs.

* get default field list
call function 'DDIF_TABL_GET'
exporting
name = zictrl_mv_structure_name
state = 'A'
langu = sy-langu
tables
dd03p_tab = zictrl_mt_fields
exceptions
illegal_input = 1
others = 2.

if sy-subrc <> 0.
message id sy-msgid type sy-msgty number sy-msgno
with sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4 into sy-msgli.
zictrl_error( ).
endif.

delete zictrl_mt_fields where fieldname = '.INCLUDE'.

loop at zictrl_mt_fields assigning field-symbol(<ls_field>).
if <ls_field>-scrtext_l = space.
<ls_field>-scrtext_l = cond #( when <ls_field>-scrtext_m <> space
then <ls_field>-scrtext_m
else <ls_field>-scrtext_s ).
endif.
if <ls_field>-scrtext_m = space.
<ls_field>-scrtext_m = cond #( when <ls_field>-scrtext_s <> space
then <ls_field>-scrtext_s
else <ls_field>-scrtext_l ).
endif.
if <ls_field>-scrtext_s = space.
<ls_field>-scrtext_s = <ls_field>-scrtext_m .
endif.

try.
data(ls_at) = zictrl_mt_fieldattr[ fieldname = <ls_field>-fieldname ].
catch cx_sy_itab_line_not_found.
clear ls_at.
endtry.
if ls_at-no_display = abap_true.
continue.
endif.

append value #( fieldlabel =
cond #( when ls_at-no_label = abap_false then
switch #(
mv_descr_len
when cv_long_descr then <ls_field>-scrtext_l
when cv_medium_descr then <ls_field>-scrtext_m
when cv_short_descr then <ls_field>-scrtext_s
)
)
ref_field = <ls_field>-fieldname
ref_table = <ls_field>-tabname
t_styles =
cond #( when mv_readonly = abap_false
then value #( ( fieldname = 'FIELDLABEL'
style = mc_style_disabled )
( fieldname = 'FIELDDESCR'
style = mc_style_disabled ) )
)
) to zictrl_mt_inputs
assigning field-symbol(<ls_input>).

call function 'DDUT_DOMVALUES_GET'
exporting
name = <ls_field>-domname
langu = sy-langu
texts_only = abap_true
tables
dd07v_tab = lt_domvalues
exceptions
illegal_input = 1
others = 2.
if sy-subrc <> 0.
return.
endif.

if ( <ls_field>-shlpname is not initial or
lt_domvalues is not initial or
<ls_field>-checktable is not initial or
<ls_field>-datatype = 'DATS' or
<ls_field>-datatype = 'TIMS' ) and
<ls_field>-domname <> 'XFELD' and
mv_readonly = abap_false and
ls_at-readonly = abap_false.
insert value #( fieldname = 'FIELDVALUE' style = mc_style_f4 )
into table <ls_input>-t_styles.
endif.


if <ls_field>-outputlen > mv_width_value.
mv_width_value = <ls_field>-outputlen.
endif.

insert value #(
color = value #(
col = cond #( when mv_readonly = abap_true
then col_key
else col_normal ) )
fname = 'FIELDLABEL' )
into table <ls_input>-t_colors.

if ls_at-readonly = abap_true or
mv_readonly = abap_true.
insert value #( color = value #( col = col_normal )
fname = 'FIELDVALUE' )
into table <ls_input>-t_colors.
endif.
endloop.

endmethod.

method zictrl_put_log_dch.
io_data_changed->add_protocol_entry(
exporting
i_msgid = sy-msgid " Message ID
i_msgty = sy-msgty " Message Typ
i_msgno = sy-msgno " Message Nr.
i_msgv1 = sy-msgv1 " Messagevariable1
i_msgv2 = sy-msgv2 " Messagevariable2
i_msgv3 = sy-msgv3 " Messagevariable3
i_msgv4 = sy-msgv4 " Messagevariable4
i_fieldname = 'FIELDVALUE' " Feldname
i_row_id = is_good-row_id " RowID
).
endmethod.

method zictrl_error.

raise exception type lcx_ictrl
exporting
t100key = value #( msgid = sy-msgid
msgno = sy-msgno
attr1 = 'MV_MESSAGE_V1'
attr2 = 'MV_MESSAGE_V2'
attr3 = 'MV_MESSAGE_V3'
attr4 = 'MV_MESSAGE_V4' )
mv_message_v1 = sy-msgv1
mv_message_v2 = sy-msgv2
mv_message_v3 = sy-msgv3
mv_message_v4 = sy-msgv4.

endmethod.

method lif_ictrl_main~refresh.

zictrl_screen_to_input( ).

endmethod.

method lif_ictrl_main~set_readonly.

mv_readonly = iv_in.
zictrl_fieldcat_build( ).
zictrl_input_table_create( ).

lif_ictrl_main~display( ).
endmethod.

method zictrl_set_style.

include <cl_alv_control>.

field-symbols <ls_field> type dd03p.
data ls_inputs type gty_s_output.
data ls_fieldattr type gty_s_fieldattr.
*
data lv_checkbox type recabool.

loop at mt_data assigning field-symbol(<ls_data>).

if <ls_data>-col_pos = 1.
clear lv_checkbox.
read table zictrl_mt_inputs into ls_inputs index <ls_data>-row_pos.
read table zictrl_mt_fields assigning <ls_field> with key fieldname = ls_inputs-ref_field.
clear ls_fieldattr.
read table zictrl_mt_fieldattr into ls_fieldattr with key fieldname = <ls_field>-fieldname.
if <ls_field>-domname = 'XFELD'.
lv_checkbox = abap_true.
endif.

endif.

if <ls_data>-col_pos = 2.
if lv_checkbox = abap_true.
if <ls_data>-value = abap_true.
<ls_data>-style = alv_style_checkbox_checked.
else.
<ls_data>-style = alv_style_checkbox_not_checked.
endif.
endif.
if ls_fieldattr-readonly = abap_true and mv_readonly = abap_false..
<ls_data>-style = <ls_data>-style + alv_style_disabled.
endif.
if ls_fieldattr-hotspot = abap_true.
<ls_data>-style = <ls_data>-style + alv_style_single_clk_event.
endif.
endif.
endloop.
***************
call method me->set_data_table
changing
data_table = mt_data[].
call method set_auto_redraw
exporting
enable = 1.

endmethod.

endclass.

module status_0001 output.

go_app->controls_init( ).
set pf-status '0001'.
set titlebar '0001'.

endmodule. " STATUS_0001 OUTPUT

module user_command_0001 input.

if gv_ucomm = 'END'.
set screen 0.
leave screen.
endif.

endmodule. " USER_COMMAND_0001 INPUT

Dynpro source


****************************************************************																																
* THIS FILE IS GENERATED BY THE SCREEN PAINTER. *
* NEVER CHANGE IT MANUALLY, PLEASE ! *
****************************************************************
%_DYNPRO
ZP_ICTRL_DEMO
0001
740
40
%_HEADER
ZP_ICTRL_DEMO 0001 0001 27120192 37 0 0 27120 0G E 20160806110017
%_DESCRIPTION
Träger für ALV-Eingabemaske
%_FIELDS
CTRL_ALL 120 00 00 00 30 00 1 2 0 0 0 27 U 1 1 101
GV_UCOMM CHAR 20 80 10 00 00 00 255 1 O 0 0 0 0 0 0 ____________________ 00
%_FLOWLOGIC
PROCESS BEFORE OUTPUT.
MODULE STATUS_0001.
*
PROCESS AFTER INPUT.
MODULE USER_COMMAND_0001.
%_PARAMS


2 Comments