- 程序说明
- 程序说明
对条码系统发货装车产生的运输单, 执行运费维护, 发货过账和审批转费用采购订单功能, 以及打印功能. 发货过账前需要对交货单做批次确认, 对与启用条码管理的仓库或物料, 以条码的批次为准, 否则以销售订单库存里的批次为准.
(1) 取得运输单数据:
ZTYSK: 运输单抬头数据
ZTYSP: 运输单项目数据
ZTYSD: 运输单项目的批次数据
编辑运输单后, 执行锁定该运输单
SELECT SINGLE *
FROM ZTYSK
WHERE ZEYSO = P_ZEYSO.
IF SY-SUBRC NE 0.
MESSAGE S001(00) WITH '运输单不存在' DISPLAY LIKE 'E'.
STOP.
ENDIF.
IF ZTYSK-EBELN NE '' OR ZTYSK-KZERM = ''.
G_MOD2 = 'A'.
ELSE.
G_MOD2 = 'U'.
ENDIF.
IF G_MOD1 = 'U'.
PERFORM FRM_LOCK_DATA USING P_ZEYSO CHANGING G_LOCK G_UNAM.
IF G_LOCK = 'X'.
MESSAGE S001(00) WITH P_ZEYSO '的处理被用户' G_UNAM '锁定' DISPLAY LIKE 'E'.
STOP.
ENDIF.
ENDIF.
SELECT SINGLE WAERS INTO L_ZZWAE FROM TVKO WHERE VKORG = ZTYSK-VKORG.
SELECT *
INTO TABLE ITAB
FROM ZTYSP
WHERE ZEYSO = P_ZEYSO.
(2) 输出屏幕2000
根据事务码和权限以及运输单状态确定哪些功能生效
运输单有如下状态:
确定状态: ZTYSK-KZERM, ‘X’/’’, X为已最终确认, 只有确认的运输单才能维护运费及后续操作;
过账状态: ZTYSK-LFGSK, ‘’/’B’/’C’, B为运输单中部分交货单已过账, C为完全过账, 在运输单过账前后均能维护运费;
审批状态: ZTYSK-ZEYST, ‘A’/’B’/’C/, 维护完运费后修改审批状态值为A 提交待审批, 流转到审批人员后, 审批不通过则直接修改为B审批拒绝, 审批通过则直接直接转采购订单, 成功后该审批状态自动修改为C审批完成.
审批完成后, 不允许再对运输单维护运费.
REFRESH FCOD.
IF ZTYSK-KZERM = '' OR G_MOD1 = 'A' OR ZTYSK-EBELN NE '' OR ZTYSK-EBEL1 NE '' OR
ZTYSK-EBEL2 NE '' OR ZTYSK-EBEL3 NE ''.
FCOD-FCODE = 'POST'.
APPEND FCOD.
FCOD-FCODE = 'TOPO'.
APPEND FCOD.
FCOD-FCODE = 'SAVE'.
APPEND FCOD.
FCOD-FCODE = 'CANC'.
APPEND FCOD.
ELSE.
IF ZTYSK-LFGSK NE ''.
FCOD-FCODE = 'CANC'.
APPEND FCOD.
IF ZTYSK-LFGSK = 'C'.
FCOD-FCODE = 'POST'.
APPEND FCOD.
IF ZTYSK-ZEYST NE 'A'.
FCOD-FCODE = 'TOPO'.
APPEND FCOD.
ENDIF.
ELSE.
FCOD-FCODE = 'TOPO'.
APPEND FCOD.
ENDIF.
ELSE.
FCOD-FCODE = 'TOPO'.
APPEND FCOD.
ENDIF.
ENDIF.
IF ZTYSK-KZERM = 'X' AND G_MOD1 NE 'A' AND ZTYSK-LFGSK = 'C' AND ZTYSK-ZEYST = 'A'.
IF ( ZTYSK-EBELN = '' AND ZTYSK-TOTA1 > 0 ) OR
( ZTYSK-EBEL1 = '' AND ZTYSK-TOTA2 > 0 ) OR
( ZTYSK-EBEL2 = '' AND ZTYSK-TOTA3 > 0 ) OR
( ZTYSK-EBEL3 = '' AND ZTYSK-TOTA5 > 0 ).
DELETE FCOD WHERE FCODE = 'TOPO'.
ENDIF.
ENDIF.
FCOD-FCODE = 'UPDE'.
APPEND FCOD.
IF G_MOD1 = 'U'.
IF ( ZTYSK-EBELN = '' AND ZTYSK-TOTA1 > 0 ) OR
( ZTYSK-EBEL1 = '' AND ZTYSK-TOTA2 > 0 ) OR
( ZTYSK-EBEL2 = '' AND ZTYSK-TOTA3 > 0 ) OR
( ZTYSK-EBEL3 = '' AND ZTYSK-TOTA5 > 0 ).
ELSE.
LOOP AT ZTAB WHERE UPDAT = '' AND YSRAT > 0.
EXIT.
ENDLOOP.
IF SY-SUBRC = 0.
DELETE FCOD WHERE FCODE = 'UPDE'.
ENDIF.
ENDIF.
ENDIF.
IF G_MOD1 = 'U'.
AUTHORITY-CHECK OBJECT 'ZSD_TRANSP'
ID 'ACTVT' FIELD '02'.
IF SY-SUBRC NE 0.
READ TABLE FCOD WITH KEY FCODE = 'UPDE'.
IF SY-SUBRC NE 0.
FCOD-FCODE = 'UPDE'.
APPEND FCOD.
ENDIF.
READ TABLE FCOD WITH KEY FCODE = 'TOPO'.
IF SY-SUBRC NE 0.
FCOD-FCODE = 'TOPO'.
APPEND FCOD.
ENDIF.
ENDIF.
ENDIF.
(3) 运输单保存功能
TMP1,TMP2为临时内表, 仅用来比较数据以判断数据是否有修改.
MODIFY ZTYSK FROM ZTYSK.
IF SY-SUBRC = 0.
MODIFY ZTYSP FROM TABLE LTP.
IF SY-SUBRC = 0.
COMMIT WORK AND WAIT.
IF PR_TYPE = 'X'.
MESSAGE S001(00) WITH '运输单' ZTYSK-ZEYSO '已保存'.
ENDIF.
TMP1 = ZTYSK.
REFRESH TMP2.
TMP2[] = ZTAB[].
(4) 执行过账功能
过账前要求联系人或电话必须输入.
ZTYSP-WABUC为项目级别的过账标识, 为空则表示为过账.
取到这些未过账的交货单到内表DEL.
读取交货单的过账状态WBSTK, 如果已用标准事务过账, 则这里提示先前已记账处理, 不需要再次记账, 只需要更新项目级别的过账标识.
LOOP AT ZTAB WHERE WABUC = ''.
DEL-VBELN = ZTAB-VBELN.
COLLECT DEL.
ENDLOOP.
DATA L_WBSTK LIKE VBUK-WBSTK.
LOOP AT DEL.
CLEAR L_WBSTK.
SELECT SINGLE WBSTK
INTO L_WBSTK
FROM VBUK WHERE VBELN = DEL-VBELN.
IF L_WBSTK = 'C'.
IT_ESP-LINENO = DEL-VBELN.
IT_ESP-MSGTY = 'W'.
IT_ESP-MSGID = '00'.
IT_ESP-MSGNO = '001'.
IT_ESP-MSGV1 = '交货单'.
IT_ESP-MSGV2 = DEL-VBELN.
IT_ESP-MSGV3 = '先前已做记账处理'.
IT_ESP-MSGV4 = ''.
APPEND IT_ESP.
PERFORM FRM_UPDATE_DATA ON COMMIT.
COMMIT WORK AND WAIT.
CONTINUE.
ENDIF.
对于需要记账的交货单, 先要做批次拆分和库位确认过程.
ZTYSK-BATCH用来标记交货行项目是否有成功做过批次拆分和库位确认.
从运输单项目ZTAB中取得当前交货单且BATCH为空的项目, 从ZTYSD中取得该项目的批次, 新增9000*项目编号的批次项目, 项目中其他字段值从主项目LIPS带出.
交货单的确认库位从运输单项目ZTAB复制过去.
如果ZTYSD没有对应项目的批次数据, 则直接从订单批次库存MSKA取到批次数据,
按批次库存的数量来满足交货单数据, 以此确定批次号.
批次拆分后交货项目还有剩余的数量, 则剩余的数量保留在主项目中.
SELECT SINGLE * INTO LS_LIPS FROM LIPS WHERE VBELN = ZTAB-VBELN AND POSNR = ZTAB-POSNR.
L_LFIMG = LS_LIPS-LFIMG.
LOOP AT YSD WHERE ZITEM = ZTAB-ZITEM AND CHARG NE ''.
LS_LIPS-LFIMG = LS_LIPS-LFIMG - YSD-LFIMG.
POSNR = POSNR + 1.
ITEM-DELIV_NUMB = ZTAB-VBELN.
ITEM-DELIV_ITEM = POSNR.
ITEM-DLV_QTY = YSD-LFIMG.
ITEM-HIERARITEM = ZTAB-POSNR.
ITEM-BATCH = YSD-CHARG.
ITEM-MATERIAL = ZTAB-MATNR.
ITEM-USEHIERITM = '1'.
ITEM-SALES_UNIT = LS_LIPS-VRKME.
ITEM-BASE_UOM = LS_LIPS-MEINS.
ITEM-DLV_QTY_IMUNIT = YSD-LFIMG.
ITEM-FACT_UNIT_NOM = 1.
ITEM-FACT_UNIT_DENOM = 1.
APPEND ITEM.
CLEAR ITEM.
ITEMC-DELIV_NUMB = ZTAB-VBELN.
ITEMC-DELIV_ITEM = POSNR.
ITEMC-CHG_DELQTY = 'X'.
APPEND ITEMC.
CLEAR ITEMC.
SPL-DELIV_NUMB = ZTAB-VBELN.
SPL-DELIV_ITEM = ZTAB-POSNR.
SPL-STGE_LOC = ZTAB-LGORT.
APPEND SPL.
CLEAR SPL.
ENDLOOP.
IF SY-SUBRC NE 0.
CLEAR L_XCHPF.
REFRESH LT_MSKA.
SELECT SINGLE XCHPF INTO L_XCHPF FROM MARC WHERE WERKS = LS_LIPS-WERKS AND MATNR = LS_LIPS-MATNR.
IF L_XCHPF = 'X'.
SELECT *
INTO TABLE LT_MSKA
FROM MSKA
WHERE MATNR = LS_LIPS-MATNR
AND WERKS = LS_LIPS-WERKS
AND LGORT = ZTAB-LGORT
AND VBELN = LS_LIPS-VGBEL
AND POSNR = LS_LIPS-VGPOS
AND KALAB > 0.
L_MENGE = LS_LIPS-LFIMG.
LOOP AT LT_MSKA.
L_MENGE = L_MENGE - LT_MSKA-KALAB.
IF L_MENGE > 0.
LS_LIPS-LFIMG = LS_LIPS-LFIMG - LT_MSKA-KALAB.
POSNR = POSNR + 1.
ITEM-DELIV_NUMB = ZTAB-VBELN.
ITEM-DELIV_ITEM = POSNR.
ITEM-DLV_QTY = LT_MSKA-KALAB.
ITEM-HIERARITEM = ZTAB-POSNR.
ITEM-BATCH = LT_MSKA-CHARG.
ITEM-MATERIAL = ZTAB-MATNR.
ITEM-USEHIERITM = '1'.
ITEM-SALES_UNIT = LS_LIPS-VRKME.
ITEM-BASE_UOM = LS_LIPS-MEINS.
ITEM-DLV_QTY_IMUNIT = LT_MSKA-KALAB.
ITEM-FACT_UNIT_NOM = 1.
ITEM-FACT_UNIT_DENOM = 1.
APPEND ITEM.
CLEAR ITEM.
ITEMC-DELIV_NUMB = ZTAB-VBELN.
ITEMC-DELIV_ITEM = POSNR.
ITEMC-CHG_DELQTY = 'X'.
APPEND ITEMC.
CLEAR ITEMC.
SPL-DELIV_NUMB = ZTAB-VBELN.
SPL-DELIV_ITEM = ZTAB-POSNR.
SPL-STGE_LOC = ZTAB-LGORT.
APPEND SPL.
CLEAR SPL.
ELSE.
L_MENGE = L_MENGE + LT_MSKA-KALAB.
LS_LIPS-LFIMG = LS_LIPS-LFIMG - L_MENGE.
POSNR = POSNR + 1.
ITEM-DELIV_NUMB = ZTAB-VBELN.
ITEM-DELIV_ITEM = POSNR.
ITEM-DLV_QTY = L_MENGE.
ITEM-HIERARITEM = ZTAB-POSNR.
ITEM-BATCH = LT_MSKA-CHARG.
ITEM-MATERIAL = ZTAB-MATNR.
ITEM-USEHIERITM = '1'.
ITEM-SALES_UNIT = LS_LIPS-VRKME.
ITEM-BASE_UOM = LS_LIPS-MEINS.
ITEM-DLV_QTY_IMUNIT = L_MENGE.
ITEM-FACT_UNIT_NOM = 1.
ITEM-FACT_UNIT_DENOM = 1.
APPEND ITEM.
CLEAR ITEM.
ITEMC-DELIV_NUMB = ZTAB-VBELN.
ITEMC-DELIV_ITEM = POSNR.
ITEMC-CHG_DELQTY = 'X'.
APPEND ITEMC.
CLEAR ITEMC.
SPL-DELIV_NUMB = ZTAB-VBELN.
SPL-DELIV_ITEM = ZTAB-POSNR.
SPL-STGE_LOC = ZTAB-LGORT.
APPEND SPL.
CLEAR SPL.
EXIT.
ENDIF.
ENDLOOP.
ENDIF.
ENDIF.
* IF SY-SUBRC = 0.
ITEM-DELIV_NUMB = ZTAB-VBELN.
ITEM-DELIV_ITEM = ZTAB-POSNR.
ITEM-MATERIAL = ZTAB-MATNR.
ITEM-DLV_QTY = LS_LIPS-LFIMG.
ITEM-DLV_QTY_IMUNIT = LS_LIPS-LFIMG.
ITEM-SALES_UNIT = LS_LIPS-VRKME.
ITEM-BASE_UOM = LS_LIPS-MEINS.
ITEM-FACT_UNIT_NOM = 1.
ITEM-FACT_UNIT_DENOM = 1.
* ITEM-USEHIERITM = '1'.
APPEND ITEM.
CLEAR ITEM.
ITEMC-DELIV_NUMB = ZTAB-VBELN.
ITEMC-DELIV_ITEM = ZTAB-POSNR.
ITEMC-CHG_DELQTY = 'X'.
APPEND ITEMC.
CLEAR ITEMC.
SPL-DELIV_NUMB = ZTAB-VBELN.
SPL-DELIV_ITEM = ZTAB-POSNR.
SPL-STGE_LOC = ZTAB-LGORT.
APPEND SPL.
CLEAR SPL.
调用BAPI: BAPI_OUTB_DELIVERY_CHANGE修改交货单
修改成功后, 更新ZTYSP-BATCH = ‘X’.
"需要更改交货,增加批次
HEAD-DELIV_NUMB = DEL-VBELN.
TECHC-UPD_IND = 'U'.
HEADC-DELIV_NUMB = DEL-VBELN.
CALL FUNCTION 'BAPI_OUTB_DELIVERY_CHANGE'
EXPORTING
HEADER_DATA = HEAD
HEADER_CONTROL = HEADC
TECHN_CONTROL = TECHC
DELIVERY = DEL-VBELN
TABLES
ITEM_DATA = ITEM
ITEM_CONTROL = ITEMC
ITEM_DATA_SPL = SPL
RETURN = RETURN.
LOOP AT RETURN WHERE TYPE = 'E'.
IT_ESP-LINENO = DEL-VBELN.
IT_ESP-MSGID = RETURN-ID.
IT_ESP-MSGTY = RETURN-TYPE.
IT_ESP-MSGNO = RETURN-NUMBER.
IT_ESP-MSGV1 = RETURN-MESSAGE_V1.
IT_ESP-MSGV2 = RETURN-MESSAGE_V2.
IT_ESP-MSGV3 = RETURN-MESSAGE_V3.
IT_ESP-MSGV4 = RETURN-MESSAGE_V4.
APPEND IT_ESP.
ENDLOOP.
IF SY-SUBRC NE 0.
PERFORM FRM_UPDATE_DATA_A ON COMMIT.
CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
EXPORTING
WAIT = 'X'.
LOOP AT ZTAB WHERE VBELN = DEL-VBELN.
ZTAB-BATCH = 'X'.
MODIFY ZTAB TRANSPORTING BATCH.
ENDLOOP.
修改交货成功后, 执行交货单过账
调用函数WS_DELIVERY_UPDATE
过账成功,或以用标准事务过账,则更新ZTYSP-WABUC = ‘X’
同时还要更新电池条码和托条码为07出货状态
CALL FUNCTION 'WS_DELIVERY_UPDATE'
EXPORTING
VBKOK_WA = VBKOK_WA
DELIVERY = DEL-VBELN
UPDATE_PICKING = 'X'
COMMIT = ''
IMPORTING
EF_ERROR_ANY_0 = EF_ERROR_ANY_0
EF_ERROR_IN_GOODS_ISSUE_0 = EF_ERROR_GI
TABLES
VBPOK_TAB = VBPOK
PROT = I_PROT.
IF EF_ERROR_GI = 'X'.
"过账失败
READ TABLE I_PROT WITH KEY MSGID = 'VL' MSGNO = '602'.
IF SY-SUBRC = 0.
"发货单已被记账, 更新过账状态
IT_ESP-LINENO = DEL-VBELN.
IT_ESP-MSGTY = 'W'.
IT_ESP-MSGID = '00'.
IT_ESP-MSGNO = '001'.
IT_ESP-MSGV1 = '交货单'.
IT_ESP-MSGV2 = DEL-VBELN.
IT_ESP-MSGV3 = '先前已做记账处理'.
IT_ESP-MSGV4 = ''.
APPEND IT_ESP.
PERFORM FRM_UPDATE_DATA ON COMMIT.
CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
EXPORTING
WAIT = 'X'.
L_F1 = 'X'.
ELSE.
CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.
LOOP AT I_PROT WHERE MSGTY = 'E'.
IT_ESP-LINENO = DEL-VBELN.
IT_ESP-MSGTY = I_PROT-MSGTY.
IT_ESP-MSGID = I_PROT-MSGID.
IT_ESP-MSGNO = I_PROT-MSGNO.
IT_ESP-MSGV1 = I_PROT-MSGV1.
IT_ESP-MSGV2 = I_PROT-MSGV2.
IT_ESP-MSGV3 = I_PROT-MSGV3.
IT_ESP-MSGV4 = I_PROT-MSGV4.
APPEND IT_ESP.
ENDLOOP.
L_F2 = 'X'.
ENDIF.
ELSE.
"过账成功
PERFORM FRM_UPDATE_DATA ON COMMIT.
CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
EXPORTING
WAIT = 'X'.
L_F1 = 'X'.
ENDIF.
FORM FRM_UPDATE_DATA .
UPDATE ZTYSP SET WABUC = 'X' WHERE VBELN = DEL-VBELN.
UPDATE ZTTBC SET ZERFS = '07' WHERE VBELF = DEL-VBELN.
UPDATE ZTMBC SET ZERFS = '07' WHERE VBELF = DEL-VBELN.
ZTAB-WABUC = 'X'.
MODIFY ZTAB TRANSPORTING WABUC WHERE VBELN = DEL-VBELN.
ENDFORM.
对于没有批次更新的交货单, 则直接做记账处理, 过程同上处理
通过所有交货单记账的结果来标记抬头过账状态ZTYSK-LFGSK的值
并保存运输单
IF L_F1 = '' AND L_F2 = ''.
ZTYSK-LFGSK = 'C'.
MESSAGE S001(00) WITH '交货单已全部记账'.
PERFORM FRM_SAVE_DATA USING ''.
ELSEIF L_F1 = 'X' AND L_F2 = ''.
ZTYSK-LFGSK = 'C'.
MESSAGE S001(00) WITH '交货单已全部记账'.
PERFORM FRM_SAVE_DATA USING ''.
ELSEIF L_F1 = '' AND L_F2 = 'X'.
IF L_F3 = 'X'.
PERFORM FRM_SAVE_DATA USING ''.
ENDIF.
MESSAGE E001(00) WITH '交货单记账失败'.
ELSE.
ZTYSK-LFGSK = 'B'.
MESSAGE S001(00) WITH '交货单已部分记账'.
PERFORM FRM_SAVE_DATA USING ''.
ENDIF.
(5) 执行转采购订单功能
转采购订单之前, 检查相关运费和供应商必须输入.
检查配置表ZTVKP中维护了运输单销售组织对应的采购订单必须的组织数据.
将运输单维护了的所有运费信息, 按供应商归集到内表LT_LFA, 装卸费和特殊运费作为单独的采购订单行项目, 相同供应商的运费产生在同一张采购订单上.
海运段运费以输入的货币计入采购订单中, 其余以rmb记录
IF ZTYSK-EBELN = ''.
LT_LFA-LIFNR = ZTYSK-LIFNR.
LT_LFA-EBELP = '00010'.
LT_LFA-TOTAL = ZTYSK-TOTA1 - ZTYSK-ZXIEF - ZTYSK-TSYSF.
LT_LFA-WAERK = 'RMB'.
IF LT_LFA-TOTAL > 0.
COLLECT LT_LFA.
ENDIF.
IF ZTYSK-ZXIEF > 0.
LT_LFA-LIFNR = ZTYSK-LIFNR.
LT_LFA-EBELP = '00020'.
LT_LFA-TOTAL = ZTYSK-ZXIEF.
LT_LFA-WAERK = 'RMB'.
COLLECT LT_LFA.
ENDIF.
IF ZTYSK-TSYSF > 0.
LT_LFA-LIFNR = ZTYSK-LIFNR.
LT_LFA-EBELP = '00030'.
LT_LFA-TOTAL = ZTYSK-TSYSF.
LT_LFA-WAERK = 'RMB'.
COLLECT LT_LFA.
ENDIF.
ENDIF.
IF ZTYSK-TOTA2 > 0 AND ZTYSK-EBEL1 = ''.
LT_LFA-LIFNR = ZTYSK-LIFN1.
LT_LFA-EBELP = '00010'.
LT_LFA-TOTAL = ZTYSK-TOTA2.
LT_LFA-WAERK = 'RMB'.
COLLECT LT_LFA.
ENDIF.
IF ZTYSK-TOTA3 > 0 AND ZTYSK-EBEL2 = ''.
LT_LFA-LIFNR = ZTYSK-LIFN2.
LT_LFA-EBELP = '00010'.
LT_LFA-TOTAL = ZTYSK-TOTA3.
LT_LFA-WAERK = ZTYSK-ZZWAE.
COLLECT LT_LFA.
ENDIF.
IF ZTYSK-TOTA5 > 0 AND ZTYSK-EBEL3 = ''.
LT_LFA-LIFNR = ZTYSK-LIFN3.
LT_LFA-EBELP = '00010'.
LT_LFA-TOTAL = ZTYSK-TOTA5.
LT_LFA-WAERK = 'RMB'.
COLLECT LT_LFA.
ENDIF.
针对每个供应商和货币调用BAPI_PO_CREATE1生成采购订单
AT END OF KEY.
READ TABLE LT_LFA INDEX L_TABIX.
CALL FUNCTION 'BAPI_PO_CREATE1'
EXPORTING
POHEADER = POHEADER
POHEADERX = POHEADERX
IMPORTING
EXPPURCHASEORDER = L_EBELN
TABLES
POITEM = POITEM
POITEMX = POITEMX
POSCHEDULE = POSCHEDULE
POSCHEDULEX = POSCHEDULEX
POACCOUNT = POACC
POACCOUNTX = POACCX
* POCOND = POCOND
* POCONDX = POCONDX
RETURN = RETURN.
同时将采购订单号更新到运输单ZTYSK上
同时采购订单上也记录当前运输单号
IF LT_LFA-WAERK NE 'RMB'.
ZTYSK-EBEL2 = L_EBELN.
ELSE.
IF ZTYSK-LIFNR = LT_LFA-LIFNR.
ZTYSK-EBELN = L_EBELN.
ENDIF.
IF ZTYSK-LIFN1 = LT_LFA-LIFNR.
ZTYSK-EBEL1 = L_EBELN.
ENDIF.
IF ZTYSK-LIFN2 = LT_LFA-LIFNR AND ZTYSK-ZZWAE = 'RMB'.
ZTYSK-EBEL2 = L_EBELN.
ENDIF.
IF ZTYSK-LIFN3 = LT_LFA-LIFNR.
ZTYSK-EBEL3 = L_EBELN.
ENDIF.
ENDIF.
UPDATE EKKO SET ZZYSO = ZTYSK-ZEYSO WHERE EBELN = L_EBELN.
只要有采购订单生成成功, 则需要保存运输单数据.
如果全部采购订单均生成成功, 则还需要将运输单项目中分摊的运费更新累加到交货单对应的销售订单行项目上.
IF IT_ESP[] IS NOT INITIAL.
CALL FUNCTION 'C14Z_MESSAGES_SHOW_AS_POPUP'
TABLES
I_MESSAGE_TAB = IT_ESP.
IF L_FLAG_S = 'X'.
G_MOD2 = 'A'.
PERFORM FRM_SAVE_DATA USING ''.
ENDIF.
ELSE.
MESSAGE I001(00) WITH '无需转成运费采购订单'.
ENDIF.
IF L_FLAG = ''.
PERFORM FRM_UPDATE_SO USING G_FLAG.
IF G_FLAG = 'X'.
PERFORM FRM_SAVE_DATA USING ''.
ENDIF.
ENDIF.
(6) 执行更新销售订单运费价格功能
采购订单完全生成后, 会自动执行该功能, 如果执行失败, 则后续可以在菜单上手工点击按钮执行该功能.
ZTYSP-UPDAT标记了没有运输单行项目是否已更新销售订单价格.
首先从运输单项目ZTAB中取得UPDAT为空的销售订单项目和运费.
LOOP AT ZTAB WHERE UPDAT = ''.
MOVE-CORRESPONDING ZTAB TO SOP.
SOP-VGPOS = ZTAB-UEPOS.
COLLECT SOP.
CLEAR SOP.
ENDLOOP.
IF SY-SUBRC NE 0.
MESSAGE I001(00) WITH '订单价格已全部更新'.
RETURN.
ENDIF.
取得销售当前的价格, 再累加上当前的运费, 作为新的运费, 调用BAPI_SALESORDER_CHANGE更新销售订单
READ TABLE LT_KONV WITH KEY KNUMV = L_KNUMV KPOSN = SOP-VGPOS KSCHL = 'ZKF1'.
COND-ITM_NUMBER = SOP-VGPOS.
COND-COND_ST_NO = LT_KONV-STUNR.
COND-COND_COUNT = LT_KONV-ZAEHK.
COND-COND_TYPE = 'ZKF1'.
COND-COND_VALUE = ( LT_KONV-KWERT + SOP-YSRAT ) / 10.
APPEND COND.
CLEAR COND.
CONDX-ITM_NUMBER = SOP-VGPOS.
CONDX-COND_ST_NO = LT_KONV-STUNR.
CONDX-COND_COUNT = LT_KONV-ZAEHK.
CONDX-COND_TYPE = 'ZKF1'.
CONDX-COND_VALUE = 'X'.
CONDX-UPDATEFLAG = 'U'.
APPEND CONDX.
CLEAR CONDX.
销售订单更新成功后, 更新运输单项目ZTYSK-UPDAT = ‘X’.
并保存运输单.
LOOP AT ZTAB WHERE VGBEL = SOP-VGBEL AND UPDAT = ''.
ZTAB-UPDAT = 'X'.
MODIFY ZTAB TRANSPORTING UPDAT.
ENDLOOP.
(7) 运费维护相关处理
模块UPDATE_DATA:
相关运费输入后, 计算合计运费, 并分摊到项目中
该过程中, 海运段运费需要将外币转换为RMB后再汇总.
注意, 调整费用允许输入负值, 所以需要判断各项合计值不能小于0
ZTYSK-TOTA1 = ZTYSK-ZZYSP * ZTYSK-BRGEW / 1000 + ZTYSK-TSYSF + ZTYSK-ZXIEF.
ZTYSK-TOTA2 = ZTYSK-ZZNRP * ZTYSK-ZZYGC + ZTYSK-TJRAT * ZTYSK-ZZYGC + ZTYSK-BCRAT * ZTYSK-ZZYGC + ZTYSK-TZFY1.
IF ZTYSK-TOTA3 > 0.
IF ZTYSK-ZZWAE NE 'RMB'.
CALL FUNCTION 'READ_EXCHANGE_RATE'
EXPORTING
* CLIENT = SY-MANDT
DATE = ZTYSK-PRSDT
FOREIGN_CURRENCY = ZTYSK-ZZWAE
LOCAL_CURRENCY = 'RMB'
* TYPE_OF_RATE = 'M'
* EXACT_DATE = ' '
IMPORTING
EXCHANGE_RATE = L_UKURS
EXCEPTIONS
NO_RATE_FOUND = 1
NO_FACTORS_FOUND = 2
NO_SPREAD_FOUND = 3
DERIVED_2_TIMES = 4
OVERFLOW = 5
ZERO_RATE = 6
OTHERS = 7.
IF SY-SUBRC NE 0.
MESSAGE E001(00) WITH '没有取得货币' ZTYSK-ZZWAE '的汇率'.
ENDIF.
ELSE.
L_UKURS = 1.
ENDIF.
L_TOTAL = ZTYSK-TOTA3 / L_UKURS.
ELSE.
L_TOTAL = 0.
ENDIF.
ZTYSK-TOTA4 = ZTYSK-TOTA2 + L_TOTAL.
ZTYSK-TOTA5 = ZTYSK-DCRAT * ZTYSK-ZZYGC + ZTYSK-THRAT * ZTYSK-ZZYGC + ZTYSK-XDRAT * ZTYSK-ZZYGC + ZTYSK-DZRAT * ZTYSK-ZZYGC +
ZTYSK-YPRAT * ZTYSK-ZZYGC + ZTYSK-WJRAT + ZTYSK-TZFY3 +
ZTYSK-ENRAT + ZTYSK-CZRAT + ZTYSK-DFRAT + ZTYSK-TFRAT +
ZTYSK-BGRAT + ZTYSK-QTRAT.
IF ZTYSK-TOTA1 < 0 OR ZTYSK-TOTA2 < 0 OR ZTYSK-TOTA4 < 0 OR ZTYSK-TOTA5 < 0.
MESSAGE E001(00) WITH '合计金额不能小于0'.
ENDIF.
按所有项目的毛重的权重来分摊运费, 并将RMB的费用转换为销售订单货币金额.
尾差全部放到最后一个项目上.
LOOP AT ZTAB.
IF SY-TABIX < L_LINES.
ZTAB-YSRAT = ZTAB-BRGEW / ZTYSK-BRGEW * L_TOTAL.
L_SYTAL = L_SYTAL - ZTAB-YSRAT.
ELSE.
ZTAB-YSRAT = L_SYTAL.
ENDIF.
CLEAR L_UKURS.
IF ZTAB-WAERK NE 'RMB'.
CALL FUNCTION 'READ_EXCHANGE_RATE'
EXPORTING
* CLIENT = SY-MANDT
DATE = ZTYSK-PRSDT
FOREIGN_CURRENCY = ZTAB-WAERK
LOCAL_CURRENCY = 'RMB'
* TYPE_OF_RATE = 'M'
* EXACT_DATE = ' '
IMPORTING
EXCHANGE_RATE = L_UKURS
EXCEPTIONS
NO_RATE_FOUND = 1
NO_FACTORS_FOUND = 2
NO_SPREAD_FOUND = 3
DERIVED_2_TIMES = 4
OVERFLOW = 5
ZERO_RATE = 6
OTHERS = 7.
IF SY-SUBRC NE 0.
MESSAGE E001(00) WITH '没有取得货币' ZTAB-WAERK '的汇率'.
ENDIF.
ELSE.
L_UKURS = 1.
ENDIF.
ZTAB-YSRAT = ZTAB-YSRAT / L_UKURS.
MODIFY ZTAB TRANSPORTING YSRAT.
ENDLOOP.