一个简洁实用的ALV显示模板

346cafac5ee9d8a8be9f7daeef710eb4.png

*&---------------------------------------------------------------------*
*& Report ZRPP021
*&---------------------------------------------------------------------*
*& 计划订单查询
*&---------------------------------------------------------------------*
REPORT zrpp021 NO STANDARD PAGE HEADING.


DATA: gt_fldct TYPE lvc_t_fcat,
      gs_slayt TYPE lvc_s_layo,
      gs_varnt TYPE disvariant,
      gv_repid TYPE sy-repid.
DATA: BEGIN OF gs_out,
        plnum TYPE plaf-plnum,
        matnr TYPE plaf-matnr,
        maktx TYPE makt-maktx,
        gsmng TYPE plaf-gsmng,
        meins TYPE plaf-meins,
        psttr TYPE plaf-psttr,
        pedtr TYPE plaf-pedtr,
        dispo TYPE plaf-dispo,
        beskz TYPE plaf-beskz,
        berid TYPE plaf-berid,
        fevor TYPE marc-fevor,
        fetxt TYPE t024f-txt,
      END OF gs_out.
DATA: gt_out LIKE TABLE OF gs_out.


SELECTION-SCREEN BEGIN OF BLOCK b1 WITH FRAME TITLE btxt1.
  PARAMETERS p_werks TYPE plaf-plwrk DEFAULT '6900'.
  SELECT-OPTIONS s_matnr FOR gs_out-matnr.
  SELECT-OPTIONS s_berid FOR gs_out-berid.
  SELECT-OPTIONS s_dispo FOR gs_out-dispo.
  SELECT-OPTIONS s_beskz FOR gs_out-beskz.
  SELECT-OPTIONS s_fevor FOR gs_out-fevor.
SELECTION-SCREEN END OF BLOCK b1.


AT SELECTION-SCREEN OUTPUT.
  btxt1 = '数据筛选'(t01).


AT SELECTION-SCREEN. "PAI
  CASE sy-ucomm.
    WHEN 'ONLI'.
      PERFORM auth_check.
  ENDCASE.


INITIALIZATION.
  PERFORM catset TABLES gt_fldct
                 USING: 'PLNUM' 'PLAF ' 'PLNUM' '',
                        'MATNR' 'PLAF ' 'MATNR' '',
                        'MAKTX' 'MAKT ' 'MAKTX' '',
                        'GSMNG' 'PLAF ' 'GSMNG' '',
                        'MEINS' 'PLAF ' 'MEINS' '',
                        'PSTTR' 'PLAF ' 'PSTTR' '',
                        'PEDTR' 'PLAF ' 'PEDTR' '',
                        'DISPO' 'PLAF ' 'DISPO' '',
                        'BESKZ' 'PLAF ' 'BESKZ' '',
                        'BERID' 'PLAF ' 'BERID' '',
                        'FEVOR' 'MARC ' 'FEVOR' 'LINE'(f01),
                        'FETXT' 'T024F' 'TXT  ' 'LINE NAME'(f02).


START-OF-SELECTION.
  PERFORM getdata.
  PERFORM outdata.


*&---------------------------------------------------------------------*
*&      Form  auth_check
*&---------------------------------------------------------------------*
FORM auth_check.
  AUTHORITY-CHECK OBJECT 'M_BEST_WRK'
        ID 'ACTVT' DUMMY
        ID 'WERKS' FIELD p_werks.
  IF sy-subrc <> 0.
    MESSAGE e000(oo) WITH '无工厂权限:'(m01) p_werks.
  ENDIF.
ENDFORM.


*&---------------------------------------------------------------------*
*& getdata
*&---------------------------------------------------------------------*
FORM getdata.
  CLEAR gt_out.


  SELECT plaf~plnum
         plaf~matnr
         makt~maktx
         plaf~gsmng
         plaf~meins
         plaf~psttr
         plaf~pedtr
         plaf~dispo
         plaf~beskz
         plaf~berid
         marc~fevor
         t024f~txt AS fetxt
    INTO CORRESPONDING FIELDS OF TABLE gt_out
    FROM plaf INNER JOIN marc  ON marc~matnr = plaf~matnr AND
                                  marc~werks = plaf~plwrk
              INNER JOIN makt  ON makt~matnr = plaf~matnr AND
                                  makt~spras = sy-langu
              LEFT  JOIN t024f ON t024f~werks = marc~werks AND
                                  t024f~fevor = marc~fevor
    WHERE plaf~plwrk EQ p_werks AND
          plaf~matnr IN s_matnr AND
          plaf~berid IN s_berid AND
          plaf~dispo IN s_dispo AND
          plaf~beskz IN s_beskz AND
          marc~fevor IN s_fevor.
  IF gt_out IS INITIAL.
    MESSAGE s000(oo) WITH 'No Data'.
  ENDIF.
ENDFORM.


