밥린이의 아밥TIP

[율밥퍼] SAP ABAP - ALV HANDLE_DATA_CHANGED

율밥퍼 2023. 9. 8. 08:19

 

이번엔 Data changed로직에 대해서

포스팅해보려함

굿

모두 다 할수있다.

나는 베리굿

 

일단

 

 

혹시 DATA_CHANGED와

DATA_CHANGED_FINISHED의 차이가

궁금하다면?


DATA CHANGED란

ALV 데이터의 변경이 인지 되었을 때 타는 EVENT다.

ALV에 입력된 값이 ITAB에 반영되기 전의 시점임.

DATA_CHANGED_FINISHED

데이터 변경시 EVENT

'DATA_CHANGED'가 호출되고 에러가 없으면

(DATA_CHANGED에서

프로토콜 오류가 있으면

실행 안되겠쥬?)

그 다음 호출되는 EVENT이다.

DATA_CHANGED에서 오류가 없으면

FINISHED이벤트를 통해 인터널테이블에

자동으로 값이 변경된다.


암튼 DATA_CHANGED의 설명을 시작하겠슴댜

 

메소드 IMPLEMENTATION부분
 
 

<Data Changed 소스코드 예시.>

*&---------------------------------------------------------------------*
*& Form DATA_CHANGED
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
FORM DATA_CHANGED USING    PO_DATA_CHANGED
                               TYPE REF TO CL_ALV_CHANGED_DATA_PROTOCOL
                  CHANGING PV_ERROR_IN_DATA.

  DEFINE __MODIFY_CELL.
    PO_DATA_CHANGED->MODIFY_CELL(
                        EXPORTING I_ROW_ID    = LS_MOD_CELL-ROW_ID
                                  I_FIELDNAME = &1
                                  I_VALUE     = &2 ).
  END-OF-DEFINITION.

  DATA : LS_MOD_CELL TYPE LVC_S_MODI.

  LOOP AT PO_DATA_CHANGED->MT_GOOD_CELLS INTO LS_MOD_CELL.
    READ TABLE GT_LIST INTO DATA(LS_LIST) INDEX LS_MOD_CELL-ROW_ID.
    IF LS_MOD_CELL-FIELDNAME = 'ROLE_CODE'.
      __MODIFY_CELL 'ROLE_CODE' LS_MOD_CELL-VALUE.
      __MODIFY_CELL 'CHECK' GC_C.

    ENDIF.

  ENDLOOP.

ENDFORM.

 

PERFORM문 안으로 들어가면

나능

이렇게 로직을 짜놨다.

(하씨.. 블로그 작성할때 소스코드 하는거 있는데

나는 그것도 모르고

정성스래 색바꿔가면서 했다 ㅡㅡ)

 

일단 차근차근 설명을 해주자면~

 

 

FORM DATA_CHANGED USING    PO_DATA_CHANGED
                               TYPE REF TO CL_ALV_CHANGED_DATA_PROTOCOL
                  CHANGING PV_ERROR_IN_DATA.

 

파라미터로 받은

ER_DATA_CHANGED는

TYPE REF TO CL_ALV_CHANGED_DATA_PROTOCOL

이 타입을 따라간당.

 

나의 로직에선 PV_ERROR_IN_DATA파라미터를 쓰지 않으니

사실 지워도 무방함.

 

나는 변경되는 값을

DEFINE 명령어(메크로라고 함)를

사용해서

 

로직을 깔끔하게 정리해줌

(반복되는 로직은 나중 유지보수 혹은

코드 가독성을 위해 모듈화를 해줘라!

서브루틴을 이용해도 OK)

 

암튼

ALV내에서 데이터 변경이 일어나게 되면

 

CL_ALV_CHANGED_DATA_PROTOCOL의

MT_GOOD_CELLS에 정보가 담기게 된다.

 

테이블 형태인데

LVC_T_MODI 타입이다.

 

구조(스트럭쳐)를 보자면

요렇게 되어있당.

 

내가 변경한게 몇번째 ROW인지(ROW_ID)

그 필드의 이름은 무엇인지(FIELDNAME)

데이터 값은 뭐라고 입력했는지(VALUE)

MT_GOOD_CELLS에 담긴다.

(일단 기본적으로 쓰이는 것들만 설명

다른것들은 상황에 따라 활용하면 될듯하다)

 

그래서

 

LOOP AT PO_DATA_CHANGED->MT_GOOD_CELLS INTO LS_MOD_CELL.
    READ TABLE GT_LIST INTO DATA(LS_LIST) INDEX LS_MOD_CELL-ROW_ID.

 

데이터를 읽어오기 위해

이렇게 LOOP문을 돌린다.

(여러값을 변경했으면

테이블 형태로 여러값이 들어있겠쥬?)

 

이렇게 몇번째 ROW인지 바로 테이블에서

READ TABLE로 읽는당.

 

