import {
Component,
ElementRef,
HostListener,
Input,
OnInit,
ViewChild,
EventEmitter,
Output,
Renderer,
AfterViewInit,
ChangeDetectorRef
} from '@angular/core';
import {TreeComponent} from '../tree/tree.component';
import * as _ from 'lodash';
@Component({
selector: 'dc-select',
template: `
-
{{(option[displayField]=='')?'':option[displayField] || option}}
No Data.
`,
styles: [
`.dc-select-container {
width: 160px;
height: 30px;
font-size: 14px;
color: #333;
background: #fff;
margin: 0 10px;
padding: 0;
display: inline-block;
position: relative
}
.new-style.dc-select-container,.new-style .dc-select-input,.new-style .dc-select-input > input,.new-style .clear-input-value,.new-style .dc-select-btn{
height: 40px;
}
.dc-select-container:hover {
/*border-color: #3d70b2*/
}
.dc-select-container:active {
/*border-color: #0081cc*/
}
.dc-select-container.disable {
background: #f5f5f5;
border-color: #ccc;
color: #999
}
.dc-select-input {
/*padding: 5px 10px;*/
height: 30px;
position: relative;
/*display: flex;*/
/*flex-direction: row;*/
}
.dc-select-input > input {
outline: none;
width: 100%;
padding: 0 30px 0 10px;
height: 30px;
line-height: 30px;
background: none;
border: 1px solid #ccc;
border-radius: 4px;
position: relative;
z-index: 1;
}
.dc-select-input > input.dc-valid {
border-color: #3FB992;
}
.dc-select-input > input.dc-invalid {
border-color: #FF3B3B;
}
.dc-select-input > input.focus,
.dc-select-input > input:focus {
border-color: #2BB1FF;
}
.dc-select-input > input:read-only {
cursor: default
}
.dc-select-input > span {
display: block;
position: absolute;
width: calc(100% - 40px);
height: 18px;
left: 10px;
top: 5px;
line-height: 18px;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
z-index: 0;
}
.new-style .dc-select-input > span{
top: 10px;
}
.clear-input-value {
position: absolute;
right: 20px;
top: 0;
cursor: pointer;
width: 12px;
height: 30px;
z-index: 2;
background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAMCAYAAABWdVznAAABS2lUWHRYTUw6Y29tLmFkb2JlLnhtcAAAAAAAPD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz4KPHg6eG1wbWV0YSB4bWxuczp4PSJhZG9iZTpuczptZXRhLyIgeDp4bXB0az0iQWRvYmUgWE1QIENvcmUgNS42LWMxMzggNzkuMTU5ODI0LCAyMDE2LzA5LzE0LTAxOjA5OjAxICAgICAgICAiPgogPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4KICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+CiA8L3JkZjpSREY+CjwveDp4bXBtZXRhPgo8P3hwYWNrZXQgZW5kPSJyIj8+IEmuOgAAAOVJREFUKJF90DFKA1EQBuAvj2Cu8MBqe8FokedeQb2A6WzU0uN4gxTbxkM8CKKSfqvAXsAi2lj4dlkh5Icp5p9/Zv6ZSdM0Ck7whDucFW6LFV7wDdNSOMUac/9xVeIet9iFMvmQeIw5XjELeOzFdV2LMQ6qGKO6rvv0HA8By55p21ZKSYxRjFFKSdu2403LKS77rOs6OWcpJZBz1nXduOEiHPF9CD8Bb2PPKSU552HT+CZsg78/g6qqBhu9vaqqxg2rSdM0M+TyhWP4xCJgjxu8HxF/4Br7/ugdEp6xwVeJTeEWReMX1Y9FK/4RDOgAAAAASUVORK5CYII=) no-repeat center center transparent;
}
.new-style .clear-input-value{
}
.clear-input-value:hover {
background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAMCAYAAABWdVznAAABS2lUWHRYTUw6Y29tLmFkb2JlLnhtcAAAAAAAPD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz4KPHg6eG1wbWV0YSB4bWxuczp4PSJhZG9iZTpuczptZXRhLyIgeDp4bXB0az0iQWRvYmUgWE1QIENvcmUgNS42LWMxMzggNzkuMTU5ODI0LCAyMDE2LzA5LzE0LTAxOjA5OjAxICAgICAgICAiPgogPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4KICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+CiA8L3JkZjpSREY+CjwveDp4bXBtZXRhPgo8P3hwYWNrZXQgZW5kPSJyIj8+IEmuOgAAAOtJREFUKJF90b1NAzEcBfBfriCVm2vR3S2ABFXYAViADACUjMMGWQCGQIoQWJngrLTXWBSBIhRxooBCnuTCz++9/4dHMUYFJ3jALc4Kt8AMT/iCUTGc4hkXDuMdN1hWJfmYWHl7wbjC/VbcdZ0Qwk4VQtB13fZ6jrsK0y0zDIO2bYUQhBA0TWMYhv1K01GMcVXa2qW2bWu9XkspyTnvG1bVkb4P4bvC29/0vu+llDRN82smLCqbPYO6rvV9L+cs5yylpK7rfcNsFGMc47Vs4RgiJhVWuLb5nP/wgSt7Qy9xiUfM8VnOvHCTovEDCGVJpA/ldQoAAAAASUVORK5CYII=) no-repeat center center transparent;
}
.dc-select-btn {
width: 0;
height: 30px;
position: absolute;
right: 0;
top: 0;
padding: 12px 15px 0 5px;
cursor: pointer;
z-index: 3;
}
.new-style .dc-select-btn{
padding-top: 16px;
}
.dc-select-container.disable .dc-select-btn {
cursor: default;
}
.dc-select-arrow {
border: solid 4px transparent;
border-top-width: 6px;
border-top-color: #333;
width: 0;
height: 0;
}
.showDropFlagBtn .dc-select-arrow {
top: 0;
transform: rotate(180deg);
-ms-transform: rotate(180deg); /* Internet Explorer */
-moz-transform: rotate(180deg); /* Firefox */
-webkit-transform: rotate(180deg); /* Safari 和 Chrome */
-o-transform: rotate(180deg); /* Opera */
}
.dc-select-container.disable .dc-select-arrow {
border-top-color: #ccc;
}
.dc-select-drop {
position: absolute;
top: 30px;
left: -1px;
width: calc(100% + 2px);
box-shadow: 0px 0px 10px 2px rgba(0, 0, 0, .2);
background: #fff;
list-style: none;
border-radius: 3px;
overflow-y: auto;
overflow-x: hidden;
z-index: 1000;
}
.new-style .dc-select-drop{
top: 40px;
}
.dc-select-drop.drop-up {
top: auto;
bottom: 25px;
}
.new-style .dc-select-drop.drop-up{
top: auto;
bottom: 40px;
}
.selected {
background-color: #0081cc;
color: #ffffff;
}
.noChecked{
color: #bbbbbb;
}
.dc-select-drop > li {
width: 100%;
height: 30px;
line-height: 26px;
cursor: pointer;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
padding: 0 11px
}
.dc-select-drop > li:hover {
color: #333333;
background: #edf0f5;
}
.dc-select-drop > li.noChecked:hover {
color: #bbbbbb;
background: #fff;
cursor: auto;
}
.tip-text {
font-size: 12px;
line-height: 20px;
padding-left: 10px;
color: #aaa;
}
.dc-select-drop > li.selected {
background-color: #0081cc;
color: #ffffff;
}`]
})
export class SelectComponent implements OnInit, AfterViewInit {
firstLoad = true;
@Input() optionList: any;
@Input() required: boolean;
@Input() clear: boolean;
@Input() dropUp: boolean;
@Input() disable: boolean;
@Input() treeSearch: boolean;
@Input() isReadonly: boolean;
@Input() displayField: string;
@Input() outputField: string;
@Input() width: string;
@Input() maxHeight: string;
@Input() isMultiple: boolean;
@Input() isTree: boolean;
@Input() treeParams: any;
@Input() folderClick: boolean;
@Input() newStyle: boolean;
@Input() placeholder: string;
@Input() checkNoParents: boolean;
@Input() checkNoChildren: boolean;
_treeParams: any = {
treeDatas: null,
keyId: null,
keyName: null,
keyChild: null,
tipText: null,
defaultCheckedNodes: null,
defaultSelectedNode: null,
options: null
};
@Output() treeCheckEvent = new EventEmitter();
@Output() treeCheckData = new EventEmitter();
@Output() treeClickEvent = new EventEmitter();
@Output() changeValueEvent = new EventEmitter();
@Output() selectBlurEvent = new EventEmitter();
@Output() selectClearEvent = new EventEmitter();
@ViewChild('inputSelect') inputSelect: ElementRef;
@ViewChild('dropBtn') dropBtn: ElementRef;
@ViewChild('dropList') dropList: ElementRef;
@ViewChild('tree') tree: TreeComponent;
@ViewChild('selectContainer') selectContainer: ElementRef;
@ViewChild('searchComponent') searchComponent: any;
@ViewChild('searchComponentNochenck') searchComponentNochenck: any;
currentValue: string;
keyword: string;
showThis = false;
isFocus = false;
_currentSelect: any;
showDropFlag = false;
@Input() set currentSelect(v) {
this._currentSelect = _.cloneDeep(v);
if (!this.optionList) {
return;
}
const result = this.optionList.find((item: any) => {
if (this.currentSelect) {
return this.currentSelect[this.displayField] === item[this.displayField];
}
});
if (result && result[this.displayField] == '') {
this.currentValue = '';
} else {
this.currentValue = result && (result[this.displayField] || result);
}
}
get currentSelect() {
return this._currentSelect;
}
constructor(private renderer: Renderer, private cdr: ChangeDetectorRef) {
this.maxHeight = this.maxHeight || '300px';
this.width = this.width || '150px';
}
ngOnInit() {
if (this.isTree) {
this.treeParams.options.checkbox = this.isMultiple;
this.treeParams.options.actionBtn = false;
Object.assign(this._treeParams, this.treeParams);
}
}
ngAfterViewInit() {
this.afterViewInit();
}
afterViewInit() {
if (!this.tree) {
setTimeout(() => {
this.afterViewInit();
}, 100);
return;
}
if (this._treeParams.defaultCheckedNodes && !_.isEmpty(this._treeParams.defaultCheckedNodes)) {
const result = this._treeParams.defaultCheckedNodes.map((value: any) => this.tree.matchSearchNodesByKey(value, this._treeParams.keyId)[0]);
this.currentValue = this.arrStringJoin(result);
}
if (this._treeParams.defaultSelectedNode && !_.isEmpty(this._treeParams.defaultSelectedNode)) {
const result = this.tree.matchSearchNodesByKey(this._treeParams.defaultSelectedNode[this._treeParams.keyId], this._treeParams.keyId);
if (result && result.length > 0) {
this.currentValue = result[0][this.displayField];
}
}
this.cdr.detectChanges();
}
calcInvalid() {
// !firstLoad && required && (!currentValue || currentValue.length == 0)
if (!this.firstLoad && this.required) {
if (this.isTree) {
if (this.showDropFlag) {
if (!this.keyword) {
return true;
} else {
return false;
}
} else {
if (!this.currentValue || this.currentValue.length == 0) {
return true;
} else {
return false;
}
}
} else {
if (!this.currentValue || this.currentValue.length == 0) {
return true;
} else {
return false;
}
}
}
}
searchTree(ev: string) {
// this._treeParams.treeDatas = _.cloneDeep(this.treeParams.treeDatas);
// if (ev) {
// setTimeout(() => {
const result = this.tree.fuzzySearchNodesByKey(ev, this._treeParams.keyName);
// this._treeParams.treeDatas = _.cloneDeep(result);
// }, 10);
// }
}
changeCurrentValue() {
const result = this.optionList.find((item: any) => this.currentSelect === item);
this.currentValue = result && (result[this.displayField] || result);
}
@HostListener('document:click', ['$event'])
onDocumentClick(ev: any) {
if (!this.disable) {
if (this.showDropFlag && !this.selectContainer.nativeElement.contains(ev.target)) {
if(this.searchComponent){
this.searchTree('');
this.searchComponent.setSearchText();
}
if(this.searchComponentNochenck){
this.searchTree('');
this.searchComponentNochenck.setSearchText();
}
this.showDropFlag = false;
this.isFocus = false;
if (this.keyword !== undefined) {
this.currentValue = this.keyword;
this.keyword = undefined;
}
}
/*
if (event.target !== this.inputSelect.nativeElement &&
event.target !== this.dropBtn.nativeElement &&
event.target.parentNode !== this.dropBtn.nativeElement
) {
if (this.dropList.nativeElement.style.display == 'none') {
return;
}
this.dropList.nativeElement.style.display = 'none';
this.isFocus = false;
if (this.keyword !== undefined) {
this.currentValue = this.keyword;
this.keyword = undefined;
}
} else {
const elm = this.dropList.nativeElement;
if (event.target === this.dropBtn.nativeElement ||
event.target.parentNode === this.dropBtn.nativeElement) {
elm.style.display = elm.style.display === 'block' ? 'none' : 'block';
this.isFocus = !this.isFocus;
} else {
if (this.tree) {
let result: Array = [];
if (this.isMultiple) {
result = this.tree.getCheckedNodes();
} else {
if (this.tree.getSelectedNodes()) {
result = [this.tree.getSelectedNodes()];
}
}
this.keyword = this.arrStringJoin(result);
}
elm.style.display = 'block';
this.isFocus = true;
}
}*/
}
}
filter(data: any, keyword: string) {
if (!this.isReadonly && keyword) {
return data.filter((item: any) => item[this.displayField].indexOf(keyword) > -1);
} else {
return data || [];
}
}
blurEvent(ev: any) {
this.selectBlurEvent.emit({
current: this.currentValue,
val: this.keyword
});
}
confirm() {
const result = this.optionList.filter((item: any) => item[this.displayField].indexOf(this.keyword) > -1);
if (result && result.length > 0) {
// this.dropList.nativeElement.style.display = 'none';
this.showDropFlag = false;
this.inputSelect.nativeElement.blur();
this.currentValue = result[0][this.displayField] || result[0];
this.keyword = '';
this.isFocus = false;
const value = result[0][this.outputField] || result[0];
this.changeValueEvent.emit(value);
}
}
changeValue(option: any) {
this.currentSelect = option;
const value = option[this.outputField] || option;
this.currentValue = (option[this.displayField]=='')?'':option[this.displayField] || option;
this.keyword = undefined;
this.changeValueEvent.emit(value);
this.showDropFlag = false;
this.isFocus = false;
}
clearValue() {
this.firstLoad = false;
this.currentValue = '';
this.keyword = undefined;
this.isFocus = false;
if (!this.isTree) {
this.currentSelect = null;
} else {
if (this.isMultiple) {
const checkedNodes = this.tree.getCheckedNodes();
const halfCheckedNodes = this.tree.getHalfCheckedNodes();
if (checkedNodes && checkedNodes.length > 0) {
for (let i = 0; i < checkedNodes.length; i++) {
checkedNodes[i].checked = 0;
}
}
if (halfCheckedNodes && halfCheckedNodes.length > 0) {
for (let i = 0; i < halfCheckedNodes.length; i++) {
halfCheckedNodes[i].checked = 0;
}
}
} else {
const selectedNode = this.tree.getSelectedNodes();
if (selectedNode) {
this.tree.deSelectTreeNode(selectedNode);
}
}
}
this.changeValueEvent.emit(null);
}
trackByIndex(index: number, value: any) {
return index;
}
treeCheck(event: any) {
// if (result.length === 1 && event.hasOwnProperty(this._treeParams.keyChild) && event[this._treeParams.keyChild].length > 0) {
// this.keyword = event[this.displayField];
// } else {
const result = this.tree.getCheckedNodes();
this.keyword = this.arrStringJoin(result);
// }
this.treeCheckEvent.emit(event);
this.treeCheckData.emit(result);
}
treeClick(event: any) {
if (event) {
if (this.folderClick && event.children && event.children.length > 0) {
this.keyword = '';
this.treeClickEvent.emit(null);
return;
}
this.keyword = event[this.displayField];
this.treeClickEvent.emit(event);
this.showDropFlag = false;
this.currentValue = this.keyword;
} else {
this.keyword = '';
this.treeClickEvent.emit(null);
}
}
arrStringJoin(arr: Array) {
if (arr && arr.length == 0) {
return '';
}
const str = arr.map(item => item[this.displayField]);
return str.length > 1 ? str.join(',') : str[0];
}
getSelectVal() {
let res: any;
if (this.isMultiple) {
res = this.tree.getCheckedNodes();
} else {
res = this.tree.getSelectedNodes();
}
return res;
}
showSourceDrop() {
this.showDropFlag = true;
this.isFocus = true;
}
hideSourceDrop() {
this.showDropFlag = false;
this.isFocus = false;
}
toggleSourceDrop() {
this.firstLoad = false;
this.showDropFlag = !this.showDropFlag;
this.isFocus = this.showDropFlag;
if(this.isReadonly){
this.keyword = this.currentValue;
}
if (this.tree && this.showDropFlag) {
let result: Array = [];
if (this.isMultiple) {
result = this.tree.getCheckedNodes();
} else {
if (this.tree.getSelectedNodes()) {
result = [this.tree.getSelectedNodes()];
}
}
this.keyword = this.arrStringJoin(result);
}
}
clearInputValue(ev: any) {
this.clearValue();
this.showDropFlag = true;
this.selectClearEvent.emit(ev);
}
}