mirror of
https://github.com/fofolee/uTools-quickcommand.git
synced 2025-06-30 13:02:46 +08:00
263 lines
5.9 KiB
Vue
263 lines
5.9 KiB
Vue
<template>
|
|
<div class="control-command-wrapper">
|
|
<div class="control-command">
|
|
<!-- 类型标签 -->
|
|
<div class="control-type-label">
|
|
{{ currentFunction?.label || modelValue.commandType }}
|
|
</div>
|
|
|
|
<!-- 输入区域 -->
|
|
<div v-if="currentFunction?.config" class="control-settings">
|
|
<ParamInput
|
|
:configs="currentFunction.config"
|
|
:values="values"
|
|
@update="handleInputUpdate"
|
|
/>
|
|
</div>
|
|
|
|
<!-- 操作按钮 -->
|
|
<q-btn-dropdown
|
|
v-if="showBranchButton"
|
|
flat
|
|
dense
|
|
dropdown-icon="add"
|
|
size="sm"
|
|
no-icon-animation
|
|
class="control-btn"
|
|
>
|
|
<q-list>
|
|
<q-item
|
|
v-for="func in branchOptions"
|
|
:key="func.value"
|
|
v-close-popup
|
|
clickable
|
|
@click="addBranch(func.value)"
|
|
class="row items-center no-wrap q-py-none"
|
|
>
|
|
<q-icon :name="func.icon" class="q-mr-md" />
|
|
<q-item-label>{{ func.label }}</q-item-label>
|
|
</q-item>
|
|
</q-list>
|
|
</q-btn-dropdown>
|
|
</div>
|
|
</div>
|
|
</template>
|
|
|
|
<script>
|
|
import { defineComponent } from "vue";
|
|
import ParamInput from "components/composer/common/ParamInput.vue";
|
|
|
|
export default defineComponent({
|
|
name: "ControlCommand",
|
|
components: {
|
|
ParamInput,
|
|
},
|
|
props: {
|
|
modelValue: {
|
|
type: Object,
|
|
required: true,
|
|
},
|
|
},
|
|
emits: ["update:modelValue", "addBranch"],
|
|
data() {
|
|
return {
|
|
defaultArgvs: {},
|
|
};
|
|
},
|
|
computed: {
|
|
currentFunction() {
|
|
return this.modelValue.subCommands?.find(
|
|
(f) => f.value === this.modelValue.commandType
|
|
);
|
|
},
|
|
values() {
|
|
if (!this.currentFunction?.config) return [];
|
|
return this.currentFunction.config.map(
|
|
(input) => this.argvs[input.key] || ""
|
|
);
|
|
},
|
|
showBranchButton() {
|
|
return (
|
|
this.modelValue.subCommands?.length > 2 &&
|
|
this.modelValue.subCommands?.[0]?.value === this.modelValue.commandType
|
|
);
|
|
},
|
|
branchOptions() {
|
|
return this.modelValue.subCommands?.slice(1, -1);
|
|
},
|
|
argvs() {
|
|
return (
|
|
this.modelValue.argvs || this.parseCodeToArgvs(this.modelValue.code)
|
|
);
|
|
},
|
|
},
|
|
methods: {
|
|
handleInputUpdate(index, value) {
|
|
const input = this.currentFunction.config[index];
|
|
this.updateArgvs(input.key, value);
|
|
},
|
|
updateArgvs(key, value) {
|
|
const argvs = {
|
|
...this.argvs,
|
|
[key]: value,
|
|
};
|
|
this.updateModelValue(argvs);
|
|
},
|
|
addBranch(type) {
|
|
this.$emit("addBranch", {
|
|
chainId: this.modelValue.chainId,
|
|
commandType: type,
|
|
value: this.modelValue.value,
|
|
});
|
|
this.updateModelValue(this.argvs || {});
|
|
},
|
|
generateCode(argvs) {
|
|
if (!this.currentFunction?.codeTemplate) return "";
|
|
|
|
let code = this.currentFunction.codeTemplate;
|
|
|
|
const variablePattern = /\${(\w+)}/g;
|
|
code = code.replace(variablePattern, (_, key) => {
|
|
return argvs[key] || "";
|
|
});
|
|
|
|
return code;
|
|
},
|
|
parseCodeToArgvs(code) {
|
|
if (!code) return this.defaultArgvs;
|
|
if (!this.currentFunction?.codeTemplate) return {};
|
|
|
|
const template = this.currentFunction.codeTemplate;
|
|
const argvs = {};
|
|
|
|
// 如果没有变量模板,直接返回空对象
|
|
if (!template.includes("${")) return {};
|
|
|
|
// 将模板转换为正则表达式
|
|
const escapeRegExp = (str) => str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
let pattern = escapeRegExp(template);
|
|
|
|
// 收集所有变量名
|
|
const variables = [];
|
|
const variablePattern = /\${(\w+)}/g;
|
|
let match;
|
|
|
|
while ((match = variablePattern.exec(template)) !== null) {
|
|
variables.push(match[1]);
|
|
pattern = pattern.replace(escapeRegExp(`\${${match[1]}}`), "([^}]*?)");
|
|
}
|
|
|
|
// 创建正则表达式并匹配代码
|
|
const regex = new RegExp(`^${pattern}$`);
|
|
const matches = code.match(regex);
|
|
|
|
if (matches) {
|
|
// 从第二个元素开始,依次赋值给变量
|
|
variables.forEach((variable, index) => {
|
|
argvs[variable] = matches[index + 1] || "";
|
|
});
|
|
return argvs;
|
|
}
|
|
|
|
return this.defaultArgvs;
|
|
},
|
|
updateModelValue(argvs) {
|
|
const code = this.generateCode(argvs);
|
|
|
|
this.$emit("update:modelValue", {
|
|
...this.modelValue,
|
|
argvs,
|
|
code,
|
|
});
|
|
},
|
|
},
|
|
created() {
|
|
// 初始化默认值
|
|
if (this.currentFunction?.config) {
|
|
this.currentFunction.config.forEach((config) => {
|
|
this.defaultArgvs[config.key] = config.defaultValue || "";
|
|
});
|
|
}
|
|
},
|
|
mounted() {
|
|
if (!this.modelValue.code) {
|
|
this.updateModelValue(this.defaultArgvs);
|
|
}
|
|
},
|
|
});
|
|
</script>
|
|
|
|
<style scoped>
|
|
.control-command-wrapper {
|
|
width: 100%;
|
|
display: flex;
|
|
}
|
|
|
|
.control-command {
|
|
width: 100%;
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 8px;
|
|
}
|
|
|
|
.control-type-label {
|
|
font-size: 13px;
|
|
font-weight: 500;
|
|
white-space: nowrap;
|
|
opacity: 0.9;
|
|
user-select: none;
|
|
flex-shrink: 0;
|
|
}
|
|
|
|
.control-settings {
|
|
display: flex;
|
|
flex: 1;
|
|
min-width: 0;
|
|
margin-right: auto;
|
|
}
|
|
|
|
/* ParamInput 容器样式 */
|
|
.control-settings :deep(.param-grid) {
|
|
display: flex;
|
|
flex-wrap: wrap;
|
|
gap: var(--grid-gap);
|
|
width: 100%;
|
|
--grid-gap: 8px;
|
|
}
|
|
|
|
/* 输入项容器样式 */
|
|
.control-settings :deep(.grid-item) {
|
|
min-width: 50px;
|
|
margin: 0;
|
|
display: flex;
|
|
justify-content: center;
|
|
align-items: center;
|
|
}
|
|
|
|
/* 输入框样式 */
|
|
.control-settings :deep(.grid-item > *) {
|
|
flex: 1;
|
|
min-width: 0;
|
|
}
|
|
|
|
.control-btn {
|
|
opacity: 0.7;
|
|
flex-shrink: 0;
|
|
margin-left: auto;
|
|
}
|
|
|
|
.control-btn:hover {
|
|
opacity: 1;
|
|
transform: scale(1.1);
|
|
}
|
|
|
|
/* 暗色模式适配 */
|
|
.body--dark .control-btn {
|
|
color: rgba(255, 255, 255, 0.7);
|
|
}
|
|
|
|
.body--dark .control-btn:hover {
|
|
color: var(--q-primary);
|
|
}
|
|
</style>
|