nuevo comportamiento para dropDown, abrir arriba

This commit is contained in:
Daniel Herrero 2017-11-23 14:07:55 +01:00
parent 5ad2c70400
commit 00bd4a7696
3 changed files with 69 additions and 20 deletions

View File

@ -1,11 +1,11 @@
<vn-vertical class="dropdown-body" ng-show="$ctrl.show"> <vn-vertical class="dropdown-body" ng-show="$ctrl.show">
<vn-one ng-show="$ctrl.filter" class="filter"> <vn-auto ng-show="$ctrl.filter" class="filter">
<vn-horizontal> <vn-horizontal>
<input vn-one placeholder="{{'Search' | translate}}" type="text" ng-model="$ctrl.search"/> <input vn-one placeholder="{{'Search' | translate}}" type="text" ng-model="$ctrl.search"/>
<vn-icon vn-none icon="clear" ng-click="$ctrl.clearSearch()"></vn-icon> <vn-icon vn-none icon="clear" ng-click="$ctrl.clearSearch()"></vn-icon>
</vn-horizontal> </vn-horizontal>
</vn-one> </vn-auto>
<vn-one> <vn-auto>
<ul class="dropdown"> <ul class="dropdown">
<li tabIndex="-1" <li tabIndex="-1"
ng-repeat="item in $ctrl.itemsFiltered track by $index" ng-repeat="item in $ctrl.itemsFiltered track by $index"
@ -25,5 +25,5 @@
translate="{{$ctrl.showLoadMore ? 'Show More' : 'No more results'}}" translate="{{$ctrl.showLoadMore ? 'Show More' : 'No more results'}}"
></li> ></li>
</ul> </ul>
</vn-one> </vn-auto>
</vn-vertical> </vn-vertical>

View File

@ -12,6 +12,7 @@ export default class DropDown {
this.itemsFiltered = []; this.itemsFiltered = [];
this._activeOption = -1; this._activeOption = -1;
this._focusingFilter = false; this._focusingFilter = false;
this._tryToShow = 0;
} }
get show() { get show() {
return this._show; return this._show;
@ -19,11 +20,20 @@ export default class DropDown {
set show(value) { set show(value) {
let oldValue = this.show; let oldValue = this.show;
this._show = value; // I wait up to 1 second if the dropdown opens but there is no data to show
this._setFocusInFilterInput(value, oldValue); if (value && !oldValue && !this.itemsFiltered.length && this._tryToShow < 4) {
this.$timeout(() => { this.$timeout(() => {
this._calculatePosition(value, oldValue); this._tryToShow++;
}); this.show = true;
}, 250);
} else {
this._tryToShow = 0;
this._show = value;
this._setFocusInFilterInput(value, oldValue);
this.$timeout(() => {
this._calculatePosition(value, oldValue);
});
}
} }
get search() { get search() {
@ -68,21 +78,42 @@ export default class DropDown {
}, 250); }, 250);
} }
} }
_background(create) {
let el = document.getElementById('ddBack');
if (el) {
el.parentNode.removeChild(el);
}
if (create) {
el = document.createElement('div');
el.id = 'ddBack';
document.body.appendChild(el);
}
}
_calculatePosition(value, oldValue) { _calculatePosition(value, oldValue) {
if (value && value !== oldValue && !this.top) { if (value && !oldValue) {
if (this.parent === undefined) { if (this.parent === undefined) {
this.parent = this.$element.parent().parent(); this.parent = this.$element.parent().parent();
} }
let parentRect = this.parent.getBoundingClientRect(); let parentRect = this.parent.getBoundingClientRect();
let elemetRect = this.$element[0].getBoundingClientRect(); let elemetRect = this.$element[0].getBoundingClientRect();
let instOffset = parentRect.bottom + elemetRect.height;
if (parentRect.y + parentRect.height + elemetRect.height > window.innerHeight) { if (instOffset >= window.innerHeight) {
let height = this.parent.nodeName === 'VN-AUTOCOMPLETE' ? elemetRect.height : elemetRect.height + parentRect.height; this._background(true);
this.$element.css('margin-top', `-${height}px`); this.$element.addClass('fixed-dropDown');
} else { this.$element.css('top', `${(parentRect.top - elemetRect.height)}px`);
this.$element.css('margin-top', ``); this.$element.css('left', `${(parentRect.x)}px`);
this.$element.css('height', `${elemetRect.height}px`);
} }
} else if (!value && oldValue) {
this.$element.removeAttr('style');
if (this.itemWidth) {
this.$element.css('width', this.itemWidth + 'px');
}
this.$element.removeClass('fixed-dropDown');
this._background();
} }
} }
@ -181,9 +212,6 @@ export default class DropDown {
} }
} }
$onChanges(changesObj) { $onChanges(changesObj) {
if (changesObj.show && changesObj.top && changesObj.top.currentValue) {
this.$element.css('top', changesObj.top.currentValue + 'px');
}
if (changesObj.show && changesObj.itemWidth && changesObj.itemWidth.currentValue) { if (changesObj.show && changesObj.itemWidth && changesObj.itemWidth.currentValue) {
this.$element.css('width', changesObj.itemWidth.currentValue + 'px'); this.$element.css('width', changesObj.itemWidth.currentValue + 'px');
} }
@ -220,7 +248,6 @@ module.component('vnDropDown', {
removeLoadMore: '<?', removeLoadMore: '<?',
filterAction: '&?', filterAction: '&?',
showLoadMore: '<?', showLoadMore: '<?',
top: '<?',
itemWidth: '<?', itemWidth: '<?',
parent: '<?', parent: '<?',
multiple: '<?' multiple: '<?'

View File

@ -4,6 +4,8 @@ vn-drop-down {
padding: 0 15px; padding: 0 15px;
margin-left: -15px; margin-left: -15px;
background: transparent; background: transparent;
max-height: 446px;
overflow: hidden;
.dropdown-body{ .dropdown-body{
background: white; background: white;
border: 1px solid #A7A7A7; border: 1px solid #A7A7A7;
@ -27,7 +29,7 @@ vn-drop-down {
padding: 0; padding: 0;
margin: 0; margin: 0;
background: white; background: white;
max-height: 400px; max-height: 378px;
overflow-y: auto; overflow-y: auto;
li { li {
outline: none; outline: none;
@ -55,4 +57,24 @@ vn-drop-down {
} }
} }
} }
}
#ddBack {
position: fixed;
z-index: 9998;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: transparent;
}
vn-drop-down.fixed-dropDown {
position: fixed;
margin: 0;
padding: 0;
.dropdown-body{
height: 100%;
ul{
border-bottom: 1px solid #A7A7A7;
}
}
} }