小程序初始提交
This commit is contained in:
@@ -0,0 +1,189 @@
|
||||
<template>
|
||||
<view
|
||||
class="cl-select-trigger"
|
||||
:class="[
|
||||
{
|
||||
'is-dark': isDark,
|
||||
'cl-select-trigger--disabled': isDisabled,
|
||||
'cl-select-trigger--focus': focus,
|
||||
'cl-select-trigger--error': isError
|
||||
},
|
||||
pt.className
|
||||
]"
|
||||
@tap="open"
|
||||
>
|
||||
<view class="cl-select-trigger__content">
|
||||
<cl-text
|
||||
v-if="showText"
|
||||
:pt="{
|
||||
className: parseClass([
|
||||
{
|
||||
'text-surface-400': isDisabled
|
||||
},
|
||||
pt.text?.className
|
||||
])
|
||||
}"
|
||||
ellipsis
|
||||
>
|
||||
{{ text }}
|
||||
</cl-text>
|
||||
|
||||
<cl-text
|
||||
:pt="{
|
||||
className: parseClass(['text-surface-400', pt.placeholder?.className])
|
||||
}"
|
||||
v-else
|
||||
>
|
||||
{{ placeholder }}
|
||||
</cl-text>
|
||||
</view>
|
||||
|
||||
<view v-if="showText && !isDisabled" class="cl-select-trigger__icon" @tap.stop="clear">
|
||||
<cl-icon
|
||||
name="close-circle-fill"
|
||||
:size="32"
|
||||
:pt="{ className: 'text-surface-400' }"
|
||||
></cl-icon>
|
||||
</view>
|
||||
|
||||
<view v-if="!isDisabled && !showText" class="cl-select-trigger__icon">
|
||||
<cl-icon
|
||||
:name="pt.icon?.name ?? arrowIcon"
|
||||
:size="pt.icon?.size ?? 32"
|
||||
:pt="{
|
||||
className: `text-surface-400 ${pt.icon?.className}`
|
||||
}"
|
||||
></cl-icon>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { computed } from "vue";
|
||||
import type { ClIconProps } from "../cl-icon/props";
|
||||
import { isDark, parseClass, parsePt } from "@/cool";
|
||||
import { t } from "@/locale";
|
||||
import type { PassThroughProps } from "../../types";
|
||||
import { useForm, useFormItem } from "../../hooks";
|
||||
|
||||
defineOptions({
|
||||
name: "cl-select-trigger"
|
||||
});
|
||||
|
||||
// 组件属性定义
|
||||
const props = defineProps({
|
||||
// 透传样式配置
|
||||
pt: {
|
||||
type: Object,
|
||||
default: () => ({})
|
||||
},
|
||||
// 显示文本
|
||||
text: {
|
||||
type: String,
|
||||
default: ""
|
||||
},
|
||||
// 占位符文本
|
||||
placeholder: {
|
||||
type: String,
|
||||
default: () => t("请选择")
|
||||
},
|
||||
// 箭头图标名称
|
||||
arrowIcon: {
|
||||
type: String,
|
||||
default: "arrow-down-s-line"
|
||||
},
|
||||
// 是否禁用选择器
|
||||
disabled: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
},
|
||||
// 是否聚焦
|
||||
focus: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
});
|
||||
|
||||
const emit = defineEmits(["open", "clear"]);
|
||||
|
||||
// cl-form 上下文
|
||||
const { disabled } = useForm();
|
||||
|
||||
// cl-form-item 上下文
|
||||
const { isError } = useFormItem();
|
||||
|
||||
// 是否禁用
|
||||
const isDisabled = computed(() => {
|
||||
return disabled.value || props.disabled;
|
||||
});
|
||||
|
||||
// 透传样式类型定义
|
||||
type PassThrough = {
|
||||
className?: string; // 根元素类名
|
||||
icon?: ClIconProps; // 图标样式
|
||||
placeholder?: PassThroughProps; // 占位符样式
|
||||
text?: PassThroughProps; // 文本样式
|
||||
};
|
||||
|
||||
// 解析透传样式配置
|
||||
const pt = computed(() => parsePt<PassThrough>(props.pt));
|
||||
|
||||
// 是否显示文本
|
||||
const showText = computed(() => props.text != "");
|
||||
|
||||
// 清空文本
|
||||
function clear() {
|
||||
emit("clear");
|
||||
}
|
||||
|
||||
// 打开选择器
|
||||
function open() {
|
||||
if (isDisabled.value) {
|
||||
return;
|
||||
}
|
||||
|
||||
emit("open");
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.cl-select-trigger {
|
||||
@apply flex flex-row items-center w-full box-border;
|
||||
@apply border border-solid border-surface-200 rounded-lg bg-white;
|
||||
height: 66rpx;
|
||||
padding: 0 20rpx;
|
||||
|
||||
&__content {
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
@apply flex flex-row items-center justify-center;
|
||||
padding-left: 20rpx;
|
||||
}
|
||||
|
||||
&--disabled {
|
||||
@apply bg-surface-100 opacity-70;
|
||||
}
|
||||
|
||||
&--focus {
|
||||
@apply border-primary-500;
|
||||
|
||||
&.is-dark {
|
||||
@apply border-primary-500;
|
||||
}
|
||||
}
|
||||
|
||||
&--error {
|
||||
@apply border-red-500;
|
||||
}
|
||||
|
||||
&.is-dark {
|
||||
@apply border-surface-700 bg-surface-800;
|
||||
|
||||
&.cl-select-trigger--disabled {
|
||||
@apply bg-surface-700;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -0,0 +1,19 @@
|
||||
import type { ClIconProps } from "../cl-icon/props";
|
||||
import type { PassThroughProps } from "../../types";
|
||||
|
||||
export type ClSelectTriggerPassThrough = {
|
||||
className?: string;
|
||||
icon?: ClIconProps;
|
||||
placeholder?: PassThroughProps;
|
||||
text?: PassThroughProps;
|
||||
};
|
||||
|
||||
export type ClSelectTriggerProps = {
|
||||
className?: string;
|
||||
pt?: ClSelectTriggerPassThrough;
|
||||
text?: string;
|
||||
placeholder?: string;
|
||||
arrowIcon?: string;
|
||||
disabled?: boolean;
|
||||
focus?: boolean;
|
||||
};
|
||||
Reference in New Issue
Block a user