Browse Source

Added RTL support to Select2

This works in the same way as the `lang` option, which pulls
directly from the `dir` property on DOM nodes.
Kevin Brown 10 years ago
parent
commit
e7c2c70d1a

+ 35 - 0
dist/css/select2.css

@@ -19,6 +19,10 @@
     padding-right: 20px;
     text-overflow: ellipsis; }
 
+[dir="rtl"] .select2-selection--single .select2-selection__rendered {
+  padding-right: 8px;
+  padding-left: 20px; }
+
 .select2-selection--multiple {
   box-sizing: border-box;
   cursor: pointer;
@@ -134,6 +138,11 @@
       position: absolute;
       top: 50%;
       width: 0; }
+.select2-container--default[dir="rtl"] .select2-selection--single .select2-selection__clear {
+  float: left; }
+.select2-container--default[dir="rtl"] .select2-selection--single .select2-selection__arrow {
+  left: 1px;
+  right: auto; }
 .select2-container--default.select2-container--disabled .select2-selection--single {
   background-color: #eee;
   cursor: default; }
@@ -170,6 +179,14 @@
     margin-right: 2px; }
     .select2-container--default .select2-selection--multiple .select2-selection__choice__remove:hover {
       color: #333; }
+.select2-container--default[dir="rtl"] .select2-selection--multiple .select2-selection__choice, .select2-container--default[dir="rtl"] .select2-selection--multiple .select2-selection__placeholder {
+  float: right; }
+.select2-container--default[dir="rtl"] .select2-selection--multiple .select2-selection__choice {
+  margin-left: 5px;
+  margin-right: auto; }
+.select2-container--default[dir="rtl"] .select2-selection--multiple .select2-selection__choice__remove {
+  margin-left: 2px;
+  margin-right: auto; }
 .select2-container--default.select2-container--disabled .select2-selection--multiple {
   background-color: #eee;
   cursor: default; }
@@ -251,6 +268,16 @@
       position: absolute;
       top: 50%;
       width: 0; }
