Search code examples
jquery-select2

How do I make a link open in an option


I added a link to the options, but when clicked only the option is selected. How do I make the link open without making a selection?

$(document).ready(function() {
  $('.js-select-multi').select2({
    placeholder: 'Select an option',
    templateResult: formatOption
  });

  function formatOption(option) {
    var $option_text = '';
    var $option_details = '';
    var $option_url = '';

    $option_head = $(
      '<div style="display: flex; flex-direction: column; flex-wrap: wrap; justify-content: space-between;">'
    );

    $option_text = $(
      '<div style="font-size: 14px; min-width: 70%; height: 100%;">' + option.text + '</div>'
    );

    if ($(option.element).data('details')) {
      $option_details = $(
        '<div style="font-size: 10px; min-width: 70%; height: 100%;">' + $(option.element).data('details') + '</div>'
      );
    }

    if ($(option.element).data('url')) {
      $option_url = $(
        '<div style="font-size: 9px; height: 100%; width: 30%;"><a href="' + $(option.element).data('url') + '">Preview</a></div>'
      );
    }

    $option_foot = $(
      '</div>'
    );

    return $option_head.append($option_text).append($option_details).append($option_url).append($option_foot);
  }
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/js/select2.min.js"></script>
<link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/select2.min.css" rel="stylesheet" />

<div id="main">
  <select class="js-select-multi" name="demos[]" id="userInput" style="width: 650px;" multiple="multiple">
    <optgroup label="Opt Group 1">
      <option value="90d1aba6" data-details="Customer" data-url="https://yahoo.com">Option #1</option>
      <option value="238e894f" data-details="Customer" data-url="https://yahoo.com">Option #2</option>
    </optgroup>
    <optgroup label="Opt Group 2">
      <option value="574b18e9" data-details="Customer" data-url="https://yahoo.com">Option #3</option>
      <option value="5b626e8b" data-details="Customer" data-url="https://yahoo.com">Option #4</option>
    </optgroup>
  </select>
</div>


Solution

  • I was able to get this to work with version 3.5.4 of select2. Does not work on select2 4.x

    $(document).ready(function() {
      var select2 = $(".js-select-multi").select2({
        formatResult: format,
        allowClear: true
      }).data('select2');
    
      select2.onSelect = (function(fn) {
        return function(data, options) {
          var target;
    
          if (options != null) {
            target = $(options.target);
          }
    
          if (target && target.hasClass('link')) {
            target_url = $(data.element).data('url');
            //alert(target_url);
            var win = window.open(target_url, '_blank');
            if (win) {
              //Browser has allowed it to be opened
              win.focus();
            } else {
              //Browser has blocked it
              alert('Please allow popup to preview demoboards');
            }
          } else {
            return fn.apply(this, arguments);
          }
        }
      })(select2.onSelect);
    
      function format(option) {
        if (!option.id) {
          return option.text; // optgroup
        } else {
          var $option_text = '';
          var $option_details = '';
          var $option_url = '';
    
          $option_head = $(
            '<div style="display: flex; flex-direction: column; flex-wrap: wrap; justify-content: space-between;">'
          );
    
          $option_text = $(
            '<div style="font-size: 14px; min-width: 70%; height: 100%;">' + option.text + '</div>'
          );
    
          if ($(option.element).data('details')) {
            $option_details = $(
              '<div style="font-size: 10px; min-width: 70%; height: 100%;">' + $(option.element).data('details') + '</div>'
            );
          }
    
          if ($(option.element).data('url')) {
            $option_url = $(
              '<div style="font-size: 9px; height: 100%; width: 30%;"><a class="link" href="' + $(option.element).data('url') + '">Preview</a></div>'
            );
          }
    
          $option_foot = $(
            '</div>'
          );
    
          return $option_head.append($option_text).append($option_details).append($option_url).append($option_foot);
        }
      }
    
    });
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
    <link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/select2/3.5.4/select2.min.css">
    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/select2/3.5.4/select2.min.js"></script>
    
      <select class="js-select-multi" name="demos[]" id="userInput" style="width: 650px;" multiple="multiple">
        <optgroup label="Opt Group 1">
          <option value="90d1aba6" data-details="Customer" data-url="https://yahoo.com">Option #1</option>
          <option value="238e894f" data-details="Customer" data-url="https://yahoo.com">Option #2</option>
        </optgroup>
        <optgroup label="Opt Group 2">
          <option value="574b18e9" data-details="Customer" data-url="https://yahoo.com">Option #3</option>
          <option value="5b626e8b" data-details="Customer" data-url="https://yahoo.com">Option #4</option>
        </optgroup>
      </select>