프로그래밍/전자정부프레임워크(eGov)

JQGrid 전자정부프레임워크에 적용하기 - (2)

Jay22 2017. 3. 20. 22:14
반응형

저번 포스팅에 이은 jqgrid를 알아보자. 이번에는 그리드에 행을 추가하고 삭제하는 방법에 대해서 볼것이다.

jqgrid를 처음 띄우는 것 부터 보고 싶다면 밑의 포스팅을 참고하기 바란다.

http://pjh3749.tistory.com/154




자 이런식으로 탭을 만들어줄건데 이거만드는 것은 너무 쉬우므로 넘어가겠다.


라고 하지만 코드를 본다면

1
2
3
4
5
<span><a href="#" onclick="javascript:jqgridTable.dataSearch();">조회</a></span
<span><a href="#" onclick="javascript:gridFunc.addRow();">행추가</a></span>
<span><a href="#" onclick="javascript:jqgridTable.saveData();">저장</a></span>
<span><a href="#" onclick="javascript:gridFunc.clearGrid();">초기화</a></span>
<span><a href="#" onclick="javascript:jqgridTable.deleteData();">삭제</a></span>
cs


이렇게 만들어주고 클릭시 스크립트의 함수를 타게 되어 있다.


행추가부터 만들어보자. 행추가는 그리드에서 조회한 데이터들의 밑에 새로운 row를 추가하는 것이다.


gridFunc의 addRow()를 타므로 똑같이 만들어 준다.