+.select2-container--classic[dir="rtl"] .select2-selection--single .select2-selection__clear {
+  float: left; }
+.select2-container--classic[dir="rtl"] .select2-selection--single .select2-selection__arrow {
+  border: none;
+  border-right: 1px solid #aaa;
+  border-radius: 0;
+  border-top-left-radius: 4px;
+  border-bottom-left-radius: 4px;
+  left: 1px;
+  right: auto; }
 .select2-container--classic.select2-container--open .select2-selection--single {
   border: 1px solid #5897fb; }
   .select2-container--classic.select2-container--open .select2-selection--single .select2-selection__arrow {
@@ -306,6 +333,14 @@
     margin-right: 2px; }
     .select2-container--classic .select2-selection--multiple .select2-selection__choice__remove:hover {
       color: #555; }
+.select2-container--classic[dir="rtl"] .select2-selection--multiple .select2-selection__choice {
+  float: right; }
+.select2-container--classic[dir="rtl"] .select2-selection--multiple .select2-selection__choice {
+  margin-left: 5px;
+  margin-right: auto; }
+.select2-container--classic[dir="rtl"] .select2-selection--multiple .select2-selection__choice__remove {
+  margin-left: 2px;
+  margin-right: auto; }
 .select2-container--classic.select2-container--open .select2-selection--multiple {
   border: 1px solid #5897fb; }
 .select2-container--classic.select2-container--open.select2-container--above .select2-selection--multiple {

File diff suppressed because it is too large
+ 0 - 0
dist/css/select2.min.css


+ 17 - 1
dist/js/select2.amd.full.js

@@ -2347,7 +2347,6 @@ define('select2/data/select',[
     }
 
     item = $.extend({}, {
-      id: '',
       text: ''
     }, item);
 
@@ -2685,6 +2684,9 @@ define('select2/dropdown',[
 ], function (Utils) {
   function Dropdown ($element, options) {
     this.$element = $element;
+    this.options = options;
+
+    Dropdown.__super__.constructor.call(this);
   }
 
   Utils.Extend(Dropdown, Utils.Observable);
@@ -2696,6 +2698,8 @@ define('select2/dropdown',[
       '</span>'
     );
 
+    $dropdown.attr('dir', this.options.get('dir'));
+
     this.$dropdown = $dropdown;
 
     return $dropdown;
@@ -3445,6 +3449,16 @@ define('select2/options',[
       }
     }
 
+    if (this.options.dir == null) {
+      if ($e.prop('dir')) {
+        this.options.dir = $e.prop('dir');
+      } else if ($e.closest('[dir]').prop('dir')) {
+        this.options.dir = $e.closest('[dir]').prop('dir');
+      } else {
+        this.options.dir = 'ltr';
+      }
+    }
+
     $e.prop('disabled', this.options.disabled);
     $e.prop('multiple', this.options.multiple);
 
@@ -3940,6 +3954,8 @@ define('select2/core',[
       '</span>'
     );
 
+    $container.attr('dir', this.options.get('dir'));
+
     this.$container = $container;
 
     this.$container.addClass('select2-container--' + this.options.get('theme'));

+ 17 - 1
dist/js/select2.amd.js

@@ -2347,7 +2347,6 @@ define('select2/data/select',[
     }
 
     item = $.extend({}, {
-      id: '',
       text: ''
     }, item);
 
@@ -2685,6 +2684,9 @@ define('select2/dropdown',[
 ], function (Utils) {
   function Dropdown ($element, options) {
     this.$element = $element;
+    this.options = options;
+
+    Dropdown.__super__.constructor.call(this);
   }
 
   Utils.Extend(Dropdown, Utils.Observable);
@@ -2696,6 +2698,8 @@ define('select2/dropdown',[
       '</span>'
     );
 
+    $dropdown.attr('dir', this.options.get('dir'));
+
     this.$dropdown = $dropdown;
 
     return $dropdown;
@@ -3445,6 +3449,16 @@ define('select2/options',[
       }
     }
 
+    if (this.options.dir == null) {
+      if ($e.prop('dir')) {
+        this.options.dir = $e.prop('dir');
+      } else if ($e.closest('[dir]').prop('dir')) {
+        this.options.dir = $e.closest('[dir]').prop('dir');
+      } else {
+        this.options.dir = 'ltr';
+      }
+    }
+
     $e.prop('disabled', this.options.disabled);
     $e.prop('multiple', this.options.multiple);
 
@@ -3940,6 +3954,8 @@ define('select2/core',[
       '</span>'
     );
 
+    $container.attr('dir', this.options.get('dir'));
+
     this.$container = $container;
 
     this.$container.addClass('select2-container--' + this.options.get('theme'));

+ 17 - 1
dist/js/select2.full.js

@@ -11882,7 +11882,6 @@ define('select2/data/select',[
     }
 
     item = $.extend({}, {
-      id: '',
       text: ''
     }, item);
 
@@ -12220,6 +12219,9 @@ define('select2/dropdown',[
 ], function (Utils) {
   function Dropdown ($element, options) {
     this.$element = $element;
+    this.options = options;
+
+    Dropdown.__super__.constructor.call(this);
   }
 
   Utils.Extend(Dropdown, Utils.Observable);
@@ -12231,6 +12233,8 @@ define('select2/dropdown',[
       '</span>'
     );
 
+    $dropdown.attr('dir', this.options.get('dir'));
+
     this.$dropdown = $dropdown;
 
     return $dropdown;
@@ -12980,6 +12984,16 @@ define('select2/options',[
       }
     }
 
+    if (this.options.dir == null) {
+      if ($e.prop('dir')) {
+        this.options.dir = $e.prop('dir');
+      } else if ($e.closest('[dir]').prop('dir')) {
+        this.options.dir = $e.closest('[dir]').prop('dir');
+      } else {
+        this.options.dir = 'ltr';
+      }
+    }
+
     $e.prop('disabled', this.options.disabled);
     $e.prop('multiple', this.options.multiple);
 
@@ -13475,6 +13489,8 @@ define('select2/core',[
       '</span>'
     );
 
+    $container.attr('dir', this.options.get('dir'));
+
     this.$container = $container;
 
     this.$container.addClass('select2-container--' + this.options.get('theme'));

File diff suppressed because it is too large
+ 0 - 0
dist/js/select2.full.min.js


+ 17 - 1
dist/js/select2.js

@@ -2775,7 +2775,6 @@ define('select2/data/select',[
     }
 
     item = $.extend({}, {
-      id: '',
       text: ''
     }, item);
 
@@ -3113,6 +3112,9 @@ define('select2/dropdown',[
 ], function (Utils) {
   function Dropdown ($element, options) {
     this.$element = $element;
+    this.options = options;
+
+    Dropdown.__super__.constructor.call(this);
   }
 
   Utils.Extend(Dropdown, Utils.Observable);
@@ -3124,6 +3126,8 @@ define('select2/dropdown',[
       '</span>'
     );
 
+    $dropdown.attr('dir', this.options.get('dir'));
+
     this.$dropdown = $dropdown;
 
     return $dropdown;
@@ -3873,6 +3877,16 @@ define('select2/options',[
       }
     }
 
+    if (this.options.dir == null) {
+      if ($e.prop('dir')) {
+        this.options.dir = $e.prop('dir');
+      } else if ($e.closest('[dir]').prop('dir')) {
+        this.options.dir = $e.closest('[dir]').prop('dir');
+      } else {
+        this.options.dir = 'ltr';
+      }
+    }
+
     $e.prop('disabled', this.options.disabled);
     $e.prop('multiple', this.options.multiple);
 
@@ -4368,6 +4382,8 @@ define('select2/core',[
       '</span>'
     );
 
+    $container.attr('dir', this.options.get('dir'));
+
     this.$container = $container;
 
     this.$container.addClass('select2-container--' + this.options.get('theme'));

File diff suppressed because it is too large
+ 0 - 0
dist/js/select2.min.js


+ 33 - 1
docs/examples.html

@@ -321,7 +321,7 @@ $(".js-programmatic-disable").on("click", function () {
     </div>
   </section>
 
-  <section id="tagss" class="row">
+  <section id="programmatic" class="row">
     <div class="col-md-4">
       <h1>Programmatic access</h1>
 
@@ -585,6 +585,36 @@ $(".js-example-language").select2({
       </script>
     </div>
   </section>
+
+  <section id="rtl" class="row">
+    <div class="col-md-4">
+      <h1>RTL support</h1>
+
+      <p>
+        Select2 will work on RTL websites if the <code>dir</code> attribute is
+        set on the <code>&lt;select&gt;</code> or any parents of it.
+      </p>
+
+      <p>
+        <select class="js-example-rtl js-states form-control" dir="rtl"></select>
+      </p>
+
+      <p>
+        You can also use initialize Select2 with <code>dir: "rtl"</code> set.
+      </p>
+    </div>
+    <div class="col-md-8">
+      <h2>Example code</h2>
+
+      <pre data-fill-from=".js-code-theme"></pre>
+
+      <script type="text/x-example-code" class="js-code-rtl">
+      $(".js-example-rtl").select2({
+        dir: "rtl"
+      });
+      </script>
+    </div>
+  </section>
 </div>
 
 <select class="js-source-states" style="display: none;">
@@ -788,5 +818,7 @@ $.fn.select2.amd.require(
   $(".js-example-theme-multiple").select2({
     theme: "classic"
   });
+
+  $(".js-example-rtl").select2();
 });
 </script>

+ 2 - 0
src/js/select2/core.js

@@ -426,6 +426,8 @@ define([
       '</span>'
     );
 
+    $container.attr('dir', this.options.get('dir'));
+
     this.$container = $container;
 
     this.$container.addClass('select2-container--' + this.options.get('theme'));

+ 0 - 1
src/js/select2/data/select.js

@@ -224,7 +224,6 @@ define([
     }
 
     item = $.extend({}, {
-      id: '',
       text: ''
     }, item);
 

+ 5 - 0
src/js/select2/dropdown.js

@@ -3,6 +3,9 @@ define([
 ], function (Utils) {
   function Dropdown ($element, options) {
     this.$element = $element;
+    this.options = options;
+
+    Dropdown.__super__.constructor.call(this);
   }
 
   Utils.Extend(Dropdown, Utils.Observable);
@@ -14,6 +17,8 @@ define([
       '</span>'
     );
 
+    $dropdown.attr('dir', this.options.get('dir'));
+
     this.$dropdown = $dropdown;
 
     return $dropdown;

+ 10 - 0
src/js/select2/options.js

@@ -31,6 +31,16 @@ define([
       }
     }
 
+    if (this.options.dir == null) {
+      if ($e.prop('dir')) {
+        this.options.dir = $e.prop('dir');
+      } else if ($e.closest('[dir]').prop('dir')) {
+        this.options.dir = $e.closest('[dir]').prop('dir');
+      } else {
+        this.options.dir = 'ltr';
+      }
+    }
+
     $e.prop('disabled', this.options.disabled);
     $e.prop('multiple', this.options.multiple);
 

+ 9 - 0
src/scss/_single.scss

@@ -17,3 +17,12 @@
     text-overflow: ellipsis;
   }
 }
+
+&[dir="rtl"] {
+  .select2-selection--single {
+    .select2-selection__rendered {
+      padding-right: 8px;
+      padding-left: 20px;
+    }
+  }
+}

+ 18 - 0
src/scss/theme/classic/_multiple.scss

@@ -48,6 +48,24 @@
   }
 }
 
+&[dir="rtl"] {
+  .select2-selection--multiple {
+    .select2-selection__choice {
+      float: right;
+    }
+
+    .select2-selection__choice {
+      margin-left: 5px;
+      margin-right: auto;
+    }
+
+    .select2-selection__choice__remove {
+      margin-left: 2px;
+      margin-right: auto;
+    }
+  }
+}
+
 &.select2-container--open {
   .select2-selection--multiple {
     border: 1px solid $focus-border-color;

+ 20 - 0
src/scss/theme/classic/_single.scss

@@ -66,6 +66,26 @@
   }
 }
 
+&[dir="rtl"] {
+  .select2-selection--single {
+    .select2-selection__clear {
+      float: left;
+    }
+
+    .select2-selection__arrow {
+      border: none;
+      border-right: 1px solid $border-color;
+
+      border-radius: 0;
+      border-top-left-radius: $border-radius;
+      border-bottom-left-radius: $border-radius;
+
+      left: 1px;
+      right: auto;
+    }
+  }
+}
+
 &.select2-container--open {
   .select2-selection--single {
     border: 1px solid $focus-border-color;

+ 18 - 0
src/scss/theme/default/_multiple.scss

@@ -47,6 +47,24 @@
   }
 }
 
+&[dir="rtl"] {
+  .select2-selection--multiple {
+    .select2-selection__choice, .select2-selection__placeholder {
+      float: right;
+    }
+
+    .select2-selection__choice {
+      margin-left: 5px;
+      margin-right: auto;
+    }
+
+    .select2-selection__choice__remove {
+      margin-left: 2px;
+      margin-right: auto;
+    }
+  }
+}
+
 &.select2-container--disabled {
   .select2-selection--multiple {
     background-color: #eee;

+ 13 - 0
src/scss/theme/default/_single.scss

@@ -47,6 +47,19 @@
   }
 }
 
+&[dir="rtl"] {
+  .select2-selection--single {
+    .select2-selection__clear {
+      float: left;
+    }
+
+    .select2-selection__arrow {
+      left: 1px;
+      right: auto;
+    }
+  }
+}
+
 &.select2-container--disabled {
   .select2-selection--single {
     background-color: #eee;

Some files were not shown because too many files changed in this diff