(ALV에선 값이 입력되거나 변경 되었지만

실제 테이블엔 반영되기 전의 시점이기 때문에

여기서 테이블 값을 변경해주기 위해 MODIFY_CELL사용)

 

    IF LS_MOD_CELL-FIELDNAME = 'ROLE_CODE'.
      PO_DATA_CHANGED->MODIFY_CELL(
                        EXPORTING I_ROW_ID    = LS_MOD_CELL-ROW_ID
                                  I_FIELDNAME = 'ROLE_CODE'
                                  I_VALUE     = LS_MODE_CELL-VALUE ).
     
      PO_DATA_CHANGED->MODIFY_CELL(
                        EXPORTING I_ROW_ID    = LS_MOD_CELL-ROW_ID
                                  I_FIELDNAME = 'CHECK'
                                  I_VALUE     = GC_C).
    ENDIF.
 

위의 로직은

아주 친절하게도~~

 

예시문에 적혀있던

DEFINE문을 풀어서 적어놓은거다

 

 

PO_DATA_CHANGED의

MODIFY_CELL메소드를 사용하여

값을 변경해주는것임.

 

EXPORTING I_ROW_ID의

'ROLE_CODE'필드는

내가 ALV에 입력한 값으로 변경하기위해

LS_MOD_CELL-VALUE

(=내가 ALV에 입력한 값)

값을 넣어준 것이다.

 

 

'CHECK'라는 필드는

수정된 값이 있다라는 것을 표시하기위해 만든

ALV에는 표시하지 않는

개발자용 필드다.

 

내가 CHECK라는 필드도 보여주는 이유는

꼭 ALV에 입력받은 값이 아니더라도

이런식으로 내가 원하는 임의의 값을

넣을 수 있다는 것을 보여주기 위해서임.

 

참고로 DATA_CHANGED를 타는 시점에 대해서

설정할 수 있는데,

 

2가지가 있다.

1. ENTER를 치자마자

2. 셀을 바꾸거나 커서를 옮겼을 때

(바로 저장누르면 안댐)

 

 

SET HANDLER하는 쪽에

* 1. ENTER를 쳐야지 DATA_CHANGED 이벤트 타게 하는 METHOD
GO_GRID->REGISTER_EDIT_EVENT( CL_GUI_ALV_GRID=>MC_EVT_ENTER ).

* 2. 값이 변경되자마자 DATA_CHANGED
GO_GRID->REGISTER_EDIT_EVENT( CL_GUI_ALV_GRID=>MC_EVT_MODIFIED ).

 

 

참고로 CL_ALV_CHANGED_DATA_PROTOCOL에는

여러가지 METHOD가 있다.

자주 사용되는 것으로는

1. GET_CELL_VALUE : 특정 CELL의 값을 가져오기.

 

2. MODIFY_CELL : 위에서 설명함.

 

3. MODIFY_STYLE :

특정 CELL에 STYLE 반영하기.

 

4. ADD_PROTOCOL_ENTRY :

ALV에 에러 로그 팝업 창에 보여질 메세지 설정

(CELL의 에러가 해결될 때까지 계속 유지된다.)


 

활용하세욤욤~

 

설명 끝

 

 

 

"METHOD 검색방법"

 

근데 초보개발자들을 위한 소소한 TIP을 하나 적자면..

 

물론 구글에 검색해보면 다 나오겠지만..

 

아놔 나 메소드 이름 모르는디..

나 외우는거 못하는디..

 

하시는 분들

꼭 이런식으로 메소드 안불러도 됩니당..

 

내가 지켜본 바로..

패턴버튼 사용하는 방법을

모르는 사람들이 꽤 있었다.

ㅇㅇ..

요 버턴..

 

FUNCTION을 부를때도

CLASS 메소드를 부를때도

 

이름이 부분만 생각나고 기억안난다?

 

그럼 앞뒤로 *넣고

F4누르면 된다.

 

*GOOD*

요렇게 쓰고 누르면

GOOD들어간거 다나옴

 

거기서 맞는거 찾아쓰면 된다.

 

클래스 메소드 부를때는

내가 라디오버튼 눌러놓은것처럼

 

ABAP 오브젝트 패턴

선택하고 확인버튼 누르면 된다.

 

그러면

이런 창이 뜨고.

 

CREATE할거면 CREATE로

나처럼 METHOD를 콜할거면

CALL METHOD 선택 후

 

위처럼 적어주면 된당.

INSTANCE는 내가 선언한 클래스를 참조하는

변수 이름을 적어주면 된당.

 

그리고 어떤 클래스의

어떤 메소드인지 저렇게 적어주면

 

 

요렇게 뿅하고 나타남.

내가 쓸건

ROW_ID

FIELDNAME

VALUE

이므로..

주석풀거 풀어주고 입력해주면 된당.

 

 

CREATE OBJECT는

나는 보통 CONTAINER나 ALV GRID 생성할때

사용한당..

똑같이 INSTANCE 적어주고

CLASS 적어주면

 

뿅하고 나타남.

 

물론 CALL METHOD 명령어 적고

조금 적은다음에

자동완성 단축키 써도 가능

CNTL + SPACE

이거쳐도 된다.

 

다만 찾는데 조금 더 어려울수도.

나는 자동완성 단축키는 이미 선언해놓은

변수 적기 귀찮을때 많이 사용함.

 

율밥퍼의 꿀팁

THE END

 

언젠가 루팡을 꿈꾸며..

킼ㅋ