본문 바로가기
개발/React

리액트 - Handsontable Customization Options (Search 구현)

by 피로물든딸기 2023. 9. 29.
반응형

리액트 전체 링크

 

참고

- https://handsontable.com/docs/javascript-data-grid/api/core/#scrollviewportto

 

- Project Settings (전체 코드)

- True / False Options

- Selected Options

- Number Options

- width, height, placeholder, sort

- 주석, comment, memo, tooltip

- Merge Cells, 셀 합치기

- Search 구현

- Columns Data Type

- Cell 커스터마이징

- afterSelection으로 수식 입력줄 구현하기

- Download CSV 구현 (콤마, 줄바꿈, 따옴표 처리)

- Mui Drawer로 Handsontable Option 관리하기

- Column Width, Row Height 로컬 스토리지에 저장하기

- Mui 토글 버튼으로 셀 스타일 편집 기능 만들기 

- 셀 스타일 로컬 스토리지에 저장하기 (전체 코드)

- Handsontable 깃허브 연동하기 (data, style, comment, merge 저장하기)


아래 링크를 참고하여 search 기능을 구현해보자.

https://handsontable.com/docs/6.2.2/Search.html

 

Ctrl + F를 이용하여 문자열을 찾는 기능을 이용할 수 있지만, data 내에서 찾지 않고 전체 페이지에서 값을 찾는다.

 

search 기능을 구현하여 검색하면 data 내에서만 검색이 가능하다.

 

먼저 데이터를 검색할 필드(search_field)와 검색 결과로 나온 개수를 만들기 위한 span 태그를 추가한다.

    <div>
      <Box sx={{ m: 2 }}>
        <input id="search_field" type="search" placeholder="search" />
        <p>
          <span id="resultCount">0</span> results
        </p>
        <div id="hot-app"></div>
      </Box>
    </div>

 

옵션에서 search를 추가한다.

callback은 search 결과를 알려주면, queryMethod는 검색 방법을 바꿀 수 있다.

searchResultClass는 검색된 결과에 대한 css를 수정할 수 있다.

  const options = {
    data,

    ...
    
    search: {
      callback: searchResultCounter,
      //queryMethod: myNewQueryMethod,
      //searchResultClass: 'customClass'
    },

    licenseKey: "non-commercial-and-evaluation",
  };

 

searchResultCounter는 다음과 같다.

let searchResultCount = 0;
function searchResultCounter(instance, row, col, value, result) {
  const DEFAULT_CALLBACK = function(instance, row, col, data, testResult) {
    instance.getCellMeta(row, col).isSearchResult = testResult;
  };

  DEFAULT_CALLBACK.apply(this, arguments);

  if (result) {
    searchResultCount++;
  }
}

 

addEvent에 keyup을 아래와 같이 등록하면 된다.

  const makeTable = () => {
    const container = document.getElementById("hot-app");
    container.innerHTML = "";

    const myTable = new Handsontable(container, options);
    
    let searchField = document.getElementById("search_field");
    let resultCount = document.getElementById("resultCount");

    Handsontable.dom.addEvent(searchField, "keyup", function(event) {
      searchResultCount = 0;

      let search = myTable.getPlugin("search");
      let queryResult = search.query(this.value);

      console.log(queryResult);

      resultCount.innerText = searchResultCount.toString();
      myTable.render();
    });
  };

queryMethod 구현하기

 

위의 경우 5가 포함된 15도 검색이 된다.

하지만 queryMethod를 이용하여 정확히 일치하는 값만 나오도록 구현할 수 있다.

 

search에서 queryMethod를 추가한다.

  search: {
    callback: searchResultCounter,
    queryMethod: myNewQueryMethod,
    //searchResultClass: 'customClass'
  },

 

myNewQueryMethod는 다음과 같이 구현한다.

비교할 data에 null이 있는 경우, 빈 문자열로 변경한다.

그리고 string으로 변환하여 값이 같은 경우 true를 리턴하도록 하였다.

const myNewQueryMethod = (searchValue, dataValue) => {
  if(!searchValue) return false;
  
  dataValue = dataValue || "";
  return searchValue.toString() === dataValue.toString();
}

focus

 

특정 셀에 포커싱을 하는 메서드는 다음과 같다.

myTable.scrollViewportTo(2, 2); // 특정 셀로 이동
myTable.selectCell(2, 2); // 특정 셀 선택

 

queryResult에는 row와 col 정보가 담겨져 있으므로, 해당 정보를 useState로 관리해서 셀을 포커싱하면 된다.

  const makeTable = () => {
    ...
    Handsontable.dom.addEvent(searchField, "keyup", function(event) {
      searchResultCount = 0;

      let search = myTable.getPlugin("search");
      let queryResult = search.query(this.value);

      console.log(queryResult); // useState 배열로 관리

      resultCount.innerText = searchResultCount.toString();
      myTable.render();
    });
  };
반응형

댓글