Skip to content

Commit 7956d7a

Browse files
author
jfoster
committed
Add option to automatically size dropdown width
1 parent 6a29e59 commit 7956d7a

2 files changed

Lines changed: 51 additions & 10 deletions

File tree

select2.css

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -147,6 +147,15 @@ Version: @@ver@@ Timestamp: @@timestamp@@
147147
box-shadow: 0 4px 5px rgba(0, 0, 0, .15);
148148
}
149149

150+
.select2-drop-auto-width {
151+
border-top: 1px solid #aaa;
152+
width: auto;
153+
}
154+
155+
.select2-drop-auto-width .select2-search {
156+
padding-top: 4px;
157+
}
158+
150159
.select2-drop.select2-drop-above {
151160
margin-top: 1px;
152161
border-top: 1px solid #aaa;

select2.js

Lines changed: 42 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ the specific language governing permissions and limitations under the Apache Lic
4747
}
4848

4949
var KEY, AbstractSelect2, SingleSelect2, MultiSelect2, nextUid, sizer,
50-
lastMousePosition, $document;
50+
lastMousePosition, $document, scrollBarDimensions,
5151

5252
KEY = {
5353
TAB: 9,
@@ -95,7 +95,8 @@ the specific language governing permissions and limitations under the Apache Lic
9595
k = k.which ? k.which : k;
9696
return k >= 112 && k <= 123;
9797
}
98-
};
98+
},
99+
MEASURE_SCROLLBAR_TEMPLATE = "<div style='position:absolute; top:-10000px; left:-10000px; width:100px; height:100px; overflow:scroll;'></div>";
99100

100101
$document = $(document);
101102

@@ -109,6 +110,19 @@ the specific language governing permissions and limitations under the Apache Lic
109110
return -1;
110111
}
111112

113+
function measureScrollbar () {
114+
var $template = $( MEASURE_SCROLLBAR_TEMPLATE );
115+
$template.appendTo('body');
116+
117+
var dim = {
118+
width: $template.width() - $template[0].clientWidth,
119+
height: $template.height() - $template[0].clientHeight
120+
};
121+
$template.remove();
122+
123+
return dim;
124+
}
125+
112126
/**
113127
* Compares equality of a and b
114128
* @param a
@@ -691,6 +705,9 @@ the specific language governing permissions and limitations under the Apache Lic
691705
}
692706

693707
if (opts.element.is(":disabled") || opts.element.is("[readonly='readonly']")) this.disable();
708+
709+
// Calculate size of scrollbar
710+
scrollBarDimensions = scrollBarDimensions || measureScrollbar();
694711
},
695712

696713
// abstract
@@ -977,22 +994,37 @@ the specific language governing permissions and limitations under the Apache Lic
977994

978995
// abstract
979996
positionDropdown: function() {
980-
var offset = this.container.offset(),
997+
var $dropdown = this.dropdown,
998+
offset = this.container.offset(),
981999
height = this.container.outerHeight(false),
9821000
width = this.container.outerWidth(false),
983-
dropHeight = this.dropdown.outerHeight(false),
1001+
dropHeight = $dropdown.outerHeight(false),
9841002
viewPortRight = $(window).scrollLeft() + $(window).width(),
9851003
viewportBottom = $(window).scrollTop() + $(window).height(),
9861004
dropTop = offset.top + height,
9871005
dropLeft = offset.left,
9881006
enoughRoomBelow = dropTop + dropHeight <= viewportBottom,
9891007
enoughRoomAbove = (offset.top - dropHeight) >= this.body().scrollTop(),
990-
dropWidth = this.dropdown.outerWidth(false),
1008+
dropWidth = $dropdown.outerWidth(false),
9911009
enoughRoomOnRight = dropLeft + dropWidth <= viewPortRight,
992-
aboveNow = this.dropdown.hasClass("select2-drop-above"),
1010+
aboveNow = $dropdown.hasClass("select2-drop-above"),
9931011
bodyOffset,
9941012
above,
995-
css;
1013+
css,
1014+
resultsListNode;
1015+
1016+
if (this.opts.dropdownAutoWidth) {
1017+
resultsListNode = $('.select2-results', $dropdown)[0];
1018+
$dropdown.addClass('select2-drop-auto-width');
1019+
$dropdown.css('width', '');
1020+
// Add scrollbar width to dropdown if vertical scrollbar is present
1021+
dropWidth = $dropdown.outerWidth(false) + (resultsListNode.scrollHeight === resultsListNode.clientHeight ? 0 : scrollBarDimensions.width);
1022+
dropWidth > width ? width = dropWidth : dropWidth = width;
1023+
enoughRoomOnRight = dropLeft + dropWidth <= viewPortRight;
1024+
}
1025+
else {
1026+
this.container.removeClass('select2-drop-auto-width');
1027+
}
9961028

9971029
//console.log("below/ droptop:", dropTop, "dropHeight", dropHeight, "sum", (dropTop+dropHeight)+" viewport bottom", viewportBottom, "enough?", enoughRoomBelow);
9981030
//console.log("above/ offset.top", offset.top, "dropHeight", dropHeight, "top", (offset.top-dropHeight), "scrollTop", this.body().scrollTop(), "enough?", enoughRoomAbove);
@@ -1022,11 +1054,11 @@ the specific language governing permissions and limitations under the Apache Lic
10221054
if (above) {
10231055
dropTop = offset.top - dropHeight;
10241056
this.container.addClass("select2-drop-above");
1025-
this.dropdown.addClass("select2-drop-above");
1057+
$dropdown.addClass("select2-drop-above");
10261058
}
10271059
else {
10281060
this.container.removeClass("select2-drop-above");
1029-
this.dropdown.removeClass("select2-drop-above");
1061+
$dropdown.removeClass("select2-drop-above");
10301062
}
10311063

10321064
css = $.extend({
@@ -1035,7 +1067,7 @@ the specific language governing permissions and limitations under the Apache Lic
10351067
width: width
10361068
}, evaluate(this.opts.dropdownCss));
10371069

1038-
this.dropdown.css(css);
1070+
$dropdown.css(css);
10391071
},
10401072

10411073
// abstract

0 commit comments

Comments
 (0)