ALV 두 개를 한 화면에 좌/우(또는 위/아래) 로 보여주는 가장 유연한 방법이 CL_GUI_SPLITTER_CONTAINER 입니다. 행/열을 자유롭게 지정해서 N분할이 가능하다는 점에서 항상 2분할 고정인 CL_GUI_EASY_SPLITTER_CONTAINER 와 다릅니다.
여기서 한 단계 더 — Splitter 의 부모 컨테이너를 SE51 의 Custom Control 이 아니라 CL_GUI_DOCKING_CONTAINER 로 잡으면 SE51 화면 페인터를 거치지 않고도 코드만으로 화면 영역을 만들 수 있습니다. Custom Control 'AREA' 를 그릴 필요 없이 Docking 이 자동으로 화면 한쪽에 영역을 붙여줍니다 — 빠른 시제품(prototype) 이나 표준 보고서 화면을 만들 때 매우 강력한 조합입니다.
이 글에서는 Docking + Splitter + ALV 두 개 조합의 컨테이너 계층 구조 → 5단계 생성 흐름 → DOCK_AT_* 상수 → ROWS x COLUMNS 자유 분할 → Field Catalog 자동 생성까지 정리합니다. 데이터는 SAP 표준 학습 환경 테이블 SFLIGHT(항공편) + SBOOK(예약) 예시.
핵심 — Docking + Splitter + ALV 의 컨테이너 계층
| 계층 | 클래스 | 역할 |
|---|---|---|
| 1. Docking | cl_gui_docking_container |
SE51 없이 화면 한쪽(상/하/좌/우) 에 영역 자동 부착 |
| 2. Splitter | cl_gui_splitter_container |
Docking 영역을 ROWS x COLUMNS 격자로 자유 분할 |
| 3. Container 셀 | cl_gui_container (셀 참조) |
get_container( row, column ) 로 각 셀 참조 획득 |
| 4. ALV Grid x N | cl_gui_alv_grid x N개 |
각 셀 컨테이너에 ALV 한 개씩 부착 |
그림으로 정리하면:
Screen 100 (빈 화면 — Custom Control 없음)
└ go_dock (cl_gui_docking_container · side=DOCK_AT_TOP · extension=500)
└ splitter (cl_gui_splitter_container · rows=1 · columns=2)
├ get_container(1,1) → container_1 ← go_grid (SFLIGHT ALV)
└ get_container(1,2) → container_2 ← go_grid2 (SBOOK ALV)
핵심은 Docking 이 부모 영역을 자동으로 제공하고, Splitter 가 그 안을 자유 분할하며, 각 격자 셀이 별도 컨테이너 참조로 떨어져 ALV 를 붙이게 해준다 는 흐름.
1단계 — SE51 화면 100 준비 (빈 화면 + PBO/PAI 모듈만)
이 패턴의 가장 큰 장점은 SE51 Custom Control 'AREA' 를 그리지 않아도 된다 는 것. SE51 에서 Screen 100 의 Layout 은 빈 채로 두고, Flow Logic 에 PBO/PAI 모듈만 연결합니다.
[1] T-Code SE51 → Program · Screen 100 (없으면 신규)
[2] Screen 100 의 Layout 은 빈 상태 (Custom Control 배치 X)
[3] Flow Logic 에 모듈 연결:
PROCESS BEFORE OUTPUT.
MODULE status_0100.
MODULE create_alv.
PROCESS AFTER INPUT.
MODULE user_command_0100.
[4] 활성화
Docking 이 PBO 시점에 화면 영역을 코드로 잡아주므로, Layout 은 정말 빈 상태로 OK. 화면 페인터를 손대지 않아도 ALV 표시가 됩니다.
2단계 — DATA 선언 (ALV/Splitter/Docking + 데이터 + Field Catalog)
ALV 두 개니까 Grid·Container 셀 참조·Field Catalog·데이터 테이블 모두 "쌍" 으로 묶입니다.
DATA: go_grid TYPE REF TO cl_gui_alv_grid,
go_grid2 TYPE REF TO cl_gui_alv_grid,
go_dock TYPE REF TO cl_gui_docking_container,
splitter TYPE REF TO cl_gui_splitter_container,
container_1 TYPE REF TO cl_gui_container,
container_2 TYPE REF TO cl_gui_container.
* ALV Layout / Sort / Field Catalog
DATA: g_layo TYPE lvc_s_layo,
g_sort TYPE lvc_s_sort.
DATA: gt_fcat TYPE lvc_t_fcat,
gs_fcat TYPE lvc_s_fcat,
gt_fcat2 TYPE lvc_t_fcat,
gs_fcat2 TYPE lvc_s_fcat.
* 데이터 — SFLIGHT(왼쪽 ALV) + SBOOK(오른쪽 ALV)
DATA: gt_data TYPE TABLE OF sflight,
gt_data2 TYPE TABLE OF sbook.
DATA: ok_code TYPE sy-ucomm.
container_1 · container_2 는 Splitter 의 각 셀을 가리키는 참조 변수. get_container( row, column ) 의 RECEIVING 인자로 받아옵니다.
3단계 — START-OF-SELECTION → 데이터 조회 → CALL SCREEN
START-OF-SELECTION.
* 왼쪽 ALV — SFLIGHT
SELECT *
INTO TABLE @gt_data
FROM sflight.
* 오른쪽 ALV — SBOOK
SELECT *
INTO TABLE @gt_data2
FROM sbook.
END-OF-SELECTION.
CALL SCREEN 100.
데이터를 채운 뒤 CALL SCREEN 100. 화면 100 의 PBO 가 돌면서 Docking → Splitter → 두 ALV 가 차례로 그려집니다.
4단계 — PBO 모듈에서 Docking + Splitter + 두 그리드 생성
PBO 의 핵심은 두 모듈. status_0100 에서 GUI Status / Titlebar 를 세팅하고, create_alv 에서 컨테이너 + 그리드를 생성.
MODULE status_0100 OUTPUT.
SET PF-STATUS 'S100'.
SET TITLEBAR 'T100'.
ENDMODULE.
MODULE create_alv OUTPUT.
* 1) Docking Container — SE51 없이 화면 위쪽에 영역 자동 부착
go_dock = NEW #(
repid = sy-cprog
dynnr = sy-dynnr
extension = 500 " 영역 크기
side = cl_gui_docking_container=>dock_at_top ). " 상단 부착
* 2) Splitter — Docking 영역을 1행 2열로 분할
splitter = NEW #(
parent = go_dock
rows = 1
columns = 2 ).
* 3) 왼쪽 컬럼 폭 조정 (선택)
splitter->set_column_width(
EXPORTING
id = 1
width = 60 ). " 1번 컬럼을 60% 폭
* 4) 각 셀의 컨테이너 참조 획득
splitter->get_container(
EXPORTING
row = 1
column = 1
RECEIVING
container = container_1 ).
splitter->get_container(
EXPORTING
row = 1
column = 2
RECEIVING
container = container_2 ).
* 5) 두 ALV Grid 를 각 컨테이너에 부착
go_grid = NEW #( i_parent = container_1 ).
go_grid2 = NEW #( i_parent = container_2 ).
* 6) 두 그리드 표시 — i_structure_name 으로 Field Catalog 자동 생성
go_grid->set_table_for_first_display(
EXPORTING
i_structure_name = 'SFLIGHT'
CHANGING
it_fieldcatalog = gt_fcat
it_outtab = gt_data ).
go_grid2->set_table_for_first_display(
EXPORTING
i_structure_name = 'SBOOK'
CHANGING
it_fieldcatalog = gt_fcat2
it_outtab = gt_data2 ).
ENDMODULE.
핵심 — Docking 의 SIDE 상수와 EXTENSION
Docking 은 화면 4면 중 어디에 영역을 붙일지 SIDE 상수로 결정합니다.
| 상수 | 값 | 부착 위치 |
|---|---|---|
dock_at_left |
1 | 화면 왼쪽 |
dock_at_top |
2 | 화면 위쪽 |
dock_at_bottom |
4 | 화면 아래쪽 |
dock_at_right |
8 | 화면 오른쪽 |
extension 은 부착 변의 두께(픽셀). dock_at_top · dock_at_bottom 이면 높이, dock_at_left · dock_at_right 이면 너비. 예시의 500 은 위쪽 영역 높이 500 픽셀.
Splitter 의 ROWS x COLUMNS — Easy Splitter 와의 차이
rows = 1 + columns = 2 면 1행 2열 (좌/우 분할). 마음대로 바꿔서 2행 2열(2x2 대시보드) · 3행 1열 등 다중 분할도 가능합니다. 항상 2분할 고정인 [SAP ABAP] CL_GUI_EASY_SPLITTER_CONTAINER 와 가장 큰 차이가 이 자유도. set_row_height · set_column_width 메서드로 각 행/열의 비율도 개별 조정합니다.
5단계 — PAI 모듈 (BACK / EXIT / CANCEL 처리)
ALV 화면을 종료할 수 있도록 PAI 에서 표준 ok_code 를 처리.
MODULE user_command_0100 INPUT.
CASE sy-ucomm.
WHEN 'BACK' OR 'CANC' OR 'EXIT'.
LEAVE TO SCREEN 0.
ENDCASE.
ENDMODULE.
LEAVE TO SCREEN 0 으로 화면 종료. GUI Status 'S100' 에 BACK/EXIT/CANCEL 펑션키를 미리 설정해두어야 동작합니다.
자주 빠뜨리는 함정
Docking 의 EXTENSION 단위 혼동
extension 은 픽셀 단위(METRIC 기본값 기준). side 가 좌/우면 너비, 상/하면 높이. 너무 작으면 ALV 가 거의 안 보이고, 너무 크면 화면을 다 덮어 본 화면 영역이 사라집니다. 일반적으로 500~800 사이 권장.
PBO 가드 누락 — 매번 컨테이너 재생성
create_alv 모듈에 IF go_dock IS INITIAL 가드가 없으면 PBO 가 돌 때마다 Docking + Splitter + Grid 가 새로 만들어져 메모리 누수 + 화면 깜빡임 발생. 첫 PBO 한 번만 생성하고 이후엔 갱신 메서드(refresh_table_display) 만 호출해야 합니다.
get_container 의 row/column 인자 누락
get_container( row, column ) 는 두 인자 모두 필수. 한 개라도 빠뜨리면 잘못된 셀 참조가 돌아오거나 덤프 발생. EXPORTING / RECEIVING 키워드 명시 권장.
set_column_width 의 width 단위
MODE_RELATIVE(기본) 에서는 퍼센트, MODE_ABSOLUTE 에서는 절대값. 기본 모드 그대로면 width=60 은 60%. 두 컬럼 합이 100% 가 안 되면 SAP 가 자동 보정하지만, 예측 가능성을 위해 두 컬럼 값을 명시적으로 설정하는 게 안전.
Field Catalog 미설정 — ALV 가 비어 보임
i_structure_name 만 넘기면 SAP 가 자동 Field Catalog 를 만들지만, 컬럼 숨김/순서 조정이 필요하면 LVC_FIELDCAT_MERGE 같은 FM 으로 미리 채우고 넘겨야 합니다. 두 그리드의 Field Catalog 도 각각 별도(gt_fcat/gt_fcat2) 로 둬야 컬럼 구성이 섞이지 않습니다.
Docking + Custom Control 동시 사용
같은 화면에 SE51 Custom Control 도 있고 Docking 도 있으면 영역이 겹쳐 화면이 깨질 수 있음. Docking 패턴을 쓸 때는 Layout 을 빈 상태로 두는 게 안전합니다.
Background 실행 시 덤프
이 패턴은 Dialog 전용. 배치 잡으로 돌리면 SAPGUI 가 없어서 Docking 생성 시점에 덤프 발생. 배치 호환이 필요하면 [SAP ABAP] ALV 백그라운드 DUMP 방지 글의 cl_gui_alv_grid=>offline( ) 분기 패턴을 함께 적용해야 합니다.
전체 코드 — 복사용 통합본
아래 통합본은 SE38 에 그대로 붙여 활성화 가능. Screen 100 의 Layout 은 빈 상태로 두고, Flow Logic 에 status_0100 · create_alv · user_command_0100 모듈을 연결하면 됩니다. GUI Status 'S100' 에 BACK/EXIT/CANCEL 펑션키 등록 + Titlebar 'T100' 등록만 추가하면 완성.
*&---------------------------------------------------------------------*
*& Report ZRXX_ALV_SPLITTER_DOCK (예시)
*&---------------------------------------------------------------------*
*& Docking + Splitter + ALV 두 개 — SFLIGHT/SBOOK 좌/우 표시
*&---------------------------------------------------------------------*
REPORT zrxx_alv_splitter_dock.
* ★ 1) DATA 선언
DATA: go_grid TYPE REF TO cl_gui_alv_grid,
go_grid2 TYPE REF TO cl_gui_alv_grid,
go_dock TYPE REF TO cl_gui_docking_container,
splitter TYPE REF TO cl_gui_splitter_container,
container_1 TYPE REF TO cl_gui_container,
container_2 TYPE REF TO cl_gui_container.
DATA: g_layo TYPE lvc_s_layo,
g_sort TYPE lvc_s_sort.
DATA: gt_fcat TYPE lvc_t_fcat,
gs_fcat TYPE lvc_s_fcat,
gt_fcat2 TYPE lvc_t_fcat,
gs_fcat2 TYPE lvc_s_fcat.
DATA: gt_data TYPE TABLE OF sflight,
gt_data2 TYPE TABLE OF sbook.
DATA: ok_code TYPE sy-ucomm.
* ★ 2) 데이터 조회 → CALL SCREEN
START-OF-SELECTION.
SELECT *
INTO TABLE @gt_data
FROM sflight.
SELECT *
INTO TABLE @gt_data2
FROM sbook.
END-OF-SELECTION.
CALL SCREEN 100.
* ★ 3) PBO — Status / Titlebar
MODULE status_0100 OUTPUT.
SET PF-STATUS 'S100'.
SET TITLEBAR 'T100'.
ENDMODULE.
* ★ 4) ★ 핵심: PBO — Docking + Splitter + 두 ALV 생성
MODULE create_alv OUTPUT.
IF go_dock IS INITIAL. " 첫 PBO 에서만 1회 생성
* 4-1) Docking — SE51 없이 상단에 영역 자동 부착
go_dock = NEW #(
repid = sy-cprog
dynnr = sy-dynnr
extension = 500
side = cl_gui_docking_container=>dock_at_top ).
* 4-2) Splitter — 1행 2열 분할
splitter = NEW #(
parent = go_dock
rows = 1
columns = 2 ).
* 4-3) 왼쪽 컬럼 폭 60%
splitter->set_column_width(
EXPORTING
id = 1
width = 60 ).
* 4-4) 각 셀의 컨테이너 참조 획득
splitter->get_container(
EXPORTING
row = 1
column = 1
RECEIVING
container = container_1 ).
splitter->get_container(
EXPORTING
row = 1
column = 2
RECEIVING
container = container_2 ).
* 4-5) 두 ALV Grid 부착
go_grid = NEW #( i_parent = container_1 ).
go_grid2 = NEW #( i_parent = container_2 ).
* 4-6) 두 그리드 표시 (Field Catalog 자동)
go_grid->set_table_for_first_display(
EXPORTING
i_structure_name = 'SFLIGHT'
CHANGING
it_fieldcatalog = gt_fcat
it_outtab = gt_data ).
go_grid2->set_table_for_first_display(
EXPORTING
i_structure_name = 'SBOOK'
CHANGING
it_fieldcatalog = gt_fcat2
it_outtab = gt_data2 ).
ENDIF.
ENDMODULE.
* ★ 5) PAI — BACK / EXIT / CANCEL 처리
MODULE user_command_0100 INPUT.
CASE sy-ucomm.
WHEN 'BACK' OR 'CANC' OR 'EXIT'.
LEAVE TO SCREEN 0.
ENDCASE.
ENDMODULE.
요약
| 단계 | 위치 | 핵심 행동 |
|---|---|---|
| 1 | SE51 Screen 100 | Layout 빈 상태 + Flow Logic 에 모듈만 연결 |
| 2 | DATA 선언 | go_dock + splitter + container_1/2 + go_grid x 2 |
| 3 | START-OF-SELECTION |
SELECT * sflight/sbook + CALL SCREEN 100 |
| 4 | PBO create_alv (IS INITIAL 가드) |
docking_container(side/extension) → splitter(rows/columns) → get_container → grid x 2 |
| 5 | PAI user_command_0100 |
BACK/EXIT/CANC → LEAVE TO SCREEN 0 |
Docking + Splitter + ALV 의 본질은 "SE51 없이 코드만으로 화면 영역 확보 → 자유 분할 → 각 영역에 ALV 부착" 한 줄. side·extension 으로 Docking 위치/크기, rows·columns 로 Splitter 분할 격자, get_container( row, column ) 으로 각 셀 참조 획득. 2분할 고정인 Easy Splitter 와 달리 3분할 이상이나 격자형(2x2 대시보드) 도 자유롭게 구성 가능 — 표준 보고서 화면이 흔히 쓰는 패턴입니다.
Disclaimer — 이 포스트는 실무 정리 노트를 바탕으로 AI 보조로 정리되었습니다.
CL_GUI_DOCKING_CONTAINER 의 DOCK_AT_* 상수값(LEFT=1/TOP=2/BOTTOM=4/RIGHT=8) 과 CL_GUI_SPLITTER_CONTAINER 의 get_container/set_column_width 시그니처는 NetWeaver 표준 정의(ECC 6.0 / S/4HANA on-premise 기준) 입니다. 적용 환경 버전에 따라 일부 차이가 있을 수 있으니 실제 적용 시 SE24 의 클래스 정의를 확인하시기 바랍니다. SFLIGHT/SBOOK 은 SAP 표준 학습 환경(IDES) 테이블이라 운영 시스템에는 없을 수 있으니, 실무 적용 시 EKKO/EKPO 등 운영 테이블로 교체하시기 바랍니다.