I. Skenario.
Tutorial ini merupakan tutorial awal membahas mengenai display data koordinat map (latitude -longitude) menggunakan integrasi ABAP dengan service dari Google Map ™. Contoh kasus yang diangkat adalah data customer, sebagai latihan table customer akan dibuat di z-table. Table tersebut berisi Customer number, data latitude dan longitude. Pengembangan nantinya data koordinat customer itu bisa dihubungkan dengan data customer yang ada di SAP.
Style coding yang digunakan pada contoh masih bersifat prosedural. Namun di dalam prakteknya, report ini membutuhkan class dari SAP custom control framework (cl_gui_custom_container dan cl_gui_html_viewer). Alv pada report ini menggunakan class SALV, namun bagi yang terbiasa menggunakan cl_gui_alv_grid juga dapat menggunakannya di report ini.
II. Design dan Specification.
Berikut ini adalah desain awal dan spesifikasi umum dari sistem yang akan dirancang.
Berikut ini adalah desain awal dan spesifikasi umum dari sistem yang akan dirancang.
I. PERMINTAAN
|
||||||||||
Module
|
SD
|
Date
|
13 December
2013
|
|||||||
Request
By
|
Lina Inverse
|
Initial
Name
|
-
|
|||||||
Request
Type
|
Report
ABAP
|
Characteristic
|
Dialog
Programming
|
|||||||
Printer
|
-
|
Reference
T-Code
|
-
|
|||||||
II. INFO OBJECT
|
||||||||||
1
|
Package
|
$TMP
|
4
|
T-Code
|
ZMAP01
|
|||||
2
|
Program Name
|
ZLAT_MAP01
|
5
|
Include Program
|
-
|
|||||
3
|
Function Modul
|
-
|
6
|
|||||||
III. DESKRIPSI DETAIL INFO OBJECT
|
||||||||||
1
|
Background
|
Displaying
Customer List in ALV and Google Map.
|
||||||||
2
|
Flow of
Process
|
Select Customer
no. -> Displays
|
||||||||
3
|
Tables
|
zcustomer_01
|
||||||||
4
|
Input
Screen/Selection
|
Customer
No (zcustomer_01-KUNNR)
|
||||||||
5.
|
Output
|
|
III. Prasyarat.
1. Google account.
2. API Key.
3. Basic knowledge in HTML & Js.
4. Basic Knowledge in ABAP (Dialog Programming, HTML Viewer , Class).
5. Komputer user memiliki koneksi internet.
1. Google account.
2. API Key.
3. Basic knowledge in HTML & Js.
4. Basic Knowledge in ABAP (Dialog Programming, HTML Viewer , Class).
5. Komputer user memiliki koneksi internet.
IV. Langkah-langkah.
1. Buat account google di : www.google.com.
2. Buat API key google map di https://code.google.com/apis/console. Api yang digunakan adalah Google Maps API v3. Adapun langkah-langkah pembuatan bisa dilihat di : https://developers.google.com/maps/documentation/javascript/tutorial#api_key. Jika kesulitan membuat api key, masih dapat menggunakan api key pada coding yang tersedia (namun sewaktu-waktu dapat expired).
3. Buka SE11. Create new Z-table untuk data koordinat. misalkan : zcustomer_01. Berikut screenshoot untuk fields nya.
1. Buat account google di : www.google.com.
2. Buat API key google map di https://code.google.com/apis/console. Api yang digunakan adalah Google Maps API v3. Adapun langkah-langkah pembuatan bisa dilihat di : https://developers.google.com/maps/documentation/javascript/tutorial#api_key. Jika kesulitan membuat api key, masih dapat menggunakan api key pada coding yang tersedia (namun sewaktu-waktu dapat expired).
3. Buka SE11. Create new Z-table untuk data koordinat. misalkan : zcustomer_01. Berikut screenshoot untuk fields nya.
SAP
sebenarnya telah menyediakan domain khusus koordinat geospatial yaitu
GEOLONLAT. Namun untuk alasan mempermudah proses display di html viewer, maka
dipilihlah tipe data char :) Buatlah
Table maintenance agar mudah untuk membuat input
data dummy nantinya. Contoh
data dummy :
4. Buka SE38. Create Program ZLAT_MAP01 (atau apa saja ) type :
Executable.
5. Create
SCREEN 9000.
Screen FLow Logic.
Screen FLow Logic.
6. Create
GUI Status ST_9000.
7. Create GUI Title TL_9000.
8. Main Coding.
1: *&---------------------------------------------------------------------*
2: *& Report ZTEST_GMAP
3: *& Created by : Lina Inverse
4: *&---------------------------------------------------------------------*
5: *& Change logs.
6: *&
7: *&---------------------------------------------------------------------*
8: REPORT ztest_gmap.
9: TABLES : zcustomer_01.
10: *------------------ Types and Data Declaration -------------------------*
11: TYPES : BEGIN OF ty_html,
12: dataset(255) TYPE c,"HTML Line
13: END OF ty_html,
14: BEGIN OF ty_data_alv,
15: kunnr TYPE zcustomer_01-kunnr, "Cust. no
16: name TYPE zcustomer_01-name, "Cust. name
17: END OF ty_data_alv,
18: BEGIN OF ty_data_map,
19: kunnr TYPE zcustomer_01-kunnr, "Cust. no
20: name TYPE zcustomer_01-name, "Cust. name
21: latitude TYPE zcustomer_01-latitude, "Cust. latitude
22: longitude TYPE zcustomer_01-longitude, "Cust. longitude
23: END OF ty_data_map.
24: DATA : wa_data TYPE ty_html, "Wa for HTML content
25: gt_data TYPE STANDARD TABLE OF ty_html, "Itab untuk isi html
26: ok_code TYPE sy-ucomm, "ok code
27: gv_url TYPE char255, "Url file html
28: gv_key TYPE c LENGTH 50, "API Key
29: wa_alv TYPE ty_data_alv,
30: gt_alv TYPE STANDARD TABLE OF ty_data_alv, "itab untuk ALV
31: gt_cust TYPE STANDARD TABLE OF ty_data_map WITH HEADER LINE. "Itab data cust
32: DATA : gr_cc TYPE REF TO cl_gui_custom_container, "Custom container untuk ALV
33: gr_alv TYPE REF TO cl_salv_table, "ALV Table
34: gr_columns TYPE REF TO cl_salv_columns, "ALV Columns Desc.
35: gr_cont_map TYPE REF TO cl_gui_custom_container, "Map object Custom container
36: gr_html TYPE REF TO cl_gui_html_viewer. "Html viewer
37: *----------------------- Selection Screen -------------------------------*
38: SELECTION-SCREEN BEGIN OF SCREEN 0100 AS SUBSCREEN.
39: SELECTION-SCREEN BEGIN OF BLOCK b1 WITH FRAME.
40: SELECTION-SCREEN BEGIN OF LINE.
41: SELECTION-SCREEN COMMENT 1(20) txt1 FOR FIELD pa_kunnr.
42: PARAMETERS pa_kunnr TYPE c LENGTH 10.
43: SELECTION-SCREEN END OF LINE.
44: SELECTION-SCREEN END OF BLOCK b1.
45: SELECTION-SCREEN END OF SCREEN 0100.
46: INITIALIZATION.
47: txt1 = 'No. Customer'.
48: "!! Perhatian. API Key pada contoh sewaktu2 dapat berubah. Sebaiknya Gunakan API key pribadi yah :)
49: gv_key = 'AIzaSyADjWAt-nKmreVBK5YNEacbFRDNSQRZPxI'.
50: START-OF-SELECTION.
51: SET SCREEN 9000.
52: *&---------------------------------------------------------------------*
53: *& Module STATUS_9000 OUTPUT
54: *&---------------------------------------------------------------------*
55: * PBO for 9000
56: *----------------------------------------------------------------------*
57: MODULE status_9000 OUTPUT.
58: SET PF-STATUS 'ST_9000'.
59: SET TITLEBAR 'TL_9000'.
60: PERFORM f_get_data_cust. "Ambil data cust
61: PERFORM f_generate_html. "Generate syntax HTML
62: "Check gr_alv obj. has been created or not.
63: IF gr_alv IS BOUND.
64: gr_alv->refresh( ).
65: gr_alv->set_data(
66: CHANGING
67: t_table = gt_alv ).
68: ELSE.
69: CREATE OBJECT gr_cc
70: EXPORTING
71: container_name = 'CC_ALV'.
72: TRY.
73: CALL METHOD cl_salv_table=>factory
74: EXPORTING
75: r_container = gr_cc
76: container_name = 'CC_ALV'
77: IMPORTING
78: r_salv_table = gr_alv
79: CHANGING
80: t_table = gt_alv.
81: CATCH cx_salv_msg.
82: ENDTRY.
83: ENDIF.
84: "kustomisasi Kolom ALV
85: gr_columns = gr_alv->get_columns( ).
86: gr_columns->set_optimize( abap_true ).
87: PERFORM fm_change_column USING gr_columns :
88: 'KUNNR' ' ' ' ' '' '' 'ID Customer' 'ID Customer',
89: 'NAME' ' ' ' ' '' '' 'Customer Name' 'Cust. Name.
90: "Tampilkan ALV.
91: gr_alv->display( ).
92: "Cek object container map.
93: IF gr_cont_map IS BOUND.
94: CALL METHOD gr_cont_map->free.
95: FREE gr_cont_map.
96: ENDIF.
97: "Create map container obj
98: CREATE OBJECT gr_cont_map
99: EXPORTING
100: container_name = 'CC_MAP'
101: EXCEPTIONS
102: cntl_error = 1
103: cntl_system_error = 2
104: create_error = 3
105: lifetime_error = 4
106: lifetime_dynpro_dynpro_link = 5
107: OTHERS = 6.
108: IF sy-subrc <> 0.
109: ENDIF.
110: "Create html object on container map
111: CREATE OBJECT gr_html
112: EXPORTING
113: parent = gr_cont_map
114: EXCEPTIONS
115: cntl_error = 1
116: cntl_install_error = 2
117: dp_install_error = 3
118: dp_error = 4
119: OTHERS = 5.
120: IF sy-subrc <> 0.
121: ENDIF.
122: "Load data dari table berisi kode html (gt_data) ke sebuah url
123: CALL METHOD gr_html->load_data
124: EXPORTING
125: type = 'text'
126: subtype = 'html'
127: IMPORTING
128: assigned_url = gv_url "Dynamically assign url name
129: CHANGING
130: data_table = gt_data "Data skrip HTML
131: EXCEPTIONS
132: dp_invalid_parameter = 1
133: dp_error_general = 2
134: cntl_error = 3
135: OTHERS = 4.
136: IF sy-subrc <> 0.
137: ENDIF.
138: "Tampilkan html dari url hasil bentukan.
139: CALL METHOD gr_html->show_url
140: EXPORTING
141: url = gv_url
142: EXCEPTIONS
143: cntl_error = 1
144: cnht_error_not_allowed = 2
145: cnht_error_parameter = 3
146: dp_error_general = 4
147: OTHERS = 5.
148: IF sy-subrc <> 0.
149: ENDIF.
150: ENDMODULE. " STATUS_9000 OUTPUT
151: *&---------------------------------------------------------------------*
152: *& Module USER_COMMAND_9000 INPUT
153: *&---------------------------------------------------------------------*
154: * PAI for screen 9000
155: *----------------------------------------------------------------------*
156: MODULE user_command_9000 INPUT.
157: CASE ok_code.
158: WHEN '&BACK' OR '&EXIT' OR '&CANCEL'.
159: LEAVE TO SCREEN 0.
160: WHEN OTHERS.
161: * CALL METHOD cl_gui_cfw=>dispatch.
162: ENDCASE.
163: ENDMODULE. " USER_COMMAND_9000 INPUT
164: *&---------------------------------------------------------------------*
165: *& Form F_GENEARTE_HTML
166: *&---------------------------------------------------------------------*
167: * HTML code. Logika dan contoh bisa dicopy dari :
168: * https://developers.google.com/maps/documentation/javascript/tutorial#HelloWorld
169: *----------------------------------------------------------------------*
170: FORM f_generate_html .
171: CLEAR wa_data. FREE gt_data.
172: "Mulai membuat html
173: wa_data-dataset = '<html>'. APPEND wa_data TO gt_data.
174: wa_data-dataset = '<head>'. APPEND wa_data TO gt_data.
175: wa_data-dataset = '<meta name="viewport" content="initial-scale=1.0, user-scalable=no" />'. APPEND wa_data TO gt_data.
176: wa_data-dataset = '<style type="text/css">'. APPEND wa_data TO gt_data.
177: wa_data-dataset = 'html { height: 100% }'. APPEND wa_data TO gt_data.
178: wa_data-dataset = 'body { height: 100%; margin: 0; padding: 0 }'. APPEND wa_data TO gt_data.
179: wa_data-dataset = '#map-canvas { height: 100% }'. APPEND wa_data TO gt_data.
180: wa_data-dataset = '</style>'. APPEND wa_data TO gt_data.
181: "!! Attention : gunakan gv_key (api key) milik pribadi, api key pada tutorial dapat diganti sewaktu waktu !!.
182: CONCATENATE '<script type="text/javascript" src="https://maps.googleapis.com/maps/api/js?key=' gv_key '&sensor=false"></script>'
183: INTO wa_data-dataset.
184: APPEND wa_data TO gt_data.
185: " {{ == Start Java script ------------------------------------------------------------------------
186: CONCATENATE '<script type="text/javascript">'
187: 'function initialize(){'
188: 'var mapOptions = { center: new google.maps.LatLng(-8.674367, 115.202451), zoom: 12 };' INTO wa_data-dataset.
189: "mapOptions center (-8.674367, 115.202451) = titik tengah Map, pada contoh masih di-hardcode. pada tutorial selanjutnya akan dinamis.
190: APPEND wa_data TO gt_data.
191: CONCATENATE 'var map' ' = new google.maps.Map(document.getElementById("map-canvas"), mapOptions);' INTO wa_data-dataset.
192: APPEND wa_data TO gt_data.
193: "Loop untuk data customer dimulai disini.
194: LOOP AT gt_cust.
195: "Pastikan data latitude longitude ada isinya.
196: IF gt_cust-latitude IS NOT INITIAL AND gt_cust-longitude IS NOT INITIAL.
197: CONDENSE : gt_cust-latitude, gt_cust-longitude.
198: CONCATENATE 'var position = new google.maps.LatLng( ' gt_cust-latitude ',' gt_cust-longitude ' );' INTO wa_data-dataset. APPEND wa_data TO gt_data.
199: CONCATENATE 'var marker = new google.maps.Marker({ '
200: 'position: position,'
201: 'map: map });' INTO wa_data-dataset. APPEND wa_data TO gt_data.
202: CONCATENATE 'marker.setTitle(' '''' gt_cust-name '''' '); ' INTO wa_data-dataset. APPEND wa_data TO gt_data.
203: ENDIF.
204: ENDLOOP.
205: wa_data-dataset = '}'. APPEND wa_data TO gt_data.
206: CONCATENATE 'google.maps.event.addDomListener(window, ' '''load''' ', initialize); '
207: '</script>' INTO wa_data-dataset.
208: APPEND wa_data TO gt_data.
209: " ==== }} ----------End Java script ------------------------------------------------------------------------
210: wa_data-dataset = '</head>'.APPEND wa_data TO gt_data.
211: " Script Body, hanya berisi pemanggilan ID map-canvas.
212: wa_data-dataset = '<body>'.APPEND wa_data TO gt_data.
213: wa_data-dataset = '<div id="map-canvas"/>'. APPEND wa_data TO gt_data.
214: wa_data-dataset = '</body>'.APPEND wa_data TO gt_data.
215: wa_data-dataset = '</html>'.APPEND wa_data TO gt_data.
216: ENDFORM. " F_GENEARTE_HTML
217: *&---------------------------------------------------------------------*
218: *& Form F_GET_DATA_CUST
219: *&---------------------------------------------------------------------*
220: * Logika tarik data dari z table.
221: *&---------------------------------------------------------------------*
222: FORM f_get_data_cust .
223: CONDENSE pa_kunnr.
224: IF pa_kunnr IS INITIAL OR pa_kunnr = '*'.
225: SELECT kunnr name latitude longitude FROM zcustomer_01
226: INTO TABLE gt_cust.
227: ELSE.
228: SELECT kunnr name latitude longitude FROM zcustomer_01
229: INTO TABLE gt_cust
230: WHERE kunnr = pa_kunnr.
231: ENDIF.
232: "Isi table untuk ALV
233: IF gt_cust[] IS NOT INITIAL.
234: CLEAR wa_alv.
235: REFRESH gt_alv.
236: LOOP AT gt_cust.
237: wa_alv-kunnr = gt_cust-kunnr.
238: wa_alv-name = gt_cust-name.
239: APPEND wa_alv TO gt_alv.
240: CLEAR wa_alv.
241: ENDLOOP.
242: ENDIF.
243: ENDFORM. " F_GET_DATA_TOKO
244: *&---------------------------------------------------------------------*
245: *& Form change_column
246: *&---------------------------------------------------------------------*
247: * form untuk penamaan kolom ALV.
248: *----------------------------------------------------------------------*
249: * -->PO_COLUMNS text
250: * -->PV_FIELDNAME text
251: * -->PV_TECHNICAL text
252: * -->PV_INVISIBLE text
253: * -->PV_CURRREF text
254: * -->PV_QUANREF text
255: * -->PV_FIELDTEXTLM text
256: * -->PV_FIELDTEXTS text
257: *----------------------------------------------------------------------*
258: FORM fm_change_column USING po_columns TYPE REF TO cl_salv_columns
259: pv_fieldname TYPE c "Nama Kolom
260: pv_technical TYPE c
261: pv_invisible TYPE c
262: pv_currref TYPE c "Curr Ref
263: pv_quanref TYPE c "Quan ref
264: pv_fieldtextlm TYPE c "Nama Kolom Medium Length
265: pv_fieldtexts TYPE c."Nama Kolom Short Length
266: DATA lo_column TYPE REF TO cl_salv_column_table.
267: DATA lv_short TYPE scrtext_s.
268: DATA lv_medium TYPE scrtext_m.
269: DATA lv_long TYPE scrtext_l.
270: TRY .
271: lo_column ?= po_columns->get_column( pv_fieldname ).
272: IF pv_technical IS NOT INITIAL.
273: lo_column->set_technical( abap_true ).
274: ENDIF.
275: IF pv_invisible IS NOT INITIAL.
276: lo_column->set_visible( abap_false ).
277: RETURN.
278: ENDIF.
279: IF pv_currref IS NOT INITIAL.
280: lo_column->set_currency_column( pv_currref ).
281: ELSEIF pv_quanref IS NOT INITIAL.
282: lo_column->set_quantity_column( pv_quanref ).
283: ENDIF.
284: IF pv_fieldtextlm IS NOT INITIAL.
285: lv_medium = lv_long = pv_fieldtextlm.
286: lo_column->set_medium_text( lv_medium ).
287: lo_column->set_long_text( lv_long ).
288: ENDIF.
289: IF pv_fieldtexts IS NOT INITIAL.
290: lv_short = pv_fieldtexts.
291: lo_column->set_short_text( lv_short ).
292: ENDIF.
293: CATCH cx_salv_not_found. "#EC NO_HANDLER
294: CATCH cx_salv_data_error. "#EC NO_HANDLER
295: ENDTRY.
296: ENDFORM. " CHANGE_COLUMN
9. Activate. Jika sukses bisa langsung di-execute
F8.
10. Buat Tcodenya di SE93.
V. Kesimpulan
Sistem Display
Mapping Customer menggunakan Google Map ini merupakan rancangan sederhana
memanfaatkan media html_viewer dan koneksi internet untuk mengakses google map.
Parameter dan nilai-nilai dinamis dibentuk dan dimasukkan ke dalam kerangka
HTML. FIle HTML yang dinamis ini dibentuk dengan mengakomodasi seluruh
informasi yang dibutuhkan user. Program awal ini merupakan contoh yang masih simple
karena program hanya bersifat satu arah yaitu dari input selection screen
(filter ABAP Program) menghasilkan informasi pada citra GoogleMap, masih belum
bersifat vice versa ( proses sebaliknya,
action pada map belum bisa ditangkap ABAP). Beberapa nilai masih di hardcode
seperti inisiasi nilai titik tengah koordinat dari map, nantinya dapat
dikembangkan dengan penentuan titik tengah yang dinamis.
Pengembangan program
dan eksperimen dapat dilakukan mengingat masih banyak tools dari SAP sendiri
yang bisa digunakan untuk membaca ajax hasil response google map. Demikian pula
element-element API Google Map sendiri masih banyak sekali yang dapat di dalami
dan di eksplore untuk menghasilkan report display koordinat geospatial data
yang lebih baik. Kritik dan saran atau penambahan dapat disampaikan ke email saptestqa@gmail.com. Happy coding,
all :)
VI. Reference
1. Reinandang, A (2012). ABAP - Basic Knowledge Revision 7. SAP-Interface.
2. Google Maps JavaScript API v3 . https://developers.google.com/maps/documentation/javascript/tutorial .
1. Reinandang, A (2012). ABAP - Basic Knowledge Revision 7. SAP-Interface.
2. Google Maps JavaScript API v3 . https://developers.google.com/maps/documentation/javascript/tutorial .
No comments:
Post a Comment