selectList 80%

This commit is contained in:
fofolee 2022-04-11 12:15:31 +08:00
parent 7a04d2108a
commit 1b55377c3c
4 changed files with 364 additions and 285 deletions

View File

@ -94,15 +94,6 @@ window.quickcommand = {
}) })
}, },
// 显示选项列表
showSelectList: function(selects, opt = {}) {
return new Promise((reslove, reject) => {})
},
// 更新选项列表
updateSelectList: function(opt, id) {
},
// 关闭进程 // 关闭进程
kill: function(pid, signal = 'SIGTERM') { kill: function(pid, signal = 'SIGTERM') {
process.kill(pid, signal) process.kill(pid, signal)

View File

@ -4,43 +4,54 @@
maximized maximized
ref="dialog" ref="dialog"
transition-show="fade" transition-show="fade"
transition-hide="fade"
@hide="onDialogHide" @hide="onDialogHide"
> >
<q-scroll-area <q-card>
ref="scrollbar" <q-virtual-scroll
:thumb-style="{ ref="scrollBar"
width: '7px', :style="{ maxHeight: listMaxHeight + 'px' }"
}" :virtual-scroll-slice-size="lazyItemSize"
> :virtual-scroll-item-size="itemHeight"
<q-card> @virtual-scroll="scrollEvent"
<q-virtual-scroll :items="matchedItems"
virtual-scroll-slice-size="50" >
virtual-scroll-item-size="50" <template v-slot="{ item, index }">
@virtual-scroll="scrollEvent" <q-item
:items="items" :key="index"
> clickable
<template v-slot="{ item, index }"> v-ripple
<q-item @mousemove="currentIndex = index"
:key="index" @click="onOKClick"
ref="qitems" manual-focus
clickable :focused="index === currentIndex"
v-ripple :active="index === currentIndex"
@mousemove="currentIndex = index" :style="{
manual-focus height: itemHeight + 'px',
:focused="index === currentIndex" }"
:active="index === currentIndex" >
:style="{ <q-item-section v-if="isText">{{ item }}</q-item-section>
height: itemHeight + 'px', <q-item-section v-else-if="isJson">
}" <q-avatar v-if="item.icon">
> <q-icon :name="item.icon" />
<q-item-section> </q-avatar>
<q-item-section>{{ item }}</q-item-section> <q-item-label>{{ item.title }}</q-item-label>
</q-item-section> <q-item-label caption>{{ item.description }}</q-item-label>
</q-item> </q-item-section>
</template> <q-item-section v-else-if="isHtml">
</q-virtual-scroll> <div v-html="item"></div>
</q-card> </q-item-section>
</q-scroll-area> </q-item>
</template>
</q-virtual-scroll>
<q-btn
class="absolute-bottom-right q-ma-md"
round
color="primary"
icon="close"
@click="onCancelClick"
/>
</q-card>
</q-dialog> </q-dialog>
</template> </template>
@ -48,17 +59,44 @@
export default { export default {
data() { data() {
return { return {
result: this.items[0], listMaxHeight: 500,
currentIndex: 0, currentIndex: 0,
itemHeight: 50, itemHeight: 50,
lazyItemSize: 50,
searchWords: "",
}; };
}, },
mounted() { mounted() {
window.SelectList = this; window.SelectList = this;
this.setSubInput();
this.setUtoolsHeight(this.itemHeight * this.itemSize);
}, },
computed: { computed: {
maxIndex() { itemSize() {
return this.items.length - 1; return this.items.length;
},
matchedItems() {
if (!this.searchWords) return this.items;
let matchedItems = this.items.filter((x) => {
if (typeof x === "string") {
return x.toLowerCase().includes(this.searchWords.toLowerCase());
}
return (
x.title.toLowerCase().includes(this.searchWords.toLowerCase()) ||
x.description.toLowerCase().includes(this.searchWords.toLowerCase())
);
});
this.setUtoolsHeight(this.itemHeight * matchedItems.length);
return matchedItems;
},
isJson() {
return this.options.optionType === "json";
},
isHtml() {
return this.options.optionType === "html";
},
isText() {
return this.options.optionType === "plaintext";
}, },
}, },
props: { props: {
@ -70,6 +108,7 @@ export default {
show() { show() {
this.$refs.dialog.show(); this.$refs.dialog.show();
}, },
hide() { hide() {
this.$refs.dialog.hide(); this.$refs.dialog.hide();
}, },
@ -79,11 +118,20 @@ export default {
}, },
onOKClick() { onOKClick() {
this.$emit("ok", this.result); utools.removeSubInput();
let selected =
this.options.optionType === "json"
? this.matchedItems[this.currentIndex]
: {
id: this.currentIndex,
text: this.matchedItems[this.currentIndex],
};
this.$emit("ok", selected);
this.hide(); this.hide();
}, },
onCancelClick() { onCancelClick() {
utools.removeSubInput();
this.hide(); this.hide();
}, },
@ -94,13 +142,33 @@ export default {
this.currentIndex = Math.max(0, this.currentIndex - 1); this.currentIndex = Math.max(0, this.currentIndex - 1);
break; break;
case 40: case 40:
this.currentIndex = Math.min(this.maxIndex, this.currentIndex + 1); this.currentIndex = Math.min(
this.itemSize - 1,
this.currentIndex + 1
);
break; break;
case 13:
this.onOKClick();
return;
} }
// this.$refs.qitems[this.currentIndex].$el.scrollIntoViewIfNeeded(false); this.$refs.scrollBar.scrollTo(this.currentIndex);
}, },
scrollEvent(e) { scrollEvent(e) {
console.log(e); this.currentIndex =
e.direction === "increase"
? Math.max(e.index, this.currentIndex)
: Math.min(e.index + 9, this.currentIndex);
},
setSubInput() {
utools.setSubInput(({ text }) => {
this.searchWords = text;
}, this.options.placeholder);
},
setUtoolsHeight(height) {
utools.setExpendHeight(Math.min(height, this.listMaxHeight));
}, },
}, },
}; };