*---------------------------------------------------------------------*
* outdata
*---------------------------------------------------------------------*
FORM outdata.
  gv_repid        = sy-repid.
  gs_slayt-zebra  = 'X'.
  gs_varnt-report = sy-repid.
  gs_varnt-handle = 1.


  CHECK gt_out IS NOT INITIAL.
  CALL FUNCTION 'REUSE_ALV_GRID_DISPLAY_LVC'
    EXPORTING
      it_fieldcat_lvc          = gt_fldct
      i_save                   = 'A'
      is_variant               = gs_varnt
      is_layout_lvc            = gs_slayt
      i_callback_program       = gv_repid
      i_callback_user_command  = 'USER_COMMAND'
      i_callback_pf_status_set = 'SET_STATUS'
    TABLES
      t_outtab                 = gt_out.
ENDFORM.


*&---------------------------------------------------------------------*
*& set_status
*&---------------------------------------------------------------------*
FORM set_status USING pt_extab TYPE slis_t_extab ##CALLED.
  SET PF-STATUS 'STD_FULL' EXCLUDING pt_extab.
ENDFORM.


*&--------------------------------------------------------------------*
*& ALV user_command
*&--------------------------------------------------------------------*
FORM user_command USING pv_ucomm TYPE sy-ucomm ##CALLED
                        pv_field TYPE slis_selfield.


  READ TABLE gt_out INTO gs_out INDEX pv_field-tabindex.
  CASE pv_ucomm.
    WHEN '&IC1'.
      CASE pv_field-fieldname.
        WHEN 'MATNR' OR 'MAKTX'.
          SET PARAMETER ID 'MXX' FIELD 'K'.
          SET PARAMETER ID 'MAT' FIELD gs_out-matnr.
          SET PARAMETER ID 'WRK' FIELD p_werks.
          CALL TRANSACTION 'MM03' AND SKIP FIRST SCREEN.
        WHEN 'PLNUM'.
          SET PARAMETER ID 'PAF' FIELD gs_out-plnum.
          CALL TRANSACTION 'MD13' AND SKIP FIRST SCREEN.
        WHEN OTHERS.
      ENDCASE.
    WHEN 'TCLIP'.
      PERFORM alvtoclip IN PROGRAM zrpubform IF FOUND
                        TABLES gt_out USING 'X'.
    WHEN 'REFRE'.
      PERFORM getdata.
      pv_field-row_stable = 'X'.
      pv_field-col_stable = 'X'.
      pv_field-refresh    = 'X'.
  ENDCASE.
ENDFORM.


*---------------------------------------------------------------------*
* set fieldcat
*---------------------------------------------------------------------*
FORM catset TABLES t_fldcat
            USING pv_field pv_reftab pv_reffld pv_text.
  DATA: ls_fldcat TYPE lvc_s_fcat.


  ls_fldcat-fieldname =  pv_field.    "字段名
  ls_fldcat-scrtext_l =  pv_text.     "长描述
  ls_fldcat-coltext   =  pv_text.     "列描述
  ls_fldcat-ref_table =  pv_reftab.   "参考表名
  ls_fldcat-ref_field =  pv_reffld.   "参考字段名
  ls_fldcat-col_opt   = 'A'.          "自动优化列宽


  CASE ls_fldcat-fieldname.
    WHEN 'GSMNG'.
      ls_fldcat-qfieldname = 'MEINS'.
      ls_fldcat-no_zero    = 'X'.
    WHEN 'MENGE'.
      ls_fldcat-qfieldname = 'MEINS'.
      ls_fldcat-no_zero    = 'X'.
    WHEN 'WRBTR'.
      ls_fldcat-cfieldname = 'WAERS'.
    WHEN 'LIFNR' OR 'AUFNR' OR 'KUNNR'.
      ls_fldcat-edit_mask = '==ALPHA'.
    WHEN 'MATNR' OR 'IDNRK'.
      ls_fldcat-edit_mask = '==MATN1'.
    WHEN 'MEINS' .
      ls_fldcat-edit_mask = '==CUNIT'.
  ENDCASE.


  APPEND ls_fldcat TO t_fldcat.
  CLEAR ls_fldcat.
ENDFORM.

eacd905e9538eb6da618ad65c0dba0d7.png

几点说明:

1、使用函数的方式实现。如果仅仅是显示数据,或者有简单的交互,没有必须使用OO ALV,简洁高效是永远的神。

2、为了程序的扩展方便,以及能兼容OO ALV的参数定义,请使用REUSE_ALV_GRID_DISPLAY_LVC代替REUSE_ALV_GRID_DISPLAY,如无特殊场合,请勿再使用REUSE_ALV_GRID_DISPLAY。

3、权限检查放到PAI里面,即AT SELECTION-SCREEN事件,方便E类型MESSAGE的使用。

4、变量名考虑了SAP的扩展检查(GV_ GT_ GS_等),内表考虑到扩展检查,没有使用带表头内表,因为CLASS内不允许使用带表头内表,所以请尽量减少带表头内表使用。

5、Status使用事务码SE41复制于程序SAPLKKBL的状态STANDARD_FULLSCREEN。如果想完整的连同翻译一起复制,请复制整个用户接口,而不是仅仅一个状态。复制完再删除没用的Status即可。

6、给Fieldcat赋值,请务必不要使用宏。根据我多年积累的经验,赋值的子程序使用字段名、参考表、参考字段、列名,这四个是最适合的,如果有例外,在FORM内根据列名处理例外。

