This program lets the user select which fields to extract from a given object (ie Customer or Vendor data), creates an internal table based on the selected fields, picks up the data from the database into the dynamic internal table and outputs it to either screen (ALV list) or a .csv file on the fileserver. If the user has selected data before, the previous selection is shown on the popup screen.
The code was written in version 4.6C.
Code
REPORT zzzhlp_dyn_tabc MESSAGE-ID z1.
* short version ! For full version contact...
* Programmer: Henrik Lang Petersen, ECsoft Danmark A/S
* COMMENTS ARE WELCOME !: henrik_lang@hotmail.com
*
* The program let the user select which fields to extract from a given
* type (ie Customer or Vendor data).
* First action on selection screen is to choose Customer or vendor data,
* The list is output to screen (ALV list)
* Fill in if there is any restrictions on company code/vendor/customer
*
* Secondly a popup screen is shown with all possible fields.
* Fields can now be deselected or selected, and sort order changed by
* entering an appropriate number in the SORT field.
TYPE-POOLS: slis.
TABLES: dd03vt, "Table/field info
kna1, "Customer
knb1,
lfa1, "Vendor
lfb1.
* gt_out_tab_type fields on screen popup
TYPES: BEGIN OF gt_out_tab_type,
check(1) TYPE c,
sortering(4) type n,
tabname LIKE dd03vt-tabname,
fieldname LIKE dd03vt-fieldname,
ddtext LIKE dd03vt-ddtext,
inttype LIKE dd03vt-inttype,
intlen LIKE dd03vt-intlen,
END OF gt_out_tab_type.
* For headings in the extract file
TYPES: BEGIN OF gt_header_type,
overskrift(20) TYPE c,
END OF gt_header_type.
* For ALV liste output.
TYPES: BEGIN OF gt_alv_type,
f1(35) TYPE c, f2(35) TYPE c, f3(35) TYPE c,
f4(35) TYPE c, f5(35) TYPE c, f6(35) TYPE c,
f7(35) TYPE c, f8(35) TYPE c, f9(35) TYPE c,
f10(35) TYPE c, f11(35) TYPE c, f12(35) TYPE c,
f13(35) TYPE c, f14(35) TYPE c, f15(35) TYPE c,
f16(35) TYPE c, f17(35) TYPE c, f18(35) TYPE c,
f19(35) TYPE c, f20(35) TYPE c, f21(35) TYPE c,
f22(35) TYPE c, f23(35) TYPE c, f24(35) TYPE c,
f25(35) TYPE c, f26(35) TYPE c, f27(35) TYPE c,
f28(35) TYPE c, f29(35) TYPE c, f30(35) TYPE c,
END OF gt_alv_type.
* Work fields/tables
DATA:
t_vf TYPE gt_out_tab_type OCCURS 0 WITH HEADER LINE,
t_header TYPE gt_header_type OCCURS 0 WITH HEADER LINE,
t_alv_liste TYPE gt_alv_type OCCURS 0 WITH HEADER LINE,
lt_alv_cat TYPE TABLE OF lvc_s_fcat,
ls_alv_cat LIKE LINE OF lt_alv_cat,
gt_field_catalog TYPE slis_t_fieldcat_alv, "Field catalog
gs_private TYPE slis_data_caller_exit,
gs_selfield TYPE slis_selfield,
g_lines TYPE i,
g_exit(1) TYPE c.
* For dynamic generation of table
FIELD-SYMBOLS: <l_table> TYPE ANY TABLE,
<l_line> TYPE ANY,
<l_field> TYPE ANY.
DATA: new_table TYPE REF TO data,
new_line TYPE REF TO data.
PARAMETERS:
* Customer output
p_custom RADIOBUTTON GROUP g1
DEFAULT 'X',
* Vendor output
p_vendor RADIOBUTTON GROUP g1.
SELECT-OPTIONS:
s_kunnr FOR kna1-kunnr MODIF ID k,
s_lifnr FOR lfa1-lifnr MODIF ID l,
s_bukrs FOR knb1-bukrs.
START-OF-SELECTION.
PERFORM initialise_fields.
PERFORM find_fields_for_extract.
* Build dynamic table
PERFORM build_internal_table.
* Load data i dynamisk tabel
CASE 'X'.
WHEN p_custom.
PERFORM get_customer_data.
WHEN p_vendor.
PERFORM get_vendor_data.
ENDCASE.
PERFORM show_alv_list.
**** FORMS ********
FORM find_fields_for_extract.
* Create table with fields to choose from
DATA: l_fields TYPE STANDARD TABLE OF pch01_fieldlist_wa,
wa_fields TYPE pch01_fieldlist_wa,
l_index TYPE pch01_idxlist,
wa_index TYPE pch01_idxlist_wa,
l_sort_count TYPE i.
* Get fields from data dictionary
PERFORM get_fields_dd03vt.
* Create field catalog for ALV popup
PERFORM build_field_catalog.
* Show extracted fields in PopUp - Receive selected fields
CALL FUNCTION 'REUSE_ALV_POPUP_TO_SELECT'
EXPORTING
i_title = 'Choose fields for extract'
i_checkbox_fieldname = 'CHECK'
i_tabname = '0'
it_fieldcat = gt_field_catalog
is_private = gs_private
IMPORTING
es_selfield = gs_selfield
e_exit = g_exit
TABLES
t_outtab = t_vf
EXCEPTIONS
program_error = 1
OTHERS = 2.
IF sy-subrc <> 0.
MESSAGE i000(0k) WITH sy-subrc.
ENDIF.
* Get the selected fields (check = 'X')
LOOP AT t_vf WHERE check = 'X'.
IF t_vf-sortering = '0000'.
t_vf-sortering = '9999'.
MODIFY t_vf.
ENDIF.
ENDLOOP.
SORT t_vf BY sortering. CLEAR l_sort_count.
* Take the fields which were selected by the user
LOOP AT t_vf WHERE check = 'X' OR sortering <> 0.
ls_alv_cat-fieldname = t_vf-fieldname .
ls_alv_cat-ref_table = t_vf-tabname.
ls_alv_cat-ref_field = t_vf-fieldname .
APPEND ls_alv_cat TO lt_alv_cat.
* Heading for the fields is extracted
t_header-overskrift = t_vf-ddtext(15).
APPEND t_header.
ENDLOOP.
ENDFORM.
FORM build_internal_table.
* Field catalog with the fields the user selected, used as input
CALL METHOD cl_alv_table_create=>create_dynamic_table
EXPORTING
it_fieldcatalog = lt_alv_cat
IMPORTING
ep_table = new_table.
* Create ref to the newly generated table <l_table>
* Plus a new Line with the same structure as the table.
ASSIGN new_table->* TO <l_table>.
CREATE DATA new_line LIKE LINE OF <l_table>.
ASSIGN new_line->* TO <l_line>.
ENDFORM.
* Which fields goes on screen, in what order...
FORM build_field_catalog.
DATA: ls_field_catalog TYPE slis_fieldcat_alv. "Field catalog line
CLEAR gt_field_catalog.
REFRESH gt_field_catalog.
* Definition for Checkbox.
CLEAR ls_field_catalog.
ls_field_catalog-fieldname = 'CHECK'.
ls_field_catalog-inttype = 'C'.
ls_field_catalog-outputlen = 1.
ls_field_catalog-no_out = 'X'.
ls_field_catalog-seltext_l = 'Checkbox'.
INSERT ls_field_catalog INTO TABLE gt_field_catalog.
* Input field if you want to make sorting by entering
* sort key manually (numc field 4 digits)
CLEAR ls_field_catalog.
ls_field_catalog-fieldname = 'SORTERING'.
ls_field_catalog-inttype = 'N'.
ls_field_catalog-outputlen = 4.
ls_field_catalog-input = 'X'.
ls_field_catalog-seltext_l = 'Sortering'.
INSERT ls_field_catalog INTO TABLE gt_field_catalog.
CLEAR ls_field_catalog.
ls_field_catalog-fieldname = 'FIELDNAME'.
ls_field_catalog-inttype = 'C'.
ls_field_catalog-outputlen = 20.
ls_field_catalog-seltext_l = 'Feltnavn'.
INSERT ls_field_catalog INTO TABLE gt_field_catalog.
CLEAR ls_field_catalog.
ls_field_catalog-fieldname = 'TABNAME'.
ls_field_catalog-inttype = 'C'.
ls_field_catalog-outputlen = 8.
ls_field_catalog-seltext_l = 'Tabelnavn'.
INSERT ls_field_catalog INTO TABLE gt_field_catalog.
CLEAR ls_field_catalog.
ls_field_catalog-fieldname = 'DDTEXT'.
ls_field_catalog-inttype = 'C'.
ls_field_catalog-outputlen = 45.
ls_field_catalog-seltext_l = 'Feltbeskrivelse'.
INSERT ls_field_catalog INTO TABLE gt_field_catalog.
ENDFORM. "build_fieldcatalog
FORM get_fields_dd03vt.
* Read fieldnames in dd03vt
CLEAR: t_vf. REFRESH: t_vf.
CASE 'X'.
WHEN p_custom.
SELECT
tabname fieldname ddtext inttype intlen
INTO CORRESPONDING FIELDS OF TABLE t_vf
FROM dd03vt WHERE
( tabname = 'KNA1' OR tabname = 'KNB1' )
AND ddlanguage = sy-langu.
WHEN p_vendor.
SELECT
tabname fieldname ddtext inttype intlen
INTO CORRESPONDING FIELDS OF TABLE t_vf
FROM dd03vt WHERE
( tabname = 'LFA1' OR tabname = 'LFB1' )
AND ddlanguage = sy-langu.
ENDCASE.
SORT t_vf BY fieldname.
* The create_table method dumps if same fieldname exist more than once
DELETE ADJACENT DUPLICATES FROM t_vf COMPARING fieldname.
ENDFORM.
FORM get_customer_data.
SELECT * FROM
kna1
INNER JOIN
knb1
ON kna1~mandt = knb1~mandt
AND kna1~kunnr = knb1~kunnr
INTO CORRESPONDING FIELDS OF TABLE <l_table> WHERE
kna1~kunnr IN s_kunnr AND
knb1~bukrs IN s_bukrs.
ENDFORM.
FORM get_vendor_data.
SELECT * FROM
lfa1
INNER JOIN
lfb1
ON lfa1~mandt = lfb1~mandt
AND lfa1~lifnr = lfb1~lifnr
INTO CORRESPONDING FIELDS OF TABLE <l_table> WHERE
lfa1~lifnr IN s_lifnr AND
lfb1~bukrs IN s_bukrs.
ENDFORM.
FORM initialise_fields.
CLEAR: t_header, lt_alv_cat, ls_alv_cat.
REFRESH: t_header, lt_alv_cat.
ENDFORM.
FORM show_alv_list.
DATA: l_repid LIKE sy-repid,
l_count TYPE n,
ls_field_catalog TYPE slis_fieldcat_alv, "Field catalog line
lstring(35) TYPE c,
l_char TYPE i.
CLEAR: t_alv_liste, gt_field_catalog, l_char.
REFRESH: t_alv_liste, gt_field_catalog.
l_count = '1'.
* New field catalog with the selected fields in t_vf
* OBS ! Max 30 fields (1050 characters in table t_alv_felter)
LOOP AT t_vf WHERE check = 'X'.
CLEAR ls_field_catalog.
* Fields are named F1, F2,...F30, all 35 chars type C
CONCATENATE 'F' l_count INTO ls_field_catalog-fieldname.
ls_field_catalog-inttype = 'C'.
ls_field_catalog-outputlen = 35.
ls_field_catalog-seltext_l = t_vf-ddtext(35).
INSERT ls_field_catalog INTO TABLE gt_field_catalog.
l_count = l_count + 1.
ENDLOOP.
SORT <l_table>.
* And the lines
LOOP AT <l_table> ASSIGNING <l_line>.
CLEAR: t_alv_liste, l_char.
DO 30 TIMES. "Max no of fields
ASSIGN COMPONENT sy-index OF STRUCTURE <l_line> TO <l_field>.
IF sy-subrc NE 0.
EXIT.
ENDIF.
lstring = <l_field>.
t_alv_liste+l_char(35) = lstring.
l_char = l_char + 35.
ENDDO.
APPEND t_alv_liste.
ENDLOOP.
l_repid = sy-repid.
CALL FUNCTION 'REUSE_ALV_LIST_DISPLAY'
EXPORTING
i_callback_program = l_repid
it_fieldcat = gt_field_catalog
i_bypassing_buffer = 'X'
i_save = 'A' "Std + user specific
TABLES
t_outtab = t_alv_liste.
ENDFORM.