쿼리빌더에서 제공하는 특정 플러그인들은 따로 선언해 줄 필요 없이 사용이 가능하다.
디자인 적인 부분을 활용 가능한 플러그인은 대부분 부트스트랩 기반의 플러그인 들이고,
DB 임포트/익스포트 그리고 기본적으로 제공하는 필터, 규칙 이외에 새로운 기능을 추가하기 위한 플러그인도 제공한다.

이전 쿼리빌더에 jQuery Select2 플러그인 추가해 셀렉트 스타일이나 기능 추가 해 보았다.

쿼리빌더의 기본 규칙(rule)은 Filter + Operator(연산자) + 값(value) 으로 구성되어 있는데,
여기서 Operator는 총 20개의 연산자를 포함하고 있고, 페이지 내에 쿼리빌더를 선언 할 때에
Filter별로 원하는 operator를 단일 또는 복수로 선택하여 규칙을 만들 수 있다.

위의 공식 예제를 보면 특정 필터에서 연산자가 단 한 개만 설정되는 경우에,
해당 연산자가 텍스트로 노출되고 select input이 생략되도록 설정되어 있다.

그런데 select2를 추가하고 단일 연산자로 설정을 해보면 아래와 같이 연산자가 두 번 노출 된다.

공식 예제와 다르게 중복 노출되는 이유는,
기본 라이브러리에서는 단일 operator 설정 시,
쿼리빌더 템플릿에서 조건문을 걸어 기본 select input을 숨김처리 하도록 설정 되어있다.

QueryBuilder.templates.operatorSelect ='\
{{? it.operators.length === 1 }} \
<span> \
{{= it.translate("operators", it.operators[0].type) }} \
</span> \
{{?}} \
{{ var optgroup = null; }} \
<select class="form-control {{? it.operators.length === 1 }}hide{{?}}" name="{{= it.rule.id }}_operator"> \
{{~ it.operators: operator }} \
  {{? optgroup !== operator.optgroup }} \
    {{? optgroup !== null }}</optgroup>{{?}} \
    {{? (optgroup = operator.optgroup) !== null }} \
      <optgroup label="{{= it.translate(it.settings.optgroups[optgroup]) }}"> \
    {{?}} \
  {{?}} \
  <option value="{{= operator.type }}" {{? operator.icon}}data-icon="{{= operator.icon}}"{{?}}>{{= it.translate("operators", operator.type) }}</option> \
{{~}} \
{{? optgroup !== null }}</optgroup>{{?}} \
</select>';

코드뷰에서 하이라이트 된 부분을 확인 해보면 operators.length가 하나 일 경우,
operator 타입을 텍스트로 노출하고 아래의 select input은 hide 처리하고 있다.

원하는 스타일은 위의 그림과 같이 Filter에서 value의 값만 선택 할 수 있도록
두 개의 조건만 보여지게 operator를 숨기는 거다.
해당 Filter에서 선택 또는 입력한 value값과
일치(equal) 또는 포함(contains) 등과 같은 연산자를 노출 시키지 않아도
문제가 없는 경우 활용하면 될 것 같다.

QueryBuilder.templates.operatorSelect ='\





{{ var optgroup = null; }} \
<select class="form-control {{? it.operators.length === 1 }}hide{{?}}" name="{{= it.rule.id }}_operator"> \
{{~ it.operators: operator }} \
  {{? optgroup !== operator.optgroup }} \
    {{? optgroup !== null }}</optgroup>{{?}} \
    {{? (optgroup = operator.optgroup) !== null }} \
      <optgroup label="{{= it.translate(it.settings.optgroups[optgroup]) }}"> \
    {{?}} \
  {{?}} \
  <option value="{{= operator.type }}" {{? operator.icon}}data-icon="{{= operator.icon}}"{{?}}>{{= it.translate("operators", operator.type) }}</option> \
{{~}} \
{{? optgroup !== null }}</optgroup>{{?}} \
</select>';

2-5번째 라인에 있던 operator를 텍스트로 노출하게 하는
코드를 삭제하면 아래와 같이 텍스트가 중복 노출되던 부분은 삭제된 것을 확인 할 수 있다.
단 삭제한 라인을 보이기 위해서 공백으로 남겨두었지만, 실제로 공백을 남기면
코드 에러가 나므로 공백 없이 해당 코드를 삭제하자.

이제 여기서 가운데 operator를 숨겨보자.
추가했던 select2 plugin 모듈 코드에서 operator 영역에 조건문을 걸어 operator의 값이 1개 일 때 select2를 해제한다.


select2를 선언함으로써 쿼리빌더의 select input 코드를 강제 숨김 처리하고 select2 코드로 대체하는데,
선언한 select2를 해제함으로써 쿼리빌더의 기본 select input template에 설정되어 있는 select input 자체 숨김 처리를 활용한다.

<select class="form-control {{? it.operators.length === 1 }}hide{{?}}" name="{{= it.rule.id }}_operator"> \

쿼리빌더 연산자셀렉트 기본 템플릿 설정을 보면 위와 같이 operators.length가 1개 일 때
hide라는 클래스를 추가해서 기본 select input을 숨기고 위에서 삭제했던 텍스트를 대신 노출하도록 되어있다.

혹, hide라는 클래스가 추가 되어도 기본 select input만 보여지는 경우는 bootstrap 상위 버전을 사용해서 그럴 수 있다.
상위버전을 사용하는 경우 위의 코드에서 hide를 d-none으로 변경해주면 문제 없이 숨김 처리 되어 보인다.

     this.on('afterCreateRuleOperators', function (e, rule) {
        rule.$el
          .find(Selectors.rule_operator)
          .removeClass('form-control')
          .select2(options);
      });

select2 플러그인 모듈 코드에서 ‘afterCreateRuleOperators’ 부분을 찾아서
모든 select input을 select2로 교체하는 설정에서 조건문을 추가한다.

    this.on('afterCreateRuleOperators', function(e, rule) { 

        // init variable rule-operator selectors' dom
        var ruleOpDom = rule.$el.find(Selectors.rule_operator)[0];

        // 모든 rule-operator 셀렉트를 select2로 변경 선언
        rule.$el.find(Selectors.rule_operator).removeClass('form-control').select2(options);

        // only option case, destroy select2 and hide selector
        if(ruleOpDom.length === 1) {
            rule.$el.find(Selectors.rule_operator).select2('destroy');
        } 
    });

위의 코드를 적용하고 나면 아래와 같이 operator 셀렉트는 숨김처리 되어 보이지 않는다.


Leave a Reply

Your email address will not be published. Required fields are marked *