7、自动优化列宽在Fieldcat使用参数col_opt实现,而不是layout的参数cwidth_opt实现。原因是前者可以把控制列宽优化细化到每一列,而且在ALV更改刷新后可以自动对有长度更改的列做列宽优化。

8、如果有翻译的需求,Fieldcat的列名赋值请使用 'XXXXX'(F01) 这种方式,而不要用TEXT-001这种方式,因为你也不知道TEXT-001是什么内容,还得双击一下进入到文本元素界面去看,其他文本亦是如此。

9、如无必要,SELECT的FROM部分,请务必不要使用AS语句,如果JOIN的表比较多的情况更是如此,谁也记不清A~ B~ C~ D~...是哪个表。
如下例:

d59e8f4394985300bb44a7bcf3bb293f.jpeg

改成:
0dcab243c8e6aba978ae90976f7a202d.png

立刻结构就清晰多了,看上去也赏心悦目。

10、TOCLIP功能很好用,可以直接复制ALV的表和抬头文本到剪贴板,如果用户选中了某几个列,则只复制选中列的内容。这个代码一般放到公用的子程序池程序中。

*&---------------------------------------------------------------------*
*& ALV内容复制到剪贴板
*&---------------------------------------------------------------------*
FORM alvtoclip TABLES t_alvtab USING withheader.
  DATA: fldcat  TYPE slis_t_fieldcat_alv WITH HEADER LINE,
        marked  TYPE slis_t_fieldcat_alv WITH HEADER LINE,
        entries TYPE slis_t_filtered_entries WITH HEADER LINE.
  DATA: charc   TYPE char256,
        charstr TYPE string,
        ftype .
  DATA: htab TYPE c VALUE cl_abap_char_utilities=>horizontal_tab .
  DATA: lt_clip TYPE TABLE OF char2048 WITH HEADER LINE .
  FIELD-SYMBOLS <fs_fld>.


  CALL FUNCTION 'REUSE_ALV_GRID_LAYOUT_INFO_GET'
    IMPORTING
      et_fieldcat         = fldcat[]
      et_marked_columns   = marked[]
      et_filtered_entries = entries[]
    EXCEPTIONS
      no_infos            = 1
      program_error       = 2
      OTHERS              = 3.
  IF marked[] IS INITIAL.
    marked[] = fldcat[].
    DELETE marked WHERE no_out = 'X' OR tech = 'X'.
  ENDIF.
  SORT entries.


  CHECK marked[] IS NOT INITIAL.
  CHECK t_alvtab[] IS NOT INITIAL.


  IF withheader IS NOT INITIAL.
    LOOP AT marked.
      CONCATENATE lt_clip htab marked-seltext_l INTO lt_clip.
    ENDLOOP.
    IF sy-subrc = 0.
      SHIFT lt_clip.
      APPEND lt_clip.
    ENDIF.
  ENDIF.


  LOOP AT t_alvtab.
    READ TABLE entries WITH KEY table_line = sy-tabix BINARY SEARCH.
    CHECK sy-subrc <> 0 .


    CLEAR lt_clip.
    LOOP AT marked.
      ASSIGN COMPONENT marked-fieldname OF STRUCTURE t_alvtab TO <fs_fld>.
      CHECK sy-subrc = 0.


      DESCRIBE FIELD <fs_fld> TYPE ftype.
      CASE ftype.
        WHEN 'I' OR 'P' OR 'F' OR 'a' OR 'e' OR 'b' OR 's'.
          charc = abs( <fs_fld> ).
          CONDENSE charc NO-GAPS.
          IF <fs_fld> < 0.
            CONCATENATE '-' charc INTO charc.
          ENDIF.
          charstr = charc.
        WHEN 'D' OR 'T'.
          IF <fs_fld> IS INITIAL OR <fs_fld> = ''.
            charc = ''.
          ELSE.
            WRITE <fs_fld> TO charc .
          ENDIF.
          charstr = charc.
        WHEN 'X' OR 'y' OR 'g'.
          charstr = <fs_fld> .
        WHEN OTHERS.
          WRITE <fs_fld> TO charc .
          charstr = charc.
      ENDCASE.
      CONCATENATE lt_clip htab charstr INTO lt_clip.
    ENDLOOP.
    SHIFT lt_clip.
    APPEND lt_clip.
  ENDLOOP.


  CHECK lt_clip[] IS NOT INITIAL.
  CALL FUNCTION 'CLPB_EXPORT'
    TABLES
      data_tab   = lt_clip
    EXCEPTIONS
      clpb_error = 01.
  IF sy-subrc = 0.
    MESSAGE s000(oo) WITH '已经导出到剪贴板'(m01).
  ELSE.
    MESSAGE e000(oo) WITH '导出到剪贴板错误'(m02).
  ENDIF.
ENDFORM.

程序很短,但浓缩的都是精华。
后面打算再继续出几篇ALV的文章,给大家演示如何以搭积木的方式把一个简单的程序扩展为一个复杂的交互程序。

81df7c247a880a3073f727caea8f1eb7.jpeg

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值