단속 > 단속 등록&열람: Xit 라디오 및 역순 번호 렌더러 적용, UI 및 선택 행 동기화 개선

dev
박성영 4 months ago
parent 790232a076
commit 2c005e87bb

@ -10,7 +10,8 @@
<div class="bgs-main">
<section id="section5">
<div class="sub_title"></div>
<button type="button" id="registerBtn" class="newbtn bg1 info_a1">등록</button>
<button type="button" id="registerBtn" class="newbtn bg1">등록</button>
<button type="button" id="updaterBtn" class="newbtn bg4">수정</button>
</section>
</div>
</section>
@ -140,56 +141,6 @@
SEARCH_COND.schAgrvtnLevyTrgtYn = schAgrvtnLevyTrgtYn;
};
/**
* 라디오 버튼 커스텀 렌더러
* TUI Grid에서 라디오 버튼을 렌더링하는 클래스
*/
function CustomRadioRenderer(props) {
this.el = document.createElement('div');
this.el.style.textAlign = 'center';
this.el.style.paddingTop = '5px';
this.radioEl = document.createElement('input');
this.radioEl.type = 'radio';
this.radioEl.name = 'gridRowRadio';
this.radioEl.value = props.rowKey;
// 라디오 버튼 클릭 이벤트
this.radioEl.addEventListener('click', function(e) {
e.stopPropagation();
// 그리드의 행을 선택하고 selectedRow 설정
var grid = CrdnRegistAndViewList.grid.instance;
if (grid) {
var rowData = grid.getRow(props.rowKey);
CrdnRegistAndViewList.selectedRow = rowData;
// 다른 라디오 버튼들 해제
document.querySelectorAll('input[name="gridRowRadio"]').forEach(function(radio) {
if (radio !== this.radioEl) {
radio.checked = false;
}
}.bind(this));
this.radioEl.checked = true;
}
}.bind(this));
this.el.appendChild(this.radioEl);
this.render(props);
}
CustomRadioRenderer.prototype.getElement = function() {
return this.el;
};
CustomRadioRenderer.prototype.render = function(props) {
// 현재 선택된 행과 비교하여 라디오 버튼 상태 설정
if (CrdnRegistAndViewList.selectedRow) {
var currentRowData = CrdnRegistAndViewList.grid.instance.getRow(props.rowKey);
var isSelected = currentRowData &&
CrdnRegistAndViewList.selectedRow.crdnYr === currentRowData.crdnYr &&
CrdnRegistAndViewList.selectedRow.crdnNo === currentRowData.crdnNo;
this.radioEl.checked = isSelected;
}
};
/**
* 단속 목록 관리 네임스페이스
@ -255,7 +206,12 @@
width: 50,
sortable: false,
renderer: {
type: CustomRadioRenderer
type: XitRadioRenderer,
options: {
radioName: 'gridRowRadio',
targetObject: 'CrdnRegistAndViewList',
selectedRowProperty: 'selectedRow'
}
}
},
{
@ -265,14 +221,7 @@
width: 60,
sortable: false,
formatter: function(e) {
// 전체 데이터 개수에서 현재 행 인덱스를 빼서 역순 번호 생성
var grid = CrdnRegistAndViewList.grid.instance;
console.log(e);
if (grid) {
var totalCount = grid.getData().length;
return totalCount - e.row.rowKey;
}
return '';
return XitReverseRowNumberRenderer.format(CrdnRegistAndViewList.grid.instance.getData().length, e);
}
},
{
@ -404,16 +353,24 @@
gridBindEvents: function() {
var self = this;
// 데이터 로딩 완료 이벤트 - 라디오 버튼 초기화
this.instance.on('successResponse', function(ev) {
// 라디오 버튼 모두 해제
document.querySelectorAll('input[name="gridRowRadio"]').forEach(function(radio) {
radio.checked = false;
});
// 선택된 행 초기화
CrdnRegistAndViewList.selectedRow = null;
});
// 행 선택 이벤트
this.instance.on('selection', function(ev) {
if (ev.range && ev.range.row && ev.range.row.length > 0) {
var rowKey = ev.range.row[0];
CrdnRegistAndViewList.selectedRow = self.instance.getRow(rowKey);
// 해당 행의 라디오 버튼 체크
document.querySelectorAll('input[name="gridRowRadio"]').forEach(function(radio) {
radio.checked = (radio.value == rowKey);
});
// XitRadioRenderer 동기화 함수 사용
XitRadioRenderer.syncRadioSelection(rowKey, 'gridRowRadio');
}
});
@ -422,10 +379,8 @@
if (ev.rowKey !== undefined && ev.rowKey !== null) {
CrdnRegistAndViewList.selectedRow = self.instance.getRow(ev.rowKey);
// 해당 행의 라디오 버튼 체크
document.querySelectorAll('input[name="gridRowRadio"]').forEach(function(radio) {
radio.checked = (radio.value == ev.rowKey);
});
// XitRadioRenderer 동기화 함수 사용
XitRadioRenderer.syncRadioSelection(ev.rowKey, 'gridRowRadio');
}
});
@ -438,9 +393,16 @@
}
});
// 페이지 변경 이벤트 - 페이지 이동 버튼 클릭 시 현재 페이지 업데이트
// 페이지 변경 이벤트 - 페이지 이동 버튼 클릭 시 현재 페이지 업데이트 및 라디오 버튼 초기화
this.instance.on('afterPageMove', function(ev) {
self.updatePageInfo();
// 라디오 버튼 모두 해제
document.querySelectorAll('input[name="gridRowRadio"]').forEach(function(radio) {
radio.checked = false;
});
// 선택된 행 초기화
CrdnRegistAndViewList.selectedRow = null;
//self.updatePageInfo();
});
// 데이터 로드 완료 후 페이지 정보 업데이트
@ -569,6 +531,8 @@
$("#schRgnSeCd").val("");
$("#schDsclMthdCd").val("");
$("#schExmnr").val("");
$("#schCrdnPrcsSttsCd").val("");
$("#schAgrvtnLevyTrgtYn").val("");
// 그리드 데이터 새로고침
self.grid.instance.readData(1);
@ -580,6 +544,18 @@
self.openRegisterPopup();
});
// 수정 버튼 클릭 이벤트
$("#updaterBtn").on('click', function() {
// 선택된 행 확인
if (!self.selectedRow) {
alert('수정할 단속 건을 선택해주세요.');
return;
}
// 선택된 행의 데이터로 팝업 열기
self.openViewPopup(self.selectedRow.crdnYr, self.selectedRow.crdnNo);
});
// 상태 업데이트 버튼 클릭 이벤트들
$("#btnDsps").on('click', function() {
self.updateStatus('20', '처분사전');
@ -618,6 +594,14 @@
var perPage = parseInt($(this).val(), 10);
// Grid의 perPage 설정 변경 및 데이터 리로드
self.grid.instance.setPerPage(perPage);
// 라디오 버튼 모두 해제
document.querySelectorAll('input[name="gridRowRadio"]').forEach(function(radio) {
radio.checked = false;
});
// 선택된 행 초기화
self.selectedRow = null;
// perPage 변경 후 페이지 정보 업데이트
setTimeout(function() {
self.grid.updatePageInfo();

@ -857,6 +857,204 @@ RowNumberRenderer.prototype.getElement = function(){
* @author XIT Framework Team
* @since 2025-08-22
*/
/**
* TUI Grid 라디오 버튼 렌더러
* 그리드에서 단일 선택을 위한 라디오 버튼을 제공합니다.
*
* 사용법:
* 1. 그리드 컬럼 정의에서 renderer로 사용
* {
* header: '선택',
* name: '_radio',
* align: 'center',
* width: 50,
* sortable: false,
* renderer: {
* type: XitRadioRenderer,
* options: {
* radioName: 'gridRowRadio', // 라디오 버튼 name 속성 (선택적, 기본값: 'gridRowRadio')
* targetObject: 'MyModule', // 선택된 행을 저장할 객체명 (선택적)
* selectedRowProperty: 'selectedRow', // 선택된 행 속성명 (선택적, 기본값: 'selectedRow')
* onRowSelect: function(rowData, rowKey) { // 행 선택 시 콜백 (선택적)
* console.log('선택된 행:', rowData);
* }
* }
* }
* }
*
* 2. 그리드 이벤트에서 선택과 라디오 버튼 동기화
* gridInstance.on('selection', function(ev) {
* if (ev.range && ev.range.row && ev.range.row.length > 0) {
* var rowKey = ev.range.row[0];
* XitRadioRenderer.syncRadioSelection(rowKey);
* }
* });
*
* @author XIT Framework Team
* @since 2025-08-26
*/
var XitRadioRenderer = function(props) {
// 옵션 설정
var options = (props.columnInfo.renderer && props.columnInfo.renderer.options) ? props.columnInfo.renderer.options : {};
var radioName = options.radioName || 'gridRowRadio';
var targetObject = options.targetObject;
var selectedRowProperty = options.selectedRowProperty || 'selectedRow';
var onRowSelect = options.onRowSelect;
// div 컨테이너 생성
this.el = document.createElement('div');
this.el.style.textAlign = 'center';
this.el.style.paddingTop = '5px';
// 라디오 버튼 생성
this.radioEl = document.createElement('input');
this.radioEl.type = 'radio';
this.radioEl.name = radioName;
this.radioEl.value = props.rowKey;
// 라디오 버튼 클릭 이벤트
this.radioEl.addEventListener('click', function(e) {
e.stopPropagation();
// 그리드에서 행 데이터 가져오기
var grid = props.grid;
if (grid) {
var rowData = grid.getRow(props.rowKey);
// 대상 객체에 선택된 행 저장
if (targetObject && window[targetObject]) {
window[targetObject][selectedRowProperty] = rowData;
}
// 다른 라디오 버튼들 해제
document.querySelectorAll('input[name="' + radioName + '"]').forEach(function(radio) {
if (radio !== this.radioEl) {
radio.checked = false;
}
}.bind(this));
this.radioEl.checked = true;
// 콜백 함수 호출
if (typeof onRowSelect === 'function') {
onRowSelect(rowData, props.rowKey);
}
}
}.bind(this));
this.el.appendChild(this.radioEl);
this.render(props);
};
XitRadioRenderer.prototype.getElement = function() {
return this.el;
};
XitRadioRenderer.prototype.render = function(props) {
// 현재 선택된 행과 비교하여 라디오 버튼 상태 설정
var options = (props.columnInfo.renderer && props.columnInfo.renderer.options) ? props.columnInfo.renderer.options : {};
var targetObject = options.targetObject;
var selectedRowProperty = options.selectedRowProperty || 'selectedRow';
if (targetObject && window[targetObject] && window[targetObject][selectedRowProperty]) {
var selectedRow = window[targetObject][selectedRowProperty];
var currentRowData = props.grid.getRow(props.rowKey);
// 기본적으로 rowKey로 비교하거나, 사용자 정의 비교 로직 적용
var isSelected = false;
if (selectedRow && currentRowData) {
// rowKey로 비교
isSelected = selectedRow.rowKey === currentRowData.rowKey;
// 추가적으로 특정 키 필드들로 비교 (예: ID가 있는 경우)
if (!isSelected && selectedRow.crdnYr && selectedRow.crdnNo && currentRowData.crdnYr && currentRowData.crdnNo) {
isSelected = selectedRow.crdnYr === currentRowData.crdnYr && selectedRow.crdnNo === currentRowData.crdnNo;
}
}
this.radioEl.checked = isSelected;
}
};
/**
* 라디오 버튼 선택 동기화 (그리드 외부에서 호출용)
*/
XitRadioRenderer.syncRadioSelection = function(rowKey, radioName) {
radioName = radioName || 'gridRowRadio';
document.querySelectorAll('input[name="' + radioName + '"]').forEach(function(radio) {
radio.checked = (radio.value == rowKey);
});
};
/**
* TUI Grid 역순 행번호 렌더러
* 그리드에서 전체 데이터 개수 기준으로 역순 번호를 표시합니다.
*
* 사용법:
* {
* header: '번호',
* name: '_rowNum',
* align: 'center',
* width: 60,
* sortable: false,
* formatter: function(e) {
* return XitReverseRowNumberRenderer.format(e);
* }
* }
*
* 또는 renderer로 사용:
* {
* header: '번호',
* name: '_rowNum',
* align: 'center',
* width: 60,
* sortable: false,
* renderer: {
* type: XitReverseRowNumberRenderer
* }
* }
*
* @author XIT Framework Team
* @since 2025-08-26
*/
var XitReverseRowNumberRenderer = function(props) {
// Element 생성
this.el = document.createElement('div');
this.el.style.textAlign = 'center';
this.el.innerHTML = XitReverseRowNumberRenderer.format({
grid: props.grid,
rowKey: props.rowKey,
row: props.row
});
};
XitReverseRowNumberRenderer.prototype.getElement = function() {
return this.el;
};
XitReverseRowNumberRenderer.prototype.render = function(props) {
this.el.innerHTML = XitReverseRowNumberRenderer.format({
grid: props.grid,
rowKey: props.rowKey,
row: props.row
});
};
/**
* 역순 번호 포맷팅 함수 (formatter에서 직접 사용 가능)
*/
XitReverseRowNumberRenderer.format = function(gridDataLength, e) {
var rowKey = e.row.rowKey;
if (gridDataLength) {
var totalCount = gridDataLength;
return totalCount - rowKey;
}
return '';
};
var XitTuiGridDropdownMenu = {
/**

Loading…
Cancel
Save