1
2
3
4
5
6
7
8
9
10
11
12
var gridFunc = {
        addRow : function() {
            
            var totCnt = $("#jqGrid").getGridParam("records");
            
            var addData = {"seq""""name""""phone" : ""
"address" : """etcc" : """gender" : "1"};
            
            $("#jqGrid").addRowData(totCnt+1, addData);
            $("#jqGrid").setColProp("name", {editable: true});
        
        }
}

cs


addRow함수를 만들어 준다.

totCnt는 그리드안의 총 카운트를 쳐주는데 getGridParam이라는 함수를 사용한다.


getGridParam("records")

리턴타입 : int

특징 : getter 메서드만 제공되며, 서버에 요청하여 리턴 받은 실제 레코드 수 이므로 사용자가 임의로 설정할 수 없다.


addData는 jqGrid헤더에 있는 값 (DB 칼럼명) 이다. 똑같이 맞춰준다. 해당 값은 직접입력이므로 "" 빈 문자열을 넣어준다. 성별은 기본 1로 넣어준다.

addRowData는 row한줄을 추가하는 것이다. 첫 번째 파라미터 인자는 당연히 총 카운트에 1을 더해야한다. 바로 밑에 추가해야 하기 때문이다. 두 번째 인자는 딱 보면 알다사피 아까 만든 addData가 들어간다.

setColProp은 속성을 설정해주는 것이다. "name"은 아까 헤더쪽에 name탭을 의미한다. 그것의 속성 {editable : true} 즉, 편집가능하게 만드는 것이다.


이것을 추가하고 한가지를 더 해주어야 한다. 첫 포스팅에서 jqgrid의 초기화 관련된 부분을 넣었을 것이다. 거기에 셀을 편집할 수 있다는 속성을 넣어야 한다.




실행한 모습이다.




저렇게 이름탭을 수정가능하게 할 수 있다.


하지만 저렇게 한다면 원래 불러왔던 값도 수정할 수 있으므로 원래 값들은 수정하지 못하게하고 새로 행추가 한 row들만 편집가능하게 하고 싶다.

그렇다면 jqgrid 테이블 init에서 속성을 또 추가해야 한다.


cellsubmit 속성을 추가한다.

cellsubmit은 clientArray와 remote 두 가지 속성이 존재한다. 

jqgrid공식 홈피에서 발췌하였다. 

아까 설정했던 cellEdit도 한 번 읽어보길 바란다.


PropertyTypeDescriptionDefault
cellEditbooleanEnables (disables) cell editing. When this option is set to true, onSelectRow event can not be used, and hovering is disabled (when mouseover on the rows).false
cellsubmitstringDetermines where the contents of the cell are saved - can have two values: 'remote' or 'clientArray'. 
If remote the content of the cell if anything is changed is immediately saved to the server using the cellurl property, via ajax. The rowid and the cell content are added to the url by default. If you have the “mtype” setting set to post, the key value pears will be send as post variables. For example, if we save the cell named mycell,{id: rowid, mycell: cellvalue} is added to the url. 
If cellsubmit is 'clientArray', no ajax request is made and the content of the changed cell can be obtained via the method getChangedCells or thru a event.
remote
cellurlstringthe url where the cell is to be saved. You need to set this only when you use cellsubmit as 'remote'.null
ajaxCellOptionsobjectThis option allow to set global ajax settings for the cell editiing when we save the data to the server. Note that with this option is possible to overwrite all current ajax setting in the save request including the complete event.empty object


cellsubmit은 두 가지 속성 'remote'와 'clientArray'가 있는데 remote는 저장하는 순간 cellurl로 ajax를 타고 간다. cellurl속성도 밑에 있다. 일반 ajax와 타는 방식은 같다. 하지만 clientArray로 속성을 주게 되면 ajax를 타지 않고 어떤 다른 이벤트 (클릭해서 저장같은) 를 통해서 데이터를 처리해줘야한다. 즉, 바로 ajax태우지 않을 것이라는 것이다.


clientArray를 주었을 때 처리할 로직을 작성해야한다.. 여기서 onSelectCell을 쓸 것이다. 아까 cellsubmit속성 밑에다가 넣어주자.


1
2
3
4
5
6
7
8
9
10
11
12
onCellSelect    : function(rowId, colId, val, e) { // e의 의미는 무엇인가요?
                var seq = $("#jqGrid").getCell(rowId, "seq");
                
                if(colId == 2) {
                    if(CommonJsUtil.isEmpty(seq)) {
                        $("#jqGrid").setColProp('name', {editable:true});
                    } else {
                        $("#jqGrid").setColProp('name', {editable:false});
                    }
                }
                
            },
cs

rowid는 현재 row의 id이다. 즉 0번째 줄이면 0 , 2번째 줄이면 2 이다.
colId는 cell의 인덱스 즉, 선택된 컬럼의 순서이다. 
val은 당연히 선택된 cell의 값이다.
e는 클릭한 객체이다.

getCell로 값을 가져온다. 클릭된 row의 순서와 헤더의 이름 "seq"를 넣어준다.
만약 클릭된 컬럼이 2라면 2번째 row의 seq인 값을 seq에 넣는다. 일단 값을 가지고 있고 colId는 어딜 눌렀는지 즉, 이름을 눌렀는지 전화번호를 눌렀는지 아까 얘기했던 클릭된 컬럼의 위치를 걸러주는 것이다. 그것이 2라면 즉 name이라면 (2번째가 name이다) seq가 빈문자열인지 확인한다. 왜 확인을 할까? 이것은 초기에 조회 버튼을 눌렀을시 그리드에 데이터가 쌓이게 되는데 이것을 편집하면 안되기 때문이다.(가정임, 제일 현실성있는) 편집하는 것은 새로이 추가된 row에서의 name이므로 seq가 비어있다는 것은 새로운 행이 추가된 row이고 이것을 editable : true로 설정한다. seq가 차있다는 것은 서버에서 불러온 편집하면 안되는 row이므로 editable : false로 설정한다.

이제 위 방식대로 그리드가 적용될 것이다.

이제 몇 가지 기능을 더해 볼 것이다. 
아까 성별 코드에 1,2로 구분을 했는데 이것을 남자 혹은 여자로 표현하고 싶다.
그러면 그리드 초기화에서 colModel안에 gender를 수정하자.
1
2
3
4
5
6
7
8
9
10
11
{name:'gender',      index:'gender',     width:100, editable:true, edittype: "select", formatter: "select",
                    editoptions : {
                        value        : {"1":"남자""2":"여자"},
                        dataEvents  : [{
                            type : 'change',
                            fn : function(e) {
                                
                            }
                        }]
                    }  
                 },
cs

editoptions에 설정한 값에 해당하는 값을 넣어준다. (1이면 남자 2이면여자 이런식으로) select로 설정했는데 이것은 셀렉트박스를 의미한다.
설정 후 바뀐 모습은 이렇게 박스형태로 내려오게된다.


이제 삭제 버튼을 적용해 보자. 아까 처음에 만들었던 배열을 보자. 첫 게시글 포스팅에서 만들었었다.
var cnames = ['아이디','이름','전화번호','주소','기타','성별코드','구분']; 
배열 끝에다가 구분을 하나 추가해 보자.
그리고 나서 colModel에 

{name:'btn',       index:'btn',      width:100,   formatter:gridFunc.rowBtn} 

이것을 추가한다. (아까 성별 설정하는 곳 바로 밑에다가 써주면 되겠다)
formatter가 적용되는 함수를 설정하는 것인데 rowBtn이라는 함수를 적용할 것이다. 이것은 삭제버튼을 만들기 위함이다.

그리고 gridFunc안에 rowBtn을 정의해준다.

1
2
3
4
5
6
7
8
rowBtn : function(cellvalue, options, rowObject){
             
            if(rowObject.seq ==""){
               return '<a href="javascript:gridFunc.delRow('+options.rowId+');"> 행삭제 </a>';
            }else {
               return "";
            }
         },
cs


formatter함수의 정의는 jqgrid 홈페이지에서 발췌하였다.


To the custom formatter are passed the following parameters:

function myformatter ( cellvalue, options, rowObject )
{
// format the cellvalue to new format
return new_formated_cellvalue;
}

Note the return in the function. This function should always return a value in order to work correctly.

  • cellvalue - is the value to be formatted
  • options - is an object containing the following element
    • options : { rowId: rid, colModel: cm} where rowId - is the id of the row colModel is the object of the properties for this column getted from colModel array of jqGrid
  • rowObject - is a row data represented in the format determined from datatype option. If we have datatype: xml/xmlstring - the rowObject is xml node,provided according to the rules from xmlReader If we have datatype: json/jsonstring - the rowObject is array, provided according to the rules from jsonReader

options의 rowId는 row번호이다. 즉 여기서는 행삭제를 위하여 어떤 row가 클릭되는지 구해서 delRow함수에 태우는 것이다.
rowObject는 데이터가 들어가있는 객체이다. 여기서 rowObject.seq라고 썼는데 이것은 여기들어있는 데이터의 seq의 값을 뽑는 것이다.
if문안에서 빈문자열 검사인데 이것은 원래 서버에서 받아온 데이터는 삭제를 하지 않기 위함이고 if를 탄다면 새로 행추가된 row이므로 삭제버튼을 달아주는 것이다.

결과는 아래와 같다. 행삭제가 추가된 row에만 붙는 것을 볼 수 있다.




이제 삭제 기능을 구현해보자.
gridFunc안에 delRow를 정의한다.

1
2
3
4
5
6
7
8
 delRow : function(rowid) {
             if(rowid != "") {
                 $("#jqGrid").delRowData(rowid);
             }
         },
         clearGrid : function() {
             $("#jqGrid").clearGridData();
         }
cs

직관적으로 delRowData는 rowid번째에 있는 row를 날리는 것이라고 알 수 있다. 그러면 이제 삭제 까지 구현되었다.

다음에는 데이터를 입력하고 validation check를 하고 (원하는 형태의 데이터만 들어갈 수 있게, 예를들어 전화번호는 숫자형태만 입력되게 끔) 디비에 저장을 해 보겠다.

궁금한점이 있으면 댓글 남겨주세요~





반응형