diff --git a/script/generate-css-vars.js b/script/generate-css-vars.js index 7036d68b2..0e059f418 100644 --- a/script/generate-css-vars.js +++ b/script/generate-css-vars.js @@ -39,7 +39,7 @@ if (combine[COMPONENT_NAME]) { } // 追加到文件 -const cssVariableHeadContent = `\n\n### CSS 变量\n组件提供了下列 CSS 变量,可用于自定义样式。\n名称 | 默认值 | 描述 \n-- | -- | --\n`; +const cssVariableHeadContent = `\n\n### CSS Variables\n组件提供了下列 CSS 变量,可用于自定义样式。\n名称 | 默认值 | 描述 \n-- | -- | --\n`; const cssVariableHeadContentEn = `\n\n### CSS Variables\nThe component provides the following CSS variables, which can be used to customize styles.\nName | Default Value | Description \n-- | -- | --\n`; fs.appendFileSync(resolveCwd(`src/${COMPONENT_NAME}/README.md`), cssVariableHeadContent); diff --git a/src/cascader/README.en-US.md b/src/cascader/README.en-US.md index 9b31dc4ae..2382bd0a6 100644 --- a/src/cascader/README.en-US.md +++ b/src/cascader/README.en-US.md @@ -30,12 +30,16 @@ The component provides the following CSS variables, which can be used to customi Name | Default Value | Description -- | -- | -- --td-cascader-active-color | @brand-color | - ---td-cascader-border-color | @border-color | - ---td-cascader-disabled-color | @font-gray-4 | - ---td-cascader-options-height | 640rpx | - ---td-cascader-options-title-color | @font-gray-3 | - ---td-cascader-step-arrow-color | @font-gray-3 | - +--td-cascader-bg-color | @bg-color-container | - +--td-cascader-border-color | @component-stroke | - +--td-cascader-content-height | 78vh | - +--td-cascader-disabled-color | @text-color-disabled | - +--td-cascader-options-height | calc(100% - @cascader-step-height) | - +--td-cascader-options-title-color | @text-color-placeholder | - +--td-cascader-step-arrow-color | @text-color-placeholder | - --td-cascader-step-dot-size | 16rpx | - --td-cascader-step-height | 88rpx | - ---td-cascader-title-color | @font-gray-1 | - +--td-cascader-title-color | @text-color-primary | - +--td-cascader-title-height | 26rpx | - +--td-cascader-title-padding | @spacer-2 | - --td-cascder-title-font-size | 36rpx | - diff --git a/src/cascader/README.md b/src/cascader/README.md index 52e0a05ac..b277c16d0 100644 --- a/src/cascader/README.md +++ b/src/cascader/README.md @@ -77,17 +77,21 @@ close | `(trigger: TriggerSource)` | `1.0.1`。关闭时触发。[详细类型 pick | `(value: string \| number, index: number)` | `1.0.1`。选择后触发 -### CSS 变量 +### CSS Variables 组件提供了下列 CSS 变量,可用于自定义样式。 名称 | 默认值 | 描述 -- | -- | -- --td-cascader-active-color | @brand-color | - ---td-cascader-border-color | @border-color | - ---td-cascader-disabled-color | @font-gray-4 | - ---td-cascader-options-height | 640rpx | - ---td-cascader-options-title-color | @font-gray-3 | - ---td-cascader-step-arrow-color | @font-gray-3 | - +--td-cascader-bg-color | @bg-color-container | - +--td-cascader-border-color | @component-stroke | - +--td-cascader-content-height | 78vh | - +--td-cascader-disabled-color | @text-color-disabled | - +--td-cascader-options-height | calc(100% - @cascader-step-height) | - +--td-cascader-options-title-color | @text-color-placeholder | - +--td-cascader-step-arrow-color | @text-color-placeholder | - --td-cascader-step-dot-size | 16rpx | - --td-cascader-step-height | 88rpx | - ---td-cascader-title-color | @font-gray-1 | - +--td-cascader-title-color | @text-color-primary | - +--td-cascader-title-height | 26rpx | - +--td-cascader-title-padding | @spacer-2 | - --td-cascder-title-font-size | 36rpx | - diff --git a/src/cascader/cascader.less b/src/cascader/cascader.less index 41046c0b0..b763609c1 100644 --- a/src/cascader/cascader.less +++ b/src/cascader/cascader.less @@ -6,12 +6,13 @@ @cascader-active-color: var(--td-cascader-active-color, @brand-color); @cascader-disabled-color: var(--td-cascader-disabled-color, @text-color-disabled); @cascader-title-color: var(--td-cascader-title-color, @text-color-primary); +@cascader-title-height: var(--td-cascader-title-height, 26rpx); +@cascader-title-padding: var(--td-cascader-title-padding, @spacer-2); +@cascder-title-font-size: var(--td-cascder-title-font-size, 36rpx); @cascader-options-title-color: var(--td-cascader-options-title-color, @text-color-placeholder); @cascader-border-color: var(--td-cascader-border-color, @component-stroke); - -@cascader-options-height: var(--td-cascader-options-height, 640rpx); -@cascder-title-font-size: var(--td-cascder-title-font-size, 36rpx); - +@cascader-content-height: var(--td-cascader-content-height, 78vh); +@cascader-options-height: var(--td-cascader-options-height, calc(100% - @cascader-step-height)); // steps @cascader-step-height: var(--td-cascader-step-height, 88rpx); @cascader-step-dot-size: var(--td-cascader-step-dot-size, 16rpx); @@ -22,14 +23,14 @@ flex-direction: column; background-color: @cascader-bg-color; color: @cascader-title-color; - border-radius: 24rpx 24rpx 0 0; + border-radius: @radius-extra-large @radius-extra-large 0 0; --td-radio-icon-checked-color: @cascader-active-color; --td-tab-item-active-color: @cascader-active-color; --td-tab-track-color: @cascader-active-color; &__close-btn { - right: 16px; - top: 12px; + right: 32rpx; + top: 24rpx; position: absolute; } @@ -37,37 +38,32 @@ position: relative; font-weight: 700; text-align: center; - line-height: 48px; + line-height: @cascader-title-height; + padding: @cascader-title-padding; font-size: @cascder-title-font-size; } &__content { width: 100%; - flex: 1; + height: @cascader-content-height; display: flex; flex-direction: column; } &__options { width: 100vw; - height: @cascader-options-height; &-title { - margin-top: 40rpx; color: @cascader-options-title-color; - font-size: 28rpx; + font-size: @font-size-base; line-height: 44rpx; - padding-left: 16px; - } - - &-content { - flex: 1; - height: 100%; - overflow: auto; - padding-left: 16px; + padding-top: 40rpx; + padding-left: @spacer-2; + box-sizing: border-box; } &-container { + flex: 1; display: flex; transition: all ease 0.3s; } @@ -88,7 +84,7 @@ width: @cascader-step-dot-size; height: @cascader-step-dot-size; border-radius: 50%; - border: 1px solid @cascader-active-color; + border: 2rpx solid @cascader-active-color; box-sizing: border-box; &:not(.@{cascader}__step-dot--last)::after { @@ -98,7 +94,7 @@ left: 50%; top: calc(@cascader-step-dot-size + 14rpx); height: 36rpx; - width: 1px; + width: 2rpx; background: @cascader-active-color; transform: translateX(-50%); } @@ -110,8 +106,8 @@ } &-label { - padding-left: 16px; - font-size: 16px; + padding-left: @spacer-2; + font-size: @font-size-m; &--active { color: @cascader-active-color; diff --git a/src/cascader/cascader.ts b/src/cascader/cascader.ts index b3d337d9b..6d2ac01e1 100644 --- a/src/cascader/cascader.ts +++ b/src/cascader/cascader.ts @@ -24,6 +24,14 @@ function parseOptions(options: OptionsType, keys: KeysType) { }); } +const defaultState = { + contentHeight: 0, + stepHeight: 0, + tabsHeight: 0, + subTitlesHeight: 0, + stepsInitHeight: 0, +}; + @wxComponent() export default class Cascader extends SuperComponent { externalClasses = [`${prefix}-class`]; @@ -42,6 +50,10 @@ export default class Cascader extends SuperComponent { }, ]; + state = { + ...defaultState, + }; + data = { prefix, name, @@ -50,16 +62,22 @@ export default class Cascader extends SuperComponent { selectedValue: [], scrollTopList: [], steps: [], + _optionsHeight: 0, }; observers = { visible(v) { if (v) { const $tabs = this.selectComponent('#tabs'); - $tabs?.setTrack(); + $tabs?.getTabHeight().then((res) => { + this.state.tabsHeight = res.height; + }); + this.initOptionsHeight(this.data.steps.length); this.updateScrollTop(); this.initWithValue(); + } else { + this.state = { ...defaultState }; } }, @@ -78,6 +96,7 @@ export default class Cascader extends SuperComponent { }); }, selectedIndexes() { + const { visible, theme } = this.properties; const { selectedValue, steps, items } = this.genItems(); this.setData({ @@ -85,7 +104,12 @@ export default class Cascader extends SuperComponent { selectedValue, stepIndex: items.length - 1, }); + + if (visible && theme === 'step') { + this.updateOptionsHeight(steps.length); + } }, + async stepIndex() { const { visible } = this.data; @@ -96,6 +120,42 @@ export default class Cascader extends SuperComponent { }; methods = { + updateOptionsHeight(steps: number) { + const { contentHeight, stepsInitHeight, stepHeight, subTitlesHeight } = this.state; + this.setData({ + _optionsHeight: contentHeight - stepsInitHeight - subTitlesHeight - (steps - 1) * stepHeight, + }); + }, + + async initOptionsHeight(steps: number) { + const { theme, subTitles } = this.properties; + + const { height } = await getRect(this, `.${name}__content`); + this.state.contentHeight = height; + + if (theme === 'step') { + await Promise.all([getRect(this, `.${name}__steps`), getRect(this, `.${name}__step`)]).then( + ([stepsRect, stepRect]) => { + this.state.stepsInitHeight = stepsRect.height - (steps - 1) * stepRect.height; + this.state.stepHeight = stepRect.height; + }, + ); + } + + if (subTitles.length > 0) { + const { height } = await getRect(this, `.${name}__options-title`); + this.state.subTitlesHeight = height; + } + + const optionsInitHeight = this.state.contentHeight - this.state.subTitlesHeight; + this.setData({ + _optionsHeight: + theme === 'step' + ? optionsInitHeight - this.state.stepsInitHeight - (steps - 1) * this.state.stepHeight + : optionsInitHeight - this.state.tabsHeight, + }); + }, + initWithValue() { if (this.data.value != null && this.data.value !== '') { const selectedIndexes = this.getIndexesByValue(this.data.options, this.data.value); diff --git a/src/cascader/cascader.wxml b/src/cascader/cascader.wxml index ce3b5cb68..f1068945d 100644 --- a/src/cascader/cascader.wxml +++ b/src/cascader/cascader.wxml @@ -43,6 +43,8 @@ class="{{name}}__options" scroll-y scroll-top="{{scrollTopList[index]}}" + type="list" + style="height: {{_optionsHeight}}px" > ((resolve, reject) => { if (this.trackWidth) {