Files
MikaltoResort/ManagementApp/wwwroot/js/libs/js-ASelect.js
2025-06-04 14:17:32 +07:00

547 lines
20 KiB
JavaScript

import ADropdown from '/js/libs/js-ADropdown.js'
class ASelectEle extends window.AObject {
constructor(e, id, p) {
super();
this.dropdown = new ADropdown();
this.parent = p;
this.id = id;
this.isFocus = false;
this.isTextSearch = false;
this.isSearch = false;
this.isMultiSelect = false;
this.multiSelectedItem = [];
this.element = e;
this.selectedByIndex = -1;
this.selectedEleItem = null;
this.cSubH = null;
this.changeSearch = false;
this.changeIndex = false;
this.isOpen = false;
this.o = {
damping: 0.25,
thumbMinSize: 5,
renderByPixel: true,
alwaysShowTracks: true,
continuousScrolling: true
};
this.createElement(e);
this.updateItem(true);
}
lockElement(str = "Loading....") {
this.dropdown.isLock = true;
if (this.isMultiSelect) {
var t = this.cSelectedItem.querySelectorAll(".item:not(input.item)");
if (t && t.length > 0) t.removeAll();
} else {
var t = this.cSelectedItem.querySelectorAll("span");
if (t && t.length > 0) t.removeAll();
}
this.createSelectedText(str);
this.aSelect.classList.add("lock");
}
isLockElement() {
return this.dropdown.isLock;
}
unlockElement() {
this.dropdown.isLock = false;
var t = this.cSelectedItem.querySelector("span.text");
if (t) t.remove();
this.aSelect.classList.remove("lock");
}
updateItem(f = false) {
if (this.isMultiSelect) {
this.isMultiSelect = [];
}
this.listGroups = [];
this.listItems = [];
if (!f) this.resetItem();
var listOptions = this.element.querySelectorAll("option");
if (listOptions != null) {
listOptions.forEach(u => {
this.addItem(u.getAttribute("value"), u.innerHTML);
});
this.update();
}
}
addGroup(id, text) {
var t = this.groupUI(text);
this.listGroups.push({ "id": id, "text": text, "subItems": [], "element": t });
this.updateHeight();
}
addItem(id, val) {
var it = document.createElement("span");
it.classList.add("ellipsis");
it.innerHTML = val;
this.addCustomItem(id, it, val);
}
addCustomItem(id, o, vSearch = "", g = null) {
if (g != null) {
for (var i = 0; i < this.listGroups.length; i++) {
if (this.listGroups[i].id = g.id) {
var lastE = this.listOptions[i].subitems.element;
var t = this.itemSubUI(id, o, lastE);
t.setAttribute("index", this.listItems.length);
this.listItems.push({ "id": id, "o": o, "vSearch": vSearch, "gParent": this.listGroups[i], "element": t });
this.listGroups[i].subItems.push(this.listItems[this.listItems.length - 1]);
break;
} else {
continue;
}
}
} else {
var t = this.itemUI(id, o);
t.setAttribute("index", this.listItems.length);
this.listItems.push({ "id": id, "o": o, "vSearch": vSearch, "gParent": null, "element": t });
}
}
update() {
if (!this.isMultiSelect) {
if (this.listItems.length == 0 && !this.dropdown.isLock) {
this.createSelectedText("Please choose one of the below options");
} else {
this.updateIndex(0);
}
}
this.updateHeight();
}
setElement(el, str = "active") {
if (this.selectedEleItem != null && !this.isMultiSelect) {
this.selectedEleItem.classList.remove(str);
}
el.classList.add(str);
this.selectedEleItem = el;
}
setSelectedItem(value, f = true) {
if (f) {
for (var i = 0; i < this.listItems.length; i++) {
if (this.listItems[i].id == value) {
this.updateIndex(i);
break;
}
}
} else {
this.updateIndex(value);
}
}
getSelectedItem() {
return this.selectedItem;
}
updateHeight() {
var tmp = (this.cSearch ? this.cSearch.clientHeight : 0);
var tmp1 = this.maxHeight - tmp;
if (this.scrollSub.clientHeight >= tmp1 && this.cSubH == null) {
this.cSubH = (this.maxHeight - tmp - 8);
this.cSub.style.minHeight = this.cSubH + "px";
if (this.isOpen) {
this.cSub.parentNode.style.height = this.maxHeight + "px";
}
return;
}
if (this.scrollSub.clientHeight < tmp1) {
this.cSubH = null;
this.cSub.style.minHeight = this.scrollSub.clientHeight + "px";
if (this.isOpen) {
this.cSub.parentNode.style.height = (this.scrollSub.clientHeight + tmp) + "px";
}
}
}
isItemEqual(it1, it2) {
return it1.getAttribute("data-value") === it2.getAttribute("data-value");
}
updateIndex(idx, f = false) {
if (this.isOpen) {
this.changeIndex = true;
}
if (this.isMultiSelect) {
if (this.selectedEleItem != null) this.selectedEleItem.classList.remove("hover");
this.selectedEleItem = this.listItems[idx].element;
this.selectedItem = this.listItems[idx];
if (f) {
if (!this.multiSelectedItem.hasItem(this.selectedEleItem, this.isItemEqual)) {
const item = document.createElement("div");
item.classList.add("item", "d-f", "a-i-center");
item.setAttribute("data-id", idx);
this.cSelectedItem.insertBefore(item, this.cSelectedItem.children[0]);
this.cloneNodes(this.selectedEleItem, item);
item.insertAdjacentHTML("beforeend", `<button class="ml-1 noopen action d-f a-i-center j-c-center"><span class="atg atg-x"></span></button>`);
var bt = item.querySelector("button");
bt.addEventListener("click", (e => {
this.removeItem(e.currentTarget.parentNode);
}).bind(this));
this.setElement(this.selectedEleItem);
this.multiSelectedItem.push(this.selectedEleItem);
}
this.eleSearch.value = "";
this.eleSearch.focus();
}
this.setElement(this.selectedEleItem, "hover");
} else {
this.selectedByIndex = idx;
if (this.selectedEleItem != null) this.selectedEleItem.classList.remove("active");
this.selectedEleItem = this.listItems[idx].element;
this.selectedItem = this.listItems[idx];
this.removeAllChildNodes(this.cSelectedItem);
this.cloneNodes(this.selectedEleItem, this.cSelectedItem);
this.setElement(this.selectedEleItem);
this.scroll.update();
this.scroll.scrollIntoView(this.selectedEleItem, {
offsetTop: this.selectedEleItem.clientHeight
});
}
}
itemSubUI(id, o, lastE) {
var t = this.itemBaseUI(id, o);
lastE.parentNode.insertBefore(t, lastE.nextSibling);
return t;
}
itemUI(id, o) {
var t = this.itemBaseUI(id, o);
this.scrollSub.appendChild(t);
return t;
}
itemBaseUI(id, o) {
var d = document.createElement("div");
d.classList.add("a-option", "nonhide");
d.setAttribute("data-value", id);
d.appendChild(o);
return d;
}
groupUI(text) {
var d = document.createElement("div");
d.classList.add("a-option-group", "nonhide");
d.innerHTML = text;
return d;
}
createSelectedUI() {
var s = document.createElement("div");
s.classList.add("d-f", "a-i-center");
if (this.isMultiSelect) {
s.classList.add("f-wrap");
s.setAttribute("item-multiple", "");
} ;
this.cSelectedItem = s;
return s;
}
createSelectedText(text) {
var te = document.createElement("span");
te.classList.add("ellipsis", "text");
te.innerHTML = text;
this.cSelectedItem.insertBefore(te, this.cSelectedItem.children[0]);
}
createSubItemUI() {
var s = document.createElement("div");
s.classList.add("sub-item", "a-s-sub", "d-f", "f-c");
var cs = null, inp = null, sH = 0;
if (this.isSearch || this.isMultiSelect) {
if (this.isMultiSelect) {
const t = `<input class="item nonhide" type="input"/>`;
this.cSelectedItem.insertAdjacentHTML("beforeend", t)
inp = this.cSelectedItem.querySelector("input.item");
} else {
cs = document.createElement("div");
cs.classList.add("a-search", "nonhide");
s.appendChild(cs);
inp = document.createElement("input");
cs.appendChild(inp);
s.appendChild(cs);
this.cSearch = cs;
}
this.eleSearch = inp;
var fv = function (e) {
if (this.dropdown.isLock) {
return;
}
if (!this.isFocus) {
window.fireEvent(this.aSelect, "click");
this.isFocus = true;
}
this.inputSearchEvent.call(this, e);
}.bind(this);
inp.addEventListener("keyup", fv, false);
var fv1 = function (e) {
this.keyDown.call(this, e);
}.bind(this);
inp.addEventListener("keydown", fv1, false);
}
var sub = document.createElement("div");
sub.classList.add("w-100");
sub.setAttribute("style", "height:auto");
this.cSub = sub;
var s1 = document.createElement("div");
s1.classList.add("d-f", "f-c", "sub-items");
sub.appendChild(s1);
this.scrollSub = s1;
s.appendChild(sub);
return s;
}
createElement(e) {
var d = document.createElement("div");
d.classList.add("con-aselect");
if (e.getAttribute("data-container-width") != null) {
d.style.width = e.getAttribute("data-container-width");
}
d.setAttribute("data-dropdown", "");
var cselect = document.createElement("div");
cselect.classList.add("hide");
d.appendChild(cselect);
var f = document.createElement("div");
for (var i = 0; i < e.classList.length; i++) {
f.classList.add(e.classList[i]);
}
var atts = e.attributes;
for (var i = 0; i < atts.length; i++) {
if (atts[i].nodeName == "id" || atts[i].nodeName == "name") {
continue;
}
if (atts[i].nodeName == "data-max-height") {
this.maxHeight = atts[i].nodeValue;
}
f.setAttribute(atts[i].nodeName, atts[i].nodeValue);
e.removeAttribute(atts[i].nodeName);
i--;
}
d.appendChild(f);
this.aSelect = f;
this.isMultiSelect = f.hasAttribute("isMultiple");
this.selectedUI = this.createSelectedUI();
f.appendChild(this.selectedUI);
var ic = document.createElement("div");
ic.classList.add("icon", "atg", "a-down-thick");
f.appendChild(ic);
this.isSearch = f.hasAttribute("isSearch") && !this.isMultiSelect;
d.appendChild(this.createSubItemUI());
this.conSelect = d;
e.parentNode.insertBefore(d, e);
this.conSelect = d;
cselect.appendChild(e);
this.dropdown.bindDropDowns(f);
this.scroll = Scrollbar.init(this.cSub, this.o);
f.setAttribute("data-select-id", this.id);
this.dropdown.on("opened", function (ev) {
this.isFocus = true;
this.isOpen = true;
if (this.isMultiSelect) {
this.eleSearch.focus();
this.listItems.forEach(e => { e.element.classList.remove("hover") });
this.selectedEleItem = this.listItems[0].element;
this.listItems[0].element.classList.add("hover");
}
}.bind(this));
this.dropdown.on("closed", function (ev) {
this.isFocus = false;
this.isOpen = false;
if ((this.isSearch && this.isTextSearch) || this.isMultiSelect) {
this.isTextSearch = false;
this.eleSearch.value = "";
this.resetItem(false);
this.updateHeight();
}
if (this.changeIndex) {
this.trigger("change", this);
this.changeIndex = false;
} else {
this.scroll.scrollIntoView(this.selectedEleItem, {
offsetTop: 0,
onlyScrollIfNeeded: true
});
}
}.bind(this));
if (isTouchAvailable && getOS() === "iOS") {
e.classList.add("ios");
}
var fv1 = function (ev) {
this.keyDown.call(this, ev);
}.bind(this);
e.addEventListener("keydown", fv1, false);
var fc = function (e) {
this.subItemClick.call(this, e);
}.bind(this);
var f3 = function (ev) {
ev.preventDefault();
if (!this.isFocus) {
window.fireEvent(f, "click");
this.isFocus = true;
}
}.bind(this);
e.addEventListener("focus", f3, false);
var f4 = function (ev) {
ev.preventDefault();
if (!this.isFocus) {
this.dropdown.checkCloseDropdown();
}
}.bind(this);
e.addEventListener("blur", f4, false);
this.scrollSub.addEventListener("click", fc, false);
}
subItemClick(e) {
var p = e.target.closest(".a-option");
if (p != null && !p.hasAttribute("data-empty")) {
this.updateIndex(p.getAttribute("index"), true);
this.dropdown.checkCloseDropdown();
}
}
keyDown(ev) {
var q = this.selectedEleItem;
if (ev.keyCode == 40) {
ev.preventDefault();
this.changeSearch = true;
var tmp = q.nextSibling;
while (tmp != null && tmp.classList.contains("a-option-group")) {
tmp = tmp.nextSibling;
}
if (tmp != null && tmp.classList.contains("a-option")) {
this.updateIndex(tmp.getAttribute("index"));
console.log(tmp.offsetTop);
this.scroll.scrollIntoView(tmp, {
alignToTop: false,
offsetBottom: 0,
onlyScrollIfNeeded: false
});
}
}
if (ev.keyCode == 38) {
ev.preventDefault();
this.changeSearch = true;
var tmp = q.previousSibling;
while (tmp != null && tmp.classList.contains("a-option-group")) {
tmp = tmp.previousSibling;
}
if (tmp != null && tmp.classList.contains("a-option")) {
this.updateIndex(tmp.getAttribute("index"));
this.scroll.scrollIntoView(tmp, {
offsetTop: 0,
onlyScrollIfNeeded: false
});
}
}
if (ev.keyCode == 13 || ev.keyCode == 9) {
if (ev.keyCode == 13) ev.preventDefault();
this.changeSearch = true;
if (this.eleSearch !== ev.currentTarget && this.isFocus) {
return;
}
if (q.classList.contains("a-option")) {
this.eleSearch.value = "";
this.dropdown.checkCloseDropdown();
this.updateIndex(this.selectedEleItem.getAttribute("index"), true);
}
}
if (ev.keyCode == 8 && this.isMultiSelect) {
if (this.eleSearch.value.length == 0) {
if (this.multiSelectedItem.length > 0) {
var t = this.cSelectedItem.querySelectorAll(".item:not(input)");
this.removeItem(t[t.length - 1]);
}
}
}
}
removeItem(ele) {
var l = this.listItems[ele.getAttribute("data-id")].element;
l.classList.remove("active");
this.multiSelectedItem.removeItem(l, this.isItemEqual);
ele.remove();
}
resetItem(f = true) {
if (this.scrollSub.children.length == 0) return;
this.scrollSub.removeAll();
if (this.listGroups.length == 0) {
for (var i = 0; i < this.listItems.length; i++) {
this.scrollSub.appendChild(this.listItems[i].element);
}
}
this.scroll.update(true);
if (this.isMultiSelect && f) {
var t = this.cSelectedItem.querySelectorAll(".item:not(input)");
if (t.length > 0) {
t.removeAll();
}
}
}
inputSearchEvent(ev) {
if (this.changeSearch) {
this.changeSearch = false;
return;
}
this.isTextSearch = true;
this.scrollSub.removeAll();
var first = null;
if (this.listGroups.length == 0) {
for (var i = 0; i < this.listItems.length; i++) {
if (this.listItems[i].vSearch.toLowerCase().indexOf(ev.currentTarget.value.toLowerCase()) !== -1) {
this.scrollSub.appendChild(this.listItems[i].element);
first = (first == null) ? i : first;
}
}
} else {
/*arr.sub.querySelectorAll(".a-option-group").forEach(e => e.parentNode.removeChild(e));
for (var i = 0; i < arr.listEG.length; i++) {
var d = document.createElement("div");
d.classList.add("a-option-group");
d.innerHTML = arr.listEG[i].label;
arr.sub.appendChild(d);
var c = true;
for (var j = 0; j < arr.listEG[i].subitems.length; j++) {
if (arr.listEG[i].subitems[j].name.toLowerCase().indexOf(ev.target.value.toLowerCase()) !== -1) {
c = false;
var tmp = this.addItem(arr.listEG[i].subitems[j]);
arr.sub.appendChild(tmp);
first = (first == null) ? tmp : first;
}
}
if (c) d.remove();
}*/
}
if (first != null) {
this.updateIndex(first);
}
else {
var it = document.createElement("span");
it.classList.add("ellipsis", "text-center");
it.innerHTML = "No Result";
var item = this.itemBaseUI(null, it);
item.classList.add("d-f", "j-c-center");
this.scrollSub.appendChild(item);
item.setAttribute("data-empty", "");
};
this.updateHeight();
}
}
export default class ASelect extends window.AObject {
constructor(e) {
super();
this.listE = Array.from([]);
this.listA = [];
this.el = e;
this.el.forEach((e) => {
if (e.nodeName != "SELECT") {
return;
}
this.listA.push(new ASelectEle(e, this.listA.length, this));
});
}
get(id = 0) {
if (id >= 0 && id < this.listA.length) {
return this.listA[id];
} else {
console.log("error get Aselect");
}
}
getByID(id) {
for (var i = 0; i < this.listA.length; i++) {
if (this.listA[i].element.getAttribute("id") == id) {
return this.listA[i];
}
}
}
}