From 8c646d5a8a6ea2a7b4ee527e41284cdd7bc49f19 Mon Sep 17 00:00:00 2001 From: 07akioni <07akioni2@gmail.com> Date: Fri, 6 Mar 2020 19:54:45 +0800 Subject: [PATCH] fix(dropdown): placement bugs --- src/Dropdown/src/DropdownSubmenu.vue | 37 +++++++++++------- src/_utils/component/dropdown.js | 1 - src/_utils/dom/calcPlacementTransform.js | 50 ++++++++++++------------ styles/BaseSelectMenu.scss | 1 + styles/Dropdown.scss | 4 +- 5 files changed, 52 insertions(+), 41 deletions(-) diff --git a/src/Dropdown/src/DropdownSubmenu.vue b/src/Dropdown/src/DropdownSubmenu.vue index 65e1f3f43..2ac1c2192 100644 --- a/src/Dropdown/src/DropdownSubmenu.vue +++ b/src/Dropdown/src/DropdownSubmenu.vue @@ -168,11 +168,16 @@ export default { this.vanishTimerId = window.setTimeout(() => { this.menuActivated = false }, this.duration) + }, + getAbsoluteOffsetContainer () { + return this.$el.parentElement + }, + getTrackedElement () { + return this.$el.parentElement } }, render (h) { return h('div', { - ref: 'activator', staticClass: 'n-dropdown-item n-dropdown-item--as-submenu', on: { mouseenter: this.handleMouseEnter, @@ -189,22 +194,26 @@ export default { h(iosArrowForward) ]) : null ]), - h('transition', { - props: { - name: 'n-dropdown-menu-transition' - } + h('div', { + ref: 'content', + staticClass: 'n-dropdown-menu-wrapper' }, [ - this.active ? h(NDropdownMenu, { - ref: 'content', - staticClass: 'n-dropdown-submenu', - style: this.style, + h('transition', { props: { - options: this.options, - theme: this.syntheticTheme, - defaultFocus: false, - size: this.size + name: 'n-dropdown-menu-transition' } - }) : null + }, [ + this.active ? h(NDropdownMenu, { + staticClass: 'n-dropdown-submenu', + style: this.style, + props: { + options: this.options, + theme: this.syntheticTheme, + defaultFocus: false, + size: this.size + } + }) : null + ]) ]) ]) } diff --git a/src/_utils/component/dropdown.js b/src/_utils/component/dropdown.js index 39eaefe78..3e746c896 100644 --- a/src/_utils/component/dropdown.js +++ b/src/_utils/component/dropdown.js @@ -46,7 +46,6 @@ function createSelectOptionsFromDropdownOptions (dropdownOptions, DropdownSubmen selectOptions.push(createSelectOptionForDropdownDivider(option, DropdownDivider)) } }) - console.log('createSelectOptionsFromDropdownOptions', selectOptions) return selectOptions } diff --git a/src/_utils/dom/calcPlacementTransform.js b/src/_utils/dom/calcPlacementTransform.js index fe6da7ff7..cee6fd4da 100644 --- a/src/_utils/dom/calcPlacementTransform.js +++ b/src/_utils/dom/calcPlacementTransform.js @@ -73,7 +73,7 @@ export function getTransformOriginByPlacement (placement) { return placementToTransformOrigin[placement] || null } -export function getPosition (placement, offsetContainerRect, activatorRect) { +export function getPosition (placement, offsetContainerRect, trackedRect) { const offset = { top: null, bottom: null, @@ -82,50 +82,50 @@ export function getPosition (placement, offsetContainerRect, activatorRect) { transform: null } if (placement === 'bottom-start') { - offset.top = (activatorRect.top - offsetContainerRect.top + activatorRect.height) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top + trackedRect.height) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left) + 'px' } else if (placement === 'bottom-end') { - offset.top = (activatorRect.top - offsetContainerRect.top + activatorRect.height) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left + activatorRect.width) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top + trackedRect.height) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left + trackedRect.width) + 'px' offset.transform = 'translateX(-100%)' } else if (placement === 'top-start') { - offset.top = (activatorRect.top - offsetContainerRect.top) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left) + 'px' offset.transform = 'translateY(-100%)' } else if (placement === 'top-end') { - offset.top = (activatorRect.top - offsetContainerRect.top) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left + activatorRect.width) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left + trackedRect.width) + 'px' offset.transform = 'translateY(-100%) translateX(-100%)' } else if (placement === 'right-start') { - offset.top = (activatorRect.top - offsetContainerRect.top) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left + activatorRect.width) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left + trackedRect.width) + 'px' } else if (placement === 'right-end') { - offset.top = (activatorRect.top - offsetContainerRect.top + activatorRect.height) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left + activatorRect.width) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top + trackedRect.height) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left + trackedRect.width) + 'px' offset.transform = 'translateY(-100%)' } else if (placement === 'left-start') { - offset.top = (activatorRect.top - offsetContainerRect.top) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left) + 'px' offset.transform = 'translateX(-100%)' } else if (placement === 'left-end') { - offset.top = (activatorRect.top - offsetContainerRect.top + activatorRect.height) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top + trackedRect.height) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left) + 'px' offset.transform = 'translateX(-100%) translateY(-100%)' } else if (placement === 'top') { - offset.top = (activatorRect.top - offsetContainerRect.top) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left + activatorRect.width / 2) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left + trackedRect.width / 2) + 'px' offset.transform = 'translateX(-50%) translateY(-100%)' } else if (placement === 'right') { - offset.top = (activatorRect.top - offsetContainerRect.top + activatorRect.height / 2) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left + activatorRect.width) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top + trackedRect.height / 2) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left + trackedRect.width) + 'px' offset.transform = 'translateY(-50%)' } else if (placement === 'bottom') { - offset.top = (activatorRect.top - offsetContainerRect.top + activatorRect.height) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left + activatorRect.width / 2) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top + trackedRect.height) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left + trackedRect.width / 2) + 'px' offset.transform = 'translateX(-50%)' } else if (placement === 'left') { - offset.top = (activatorRect.top - offsetContainerRect.top + activatorRect.height / 2) + 'px' - offset.left = (activatorRect.left - offsetContainerRect.left) + 'px' + offset.top = (trackedRect.top - offsetContainerRect.top + trackedRect.height / 2) + 'px' + offset.left = (trackedRect.left - offsetContainerRect.left) + 'px' offset.transform = 'translateX(-100%) translateY(-50%)' } else { console.error( diff --git a/styles/BaseSelectMenu.scss b/styles/BaseSelectMenu.scss index d43029b1f..60db21cda 100644 --- a/styles/BaseSelectMenu.scss +++ b/styles/BaseSelectMenu.scss @@ -70,6 +70,7 @@ transition: color .3s $--n-ease-in-out-cubic-bezier; text-overflow: ellipsis; overflow: hidden; + box-sizing: border-box; @include m(grouped) { padding: 0 21px; } diff --git a/styles/Dropdown.scss b/styles/Dropdown.scss index 8503c5b16..f0b41eea8 100644 --- a/styles/Dropdown.scss +++ b/styles/Dropdown.scss @@ -90,10 +90,12 @@ @include b(dropdown-divider) { margin: 2px 0; } + @include b(dropdown-menu-wrapper) { + position: absolute !important; + } @include b(dropdown-submenu) { @include fade-in-scale-up-transition(dropdown-menu); margin-top: 0; - position: absolute !important; margin-left: 6px; margin-right: 6px; }