View File

@ -89,11 +89,9 @@ const quickcommand = {
}) })
}), }),
showSelectList: (selects, options = {}) => new Promise((reslove, reject) => {
showSelectList: (selects, options = { if (!options.placeholder) options.placeholder = "输入进行筛选"
placeholder: "请选择", if (!options.optionType) options.optionType = "plaintext"
optionType: "plaintext"
}) => new Promise((reslove, reject) => {
let props = { let props = {
items: selects, items: selects,
options: options options: options
@ -106,7 +104,12 @@ const quickcommand = {
}).onCancel(() => { }).onCancel(() => {
console.log('取消') console.log('取消')
}) })
}) }),
// 更新选项列表
updateSelectList: (opt, id) => {
},
} }
export default quickcommand export default quickcommand

View File

@ -12,270 +12,287 @@ interface quickcommandApi {
* @param buttons * @param buttons
* @param title * @param title
*/ */
showButtonBox(buttons: array, title?: string): Promise<{ id: number, text: string }>; showButtonBox(
buttons: array,
title?: string
): Promise<{ id: number; text: string }>;
/** /**
* *
* *
* ```js * ```js
* quickcommand.showInputBox(["输入框1", "输入框2", "输入框3"]).then(values => { * quickcommand.showInputBox(["输入框1", "输入框2", "输入框3"]).then(values => {
* console.log(`输入的内容分别为${values}`) * console.log(`输入的内容分别为${values}`)
* }) * })
* *
* quickcommand.showInputBox({labels:["输入框标签"],values:["默认值"],hints:["输入框提示"]}).then(values => { * quickcommand.showInputBox({labels:["输入框标签"],values:["默认值"],hints:["输入框提示"]}).then(values => {
* console.log(`输入的内容分别为${values}`) * console.log(`输入的内容分别为${values}`)
* }) * })
* ``` * ```
* *
* *
* *
* @param options * @param options
* @param title * @param title
*/ */
showInputBox(options: array | { labels: array, values: array, hints: array }, title?: string): Promise<array>; showInputBox(
options: array | { labels: array; values: array; hints: array },
title?: string
): Promise<array>;
/** /**
* * html时
* *
* ```js * ```js
* // plaintext * // plaintext
* var opt = [] * var opt = []
* for (var i = 0; i < 15; i++) { * for (var i = 0; i < 15; i++) {
* // 每一个选项为文本格式 * // 每一个选项为文本格式
* opt.push(`选项` + i) * opt.push(`选项` + i)
* } * }
* quickcommand.showSelectList(opt).then(choise => { * quickcommand.showSelectList(opt).then(choise => {
* console.log(`选择的选项为${choise.text}`) * console.log(`选择的选项为${choise.text}`)
* }) * })
* *
* // json * // json
* var opt = [] * var opt = []
* for (var i = 0; i < 15; i++) { * for (var i = 0; i < 15; i++) {
* // 每一个选项为 json 格式 * // 每一个选项为 json 格式
* opt.push({title: `选项${i}`, description: `选项${i}的描述`, abcd: `选项${i}的自定义属性`}) * opt.push({title: `选项${i}`, description: `选项${i}的描述`, icon: `选项${i}的图标`,abcd: `选项${i}的自定义属性`})
* } * }
* quickcommand.showSelectList(opt, {optionType: 'json'}).then(choise => { * quickcommand.showSelectList(opt, {optionType: 'json'}).then(choise => {
* console.log(`选择的选项为${choise.title}`) * console.log(`选择的选项为${choise.title}`)
* }) * })
* *
* // html * // html
* var opt = [] * var opt = []
* for (var i = 0; i < 15; i++) { * for (var i = 0; i < 15; i++) {
* // 每一个选项为 html 格式 * // 每一个选项为 html 格式
* opt.push(`<div style="color: red">选项${i}</div>`) * opt.push(`<div style="color: red">选项${i}</div>`)
* } * }
* quickcommand.showSelectList(opt, {optionType: 'html'}).then(choise => { * quickcommand.showSelectList(opt, {optionType: 'html'}).then(choise => {
* console.log(`选择的选项为${quickcommand.htmlParse(choise.text).body.innerText}`) * console.log(`选择的选项为${quickcommand.htmlParse(choise.text).body.innerText}`)
* }) * })
* ``` * ```
* *
* @param selects * @param selects
* @param options placeholder: 搜索框占位符,optionType: 选项的格式plaintext * @param options placeholder: 搜索框占位符,optionType: 选项的格式plaintext
*/ */
showSelectList(selects: array, options?: { placeholder: string, optionType: 'plaintext' | 'html' | 'json' }): Promise<{ id: number, text: string }>; showSelectList(
selects: array,
options?: { placeholder: string; optionType: "plaintext" | "html" | "json" }
): Promise<{ id: number; text: string | object }>;
/** /**
* *
* *
* ```js * ```js
* // 初始状态只有 1、2、3 三个选项 * // 初始状态只有 1、2、3 三个选项
* quickcommand.showSelectList(['1','2','3']).then(x=>{ * quickcommand.showSelectList(['1','2','3']).then(x=>{
* console.log(x) * console.log(x)
* }) * })
* *
* // 1s 后追加一个选项 * // 1s 后追加一个选项
* quickcommand.setTimeout(()=>{ * quickcommand.setTimeout(()=>{
* quickcommand.updateSelectList('4') * quickcommand.updateSelectList('4')
* }, 1000) * }, 1000)
* *
* // 2s 后更新第二个选项的值 * // 2s 后更新第二个选项的值
* quickcommand.setTimeout(()=>{ * quickcommand.setTimeout(()=>{
* quickcommand.updateSelectList('updated', 1) * quickcommand.updateSelectList('updated', 1)
* }, 2000) * }, 2000)
* ``` * ```
* *
* @param opt * @param opt
* @param id * @param id
*/ */
updateSelectList(opt: string, id?: number): void; updateSelectList(opt: string, id?: number): void;
/** /**
* *
* *
* ```js * ```js
* quickcommand.showTextAera("请输入文本").then(text=>{ * quickcommand.showTextAera("请输入文本").then(text=>{
* console.log(`输入的文本为${text}`) * console.log(`输入的文本为${text}`)
* }) * })
* ``` * ```
* *
* @param placeholder * @param placeholder
* @param value * @param value
*/ */
showTextArea(placeholder?: string, value?: string): Promise<string>; showTextArea(placeholder?: string, value?: string): Promise<string>;
/** /**
* *
* *
* ```js * ```js
* quickcommand.showMessageBox("这是一段3s后自动消失的成功提示") * quickcommand.showMessageBox("这是一段3s后自动消失的成功提示")
* ``` * ```
* @param message * @param message
* @param icon success * @param icon success
* @param time 3000 * @param time 3000
*/ */
showMessageBox(message: string, icon?: 'success' | 'error' | 'warning' | 'info' , time?: number): void; showMessageBox(
message: string,
icon?: "success" | "error" | "warning" | "info",
time?: number
): void;
/** /**
* *
* *
* ```js * ```js
* quickcommand.showConfirmBox().then(confirmed => { * quickcommand.showConfirmBox().then(confirmed => {
* confirmed && console.log('点击了确定') * confirmed && console.log('点击了确定')
* }) * })
* ``` * ```
* @param message * @param message
* @param title * @param title
*/ */
showConfirmBox(message?: string, title?: string): Promise<boolean>; showConfirmBox(message?: string, title?: string): Promise<boolean>;
/** /**
* *
* @param ms * @param ms
*/ */
sleep(ms: number): void; sleep(ms: number): void;
/** /**
* *
* *
* ```js * ```js
* quickcommand.setTimeout(()=>{ * quickcommand.setTimeout(()=>{
* console.log('2000毫秒后执行') * console.log('2000毫秒后执行')
* }, 2000) * }, 2000)
* ``` * ```
* *
* @param ms * @param ms
*/ */
setTimeout(callback: () => void, ms) setTimeout(callback: () => void, ms);
/** /**
* html字符串解析为 DOM * html字符串解析为 DOM
* *
* ```js * ```js
* var html = `<a href="https://u.tools/">uTools</a>` * var html = `<a href="https://u.tools/">uTools</a>`
* var href = quickcommand.htmlParse(html).querySelector('a').href * var href = quickcommand.htmlParse(html).querySelector('a').href
* console.log(`解析出来的a标签地址为${href}`) * console.log(`解析出来的a标签地址为${href}`)
* ``` * ```
* *
* @param html html * @param html html
*/ */
htmlParse(html: string): object htmlParse(html: string): object;
/** /**
* Buffer * Buffer
* *
* ```js * ```js
* // 下载文件到D:/ * // 下载文件到D:/
* quickcommand.downloadFile('https://res.u-tools.cn/currentversion/uTools-1.1.3.exe', 'D:/') * quickcommand.downloadFile('https://res.u-tools.cn/currentversion/uTools-1.1.3.exe', 'D:/')
* *
* // 下载文件,并弹出对话框询问保存路径 * // 下载文件,并弹出对话框询问保存路径
* quickcommand.downloadFile('https://res.u-tools.cn/currentversion/uTools-1.1.3.exe') * quickcommand.downloadFile('https://res.u-tools.cn/currentversion/uTools-1.1.3.exe')
* ``` * ```
* *
* @param url * @param url
* @param file * @param file
* *
* Object时 options utools.showSaveDialog options一致 * Object时 options utools.showSaveDialog options一致
*/ */
downloadFile(url, file?: string | object): Promise<Buffer> downloadFile(url, file?: string | object): Promise<Buffer>;
/** /**
* *
* *
* ```js * ```js
* // 上传图片到图床 * // 上传图片到图床
* quickcommand.uploadFile("https://imgkr.com/api/v2/files/upload", "C:\\test.jpg").then(res=>{ * quickcommand.uploadFile("https://imgkr.com/api/v2/files/upload", "C:\\test.jpg").then(res=>{
* console.log('上传成功,图片地址为:' + res.data.data) * console.log('上传成功,图片地址为:' + res.data.data)
* }) * })
* *
* // 包含额外表单数据 * // 包含额外表单数据
* quickcommand.uploadFile("https://catbox.moe/user/api.php", "C:\\test.jpg", 'fileToUpload', { * quickcommand.uploadFile("https://catbox.moe/user/api.php", "C:\\test.jpg", 'fileToUpload', {
* "reqtype": "fileupload" * "reqtype": "fileupload"
* }).then(res=>{ * }).then(res=>{
* console.log('上传成功,图片地址为:' + res.data) * console.log('上传成功,图片地址为:' + res.data)
* }) * })
* ``` * ```
* *
* @param url * @param url
* @param file * @param file
* *
* Object时 options utools.showOpenDialog options一致 * Object时 options utools.showOpenDialog options一致
* *
* @param name file * @param name file
* @param formData * @param formData
*/ */
uploadFile(url: string, file?: string | object, name?: string, formData?: object): Promise<object> uploadFile(
url: string,
file?: string | object,
name?: string,
formData?: object
): Promise<object>;
/** /**
* export * export
* *
* ```js * ```js
* let remote = 'https://cdn.jsdelivr.net/npm/sweetalert2@9' * let remote = 'https://cdn.jsdelivr.net/npm/sweetalert2@9'
* quickcommand.loadRemoteScript(remote).then(swal => { * quickcommand.loadRemoteScript(remote).then(swal => {
* swal.fire('已加载 sweetalert2 并成功弹窗') * swal.fire('已加载 sweetalert2 并成功弹窗')
* }) * })
* ``` * ```
* *
* @param url * @param url
*/ */
loadRemoteScript(url: string): Promise<object> loadRemoteScript(url: string): Promise<object>;
/** /**
* signal pid , process.kill * signal pid , process.kill
* @param pid ID * @param pid ID
* @param signal SIGTERM * @param signal SIGTERM
*/ */
kill(pid: number, signal?: number | string): void kill(pid: number, signal?: number | string): void;
/** /**
* windows VBS * windows VBS
* *
* ```js * ```js
* quickcommand.runVbs(`CreateObject("SAPI.SpVoice").Speak"Hello"`) * quickcommand.runVbs(`CreateObject("SAPI.SpVoice").Speak"Hello"`)
* ``` * ```
* *
* @param script VBS * @param script VBS
*/ */
runVbs(script: string): Promise<string> runVbs(script: string): Promise<string>;
/** /**
* utools.onPluginEnter code type payload * utools.onPluginEnter code type payload
* *
* code: 唯一标识 * code: 唯一标识
* *
* type: text | img | files | regex | over | window * type: text | img | files | regex | over | window
* *
* payload: 当匹配模式为关键字时 * payload: 当匹配模式为关键字时
* *
* ```js * ```js
* if (quickcommand.enterData.type == 'regex'){ * if (quickcommand.enterData.type == 'regex'){
* var text = quickcommand.enterData.payload * var text = quickcommand.enterData.payload
* console.log(`主输入框匹配的文本为${text}`) * console.log(`主输入框匹配的文本为${text}`)
* } * }
* ``` * ```
* *
*/ */
enterData: { code: string, type: string, payload: any } enterData: { code: string; type: string; payload: any };
/** /**
* *
*/ */
simulateCopy() simulateCopy();
/** /**
* *
*/ */
simulatePaste() simulatePaste();
} }
declare var quickcommand: quickcommandApi; declare var quickcommand: quickcommandApi;