element-plus の el-select の全選択メソッドのカプセル化。
起因:
プロジェクトは vue3+elmentui-plus+ts でビルドされています。ユーザー インターフェイスの設計には、すべてを選択するドロップダウン選択ボックスが必要です。しかし、エレメントプラスの公式サイトが提供するドロップダウンの複数選択ボックスには、
この形式では全選択ボタンがなく、想定されている全選択の操作に準拠していないスタイルとなっています。そこで、新しい条件を組み合わせて新しいコンポーネントをカプセル化する方法を考え始めました。
結果を示す:
設計原理:
ユーザーは全選択のドロップダウン ボックスを好み、右側の √ 選択マークを好まないため、複数選択ボックスと同じ選択ボックスに置き換える必要があります。既存の条件では、el-select + el-checkbox フォームを使用してこのコンポーネントを作成します。
コンポーネント コードの合成により、サブコンポーネント selectCheckBox.vue ファイルが作成されます
html部分
<el-select
v-model="menusTitle"
multiple
collapse-tags
collapse-tags-tooltip
:placeholder="props.placeholder"
clearable
@clear="clearData"
>
<!-- @change="changeSelectMenu" -->
<el-checkbox v-model="checkedAll" @change="selectAll">全选</el-checkbox>
<el-option
v-for="(item, index) in menuList"
:key="item[props.id]"
:value="item[props.id]"
>
<el-checkbox
:label="item[props.label]"
size="large"
@change="changeCheckBox(item, index)"
:checked="isChecked(item, index)"
v-model="checkBoxObj[index]"
/>
</el-option>
</el-select>
js部分
<script lang="ts" setup>
import { ref, reactive, defineProps, defineEmits } from "vue";
const props = defineProps({
list: { type: Array, required: true },
id: { type: String, required: true },
label: { type: String, required: true },
modelValue: { type: Array },
placeholder: { type: String, default: "选择" },
});
const emit = defineEmits(["update:modelValue"]);
const value = ref("");
const checkedAll = ref("false");
const menus = ref([]);
const menuList = props.list;
const checkBoxObj = ref({});
menuList.forEach((res, index) => {
checkBoxObj.value[index] = false;
});
const menusTitle = ref([]);
const changeSelectMenu = (val) => {};
const selectAll = (value) => {
menus.value = [];
menusTitle.value = [];
if (value) {
menuList.forEach((item, index) => {
menus.value.push(item[props.id]);
menusTitle.value.push(item[props.label]);
checkBoxObj.value[index] = true;
});
} else {
menus.value = [];
menusTitle.value = [];
menuList.forEach((item, index) => {
checkBoxObj.value[index] = false;
});
}
emit("update:modelValue", menus.value);
};
const isChecked = (item) => {
return menus.value.indexOf(item[props.id]) > -1;
};
const changeCheckBox = (item, index) => {
let i = menus.value.indexOf(item[props.id]);
if (i == -1) {
menus.value.push(item[props.id]);
menusTitle.value.push(item[props.label]);
} else {
menus.value.splice(i, 1);
menusTitle.value.splice(i, 1);
}
if (menus.value.length == menuList.length) {
checkedAll.value = true;
} else {
checkedAll.value = false;
}
emit("update:modelValue", menus.value);
};
const clearData = () => {
menus.value = [];
menusTitle.value = [];
emit("update:modelValue", menus.value);
checkedAll.value = false;
menuList.forEach((item, index) => {
checkBoxObj.value[index] = false;
});
};
</script>
CSS部分:
<style lang="scss" scoped>
.el-select-dropdown {
.el-checkbox {
display: flex;
align-items: center;
padding-left: 20px;
width: 100%;
box-sizing: border-box;
}
.el-select-dropdown__item {
// background-color: red !important;
padding: 0;
display: flex;
align-items: center;
}
}
</style>
親コンポーネントの呼び出し
htmlインポート部分
<selectCheckBox
v-model="value3 "
:list="options"
id="value"
label="label"
placeholder="选择项目"
></selectCheckBox>
jsインポート部分
import selectCheckBox from "@_components/dataClassification/selectCheckBox.vue";
const value3 = ref([]);
const options = [
{
value: "1",
label: "项目一",
},
{
value: "2",
label: "项目二",
},
{
value: "3",
label: "项目三",
},
];
要約する
コンポーネントはまだアップグレード中であり、セカンダリ パッケージング コンポーネントが処理されています。さらなるカプセル化プロセスの目標は、クラス el-select のパラメータ コンポーネントを作成することです。今日は記録として残しておいてください。