Refactor #5681, #5682, #5683 - For AutoComplete, CascadeSelect, Tree, TreeSelect

This commit is contained in:
tugcekucukoglu 2024-05-03 14:46:02 +03:00
parent 4c481aef89
commit d9d2be9cca
16 changed files with 213 additions and 115 deletions

View file

@ -112,35 +112,35 @@ export interface TreePassThroughOptions<T = any> {
* Used to pass attributes to the input's DOM element.
* @see {@link InputTextPassThroughOptions}
*/
input?: InputTextPassThroughOptions<TreeSharedPassThroughMethodOptions>;
filterInput?: InputTextPassThroughOptions<TreeSharedPassThroughMethodOptions>;
/**
* Used to pass attributes to the search icon's DOM element.
* Used to pass attributes to the filter icon's DOM element.
*/
searchIcon?: TreePassThroughOptionType<T>;
filterIcon?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the wrapper's DOM element.
*/
wrapper?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the container's DOM element.
* Used to pass attributes to the root children's DOM element.
*/
container?: TreePassThroughOptionType<T>;
rootChildren?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the node's DOM element.
*/
node?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the content's DOM element.
* Used to pass attributes to the node content's DOM element.
*/
content?: TreePassThroughOptionType<T>;
nodeContent?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the toggler's DOM element.
* Used to pass attributes to the node toggle button's DOM element.
*/
toggler?: TreePassThroughOptionType<T>;
nodeToggleButton?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the toggler icon's DOM element.
* Used to pass attributes to the node toggle icon's DOM element.
*/
togglerIcon?: TreePassThroughOptionType<T>;
nodeToggleIcon?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the checkbox's DOM element.
*/
@ -150,17 +150,17 @@ export interface TreePassThroughOptions<T = any> {
*/
nodeIcon?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the label's DOM element.
* Used to pass attributes to the node label's DOM element.
*/
label?: TreePassThroughOptionType<T>;
nodeLabel?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the subgroup's DOM element.
* Used to pass attributes to the node children's DOM element.
*/
subgroup?: TreePassThroughOptionType<T>;
nodeChildren?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the loading overlay's DOM element.
* Used to pass attributes to the mask's DOM element.
*/
loadingOverlay?: TreePassThroughOptionType<T>;
mask?: TreePassThroughOptionType<T>;
/**
* Used to pass attributes to the loading icon's DOM element.
*/
@ -349,6 +349,7 @@ export interface TreeSlots {
class: string;
}): VNode[];
/**
* @deprecated since v4.0. Use 'filtericon' slot instead.
* Custom search icon template.
* @param {Object} scope - searchicon slot's params.
*/
@ -358,6 +359,16 @@ export interface TreeSlots {
*/
class: string;
}): VNode[];
/**
* Custom search icon template.
* @param {Object} scope - filtericon slot's params.
*/
filtericon(scope: {
/**
* Style class of the icon.
*/
class: string;
}): VNode[];
/**
* Custom toggler icon template.
* @param {Object} scope - togglericon slot's params.

View file

@ -1,7 +1,7 @@
<template>
<div :class="cx('root')" v-bind="ptmi('root')">
<template v-if="loading && loadingMode === 'mask'">
<div :class="cx('loadingOverlay')" v-bind="ptm('loadingOverlay')">
<div :class="cx('mask')" v-bind="ptm('mask')">
<slot name="loadingicon" :class="cx('loadingIcon')">
<i v-if="loadingIcon" :class="[cx('loadingIcon'), 'pi-spin', loadingIcon]" v-bind="ptm('loadingIcon')" />
<SpinnerIcon v-else spin :class="cx('loadingIcon')" v-bind="ptm('loadingIcon')" />
@ -9,13 +9,14 @@
</div>
</template>
<div v-if="filter" :class="cx('filterContainer')" v-bind="ptm('filterContainer')">
<InputText v-model="filterValue" autocomplete="off" :class="cx('input')" :placeholder="filterPlaceholder" @keydown="onFilterKeydown" v-bind="ptm('input')" />
<slot name="searchicon" :class="cx('searchIcon')">
<SearchIcon :class="cx('searchIcon')" v-bind="ptm('searchIcon')" />
<InputText v-model="filterValue" autocomplete="off" :class="cx('filterInput')" :placeholder="filterPlaceholder" @keydown="onFilterKeydown" v-bind="ptm('filterInput')" />
<!--TODO: searchicon deprecated since v4.0-->
<slot :name="$slots.searchicon ? 'searchicon' : 'filtericon'" :class="cx('filterIcon')">
<SearchIcon :class="cx('filterIcon')" v-bind="ptm('filterIcon')" />
</slot>
</div>
<div :class="cx('wrapper')" :style="{ maxHeight: scrollHeight }" v-bind="ptm('wrapper')">
<ul :class="cx('container')" role="tree" :aria-labelledby="ariaLabelledby" :aria-label="ariaLabel" v-bind="ptm('container')">
<ul :class="cx('rootChildren')" role="tree" :aria-labelledby="ariaLabelledby" :aria-label="ariaLabel" v-bind="ptm('rootChildren')">
<TreeNode
v-for="(node, index) of valueToRender"
:key="node.key"

View file

@ -12,18 +12,18 @@
:aria-checked="ariaChecked"
:tabindex="index === 0 ? 0 : -1"
@keydown="onKeyDown"
v-bind="level === 1 ? getPTOptions('node') : ptm('subgroup')"
v-bind="level === 1 ? getPTOptions('node') : ptm('nodeChildren')"
>
<div :class="cx('content')" @click="onClick" @touchend="onTouchEnd" :style="node.style" v-bind="getPTOptions('content')" :data-p-highlight="checkboxMode ? checked : selected" :data-p-selectable="selectable">
<button v-ripple type="button" :class="cx('toggler')" @click="toggle" tabindex="-1" aria-hidden="true" v-bind="getPTOptions('toggler')">
<div :class="cx('nodeContent')" @click="onClick" @touchend="onTouchEnd" :style="node.style" v-bind="getPTOptions('nodeContent')" :data-p-highlight="checkboxMode ? checked : selected" :data-p-selectable="selectable">
<button v-ripple type="button" :class="cx('nodeToggleButton')" @click="toggle" tabindex="-1" aria-hidden="true" v-bind="getPTOptions('nodeToggleButton')">
<template v-if="node.loading && loadingMode === 'icon'">
<component v-if="templates['nodetogglericon']" :is="templates['nodetogglericon']" :class="cx('nodetogglericon')" />
<SpinnerIcon v-else spin :class="cx('nodetogglericon')" v-bind="ptm('nodetogglericon')" />
</template>
<template v-else>
<component v-if="templates['togglericon']" :is="templates['togglericon']" :node="node" :expanded="expanded" :class="cx('togglerIcon')" />
<component v-else-if="expanded" :is="node.expandedIcon ? 'span' : 'ChevronDownIcon'" :class="cx('togglerIcon')" v-bind="getPTOptions('togglerIcon')" />
<component v-else :is="node.collapsedIcon ? 'span' : 'ChevronRightIcon'" :class="cx('togglerIcon')" v-bind="getPTOptions('togglerIcon')" />
<component v-if="templates['togglericon']" :is="templates['togglericon']" :node="node" :expanded="expanded" :class="cx('nodeToggleIcon')" />
<component v-else-if="expanded" :is="node.expandedIcon ? 'span' : 'ChevronDownIcon'" :class="cx('nodeToggleIcon')" v-bind="getPTOptions('nodeToggleIcon')" />
<component v-else :is="node.collapsedIcon ? 'span' : 'ChevronRightIcon'" :class="cx('nodeToggleIcon')" v-bind="getPTOptions('nodeToggleIcon')" />
</template>
</button>
<Checkbox v-if="checkboxMode" :modelValue="checked" :binary="true" :indeterminate="partialChecked" :class="cx('nodeCheckbox')" :tabindex="-1" :unstyled="unstyled" :pt="getPTOptions('nodeCheckbox')" :data-p-partialchecked="partialChecked">
@ -33,12 +33,12 @@
</Checkbox>
<component v-if="templates['nodeicon']" :is="templates['nodeicon']" :node="node" :class="[cx('nodeIcon')]" v-bind="getPTOptions('nodeIcon')"></component>
<span v-else :class="[cx('nodeIcon'), node.icon]" v-bind="getPTOptions('nodeIcon')"></span>
<span :class="cx('label')" v-bind="getPTOptions('label')" @keydown.stop>
<span :class="cx('nodeLabel')" v-bind="getPTOptions('nodeLabel')" @keydown.stop>
<component v-if="templates[node.type] || templates['default']" :is="templates[node.type] || templates['default']" :node="node" />
<template v-else>{{ label(node) }}</template>
</span>
</div>
<ul v-if="hasChildren && expanded" :class="cx('subgroup')" role="group" v-bind="ptm('subgroup')">
<ul v-if="hasChildren && expanded" :class="cx('nodeChildren')" role="group" v-bind="ptm('nodeChildren')">
<TreeNode
v-for="childNode of node.children"
:key="childNode.key"
@ -134,7 +134,7 @@ export default {
});
},
onClick(event) {
if (this.toggleClicked || DomHandler.getAttribute(event.target, '[data-pc-section="toggler"]') || DomHandler.getAttribute(event.target.parentElement, '[data-pc-section="toggler"]')) {
if (this.toggleClicked || DomHandler.getAttribute(event.target, '[data-pc-section="nodetogglebutton"]') || DomHandler.getAttribute(event.target.parentElement, '[data-pc-section="nodetogglebutton"]')) {
this.toggleClicked = false;
return;
@ -199,7 +199,7 @@ export default {
}
},
onArrowDown(event) {
const nodeElement = event.target.getAttribute('data-pc-section') === 'toggler' ? event.target.closest('[role="treeitem"]') : event.target;
const nodeElement = event.target.getAttribute('data-pc-section') === 'nodetogglebutton' ? event.target.closest('[role="treeitem"]') : event.target;
const listElement = nodeElement.children[1];
if (listElement) {
@ -244,7 +244,7 @@ export default {
});
},
onArrowLeft(event) {
const togglerElement = DomHandler.findSingle(event.currentTarget, '[data-pc-section="toggler"]');
const togglerElement = DomHandler.findSingle(event.currentTarget, '[data-pc-section="nodetogglebutton"]');
if (this.level === 0 && !this.expanded) {
return false;
@ -272,7 +272,7 @@ export default {
this.setAllNodesTabIndexes();
},
setAllNodesTabIndexes() {
const nodes = DomHandler.find(this.$refs.currentNode.closest('[data-pc-section="container"]'), '[role="treeitem"]');
const nodes = DomHandler.find(this.$refs.currentNode.closest('[data-pc-section="rootchildren"]'), '[role="treeitem"]');
const hasSelectedNode = [...nodes].some((node) => node.getAttribute('aria-selected') === 'true' || node.getAttribute('aria-checked') === 'true');

View file

@ -159,7 +159,7 @@ const theme = ({ dt }) => `
height: 2rem;
}
.p-tree-mask {
.p-tree .p-tree-mask {
position: absolute;
z-index: 1;
display: flex;
@ -188,15 +188,15 @@ const classes = {
'p-tree-flex-scrollable': props.scrollHeight === 'flex'
}
],
loadingOverlay: 'p-tree-mask p-component-overlay',
mask: 'p-tree-mask p-component-overlay',
loadingIcon: 'p-tree-loading-icon',
filterContainer: 'p-tree-filter-container',
input: 'p-tree-filter-input',
searchIcon: 'p-tree-filter-icon',
wrapper: 'p-tree-root',
container: 'p-tree-root-children',
filterInput: 'p-tree-filter-input',
filterIcon: 'p-tree-filter-icon',
wrapper: 'p-tree-root', //TODO: discuss
rootChildren: 'p-tree-root-children',
node: ({ instance }) => ['p-tree-node', { 'p-tree-node-leaf': instance.leaf }],
content: ({ instance }) => [
nodeContent: ({ instance }) => [
'p-tree-node-content',
instance.node.styleClass,
{
@ -204,13 +204,13 @@ const classes = {
'p-tree-node-selected': instance.checkboxMode && instance.$parentInstance.highlightOnSelect ? instance.checked : instance.selected
}
],
toggler: 'p-tree-node-toggle-button',
togglerIcon: 'p-tree-node-toggle-icon',
nodeTogglerIcon: 'p-tree-node-toggler-icon', //todo: discuss
nodeToggleButton: 'p-tree-node-toggle-button',
nodeToggleIcon: 'p-tree-node-toggle-icon',
nodeTogglerIcon: 'p-tree-node-toggler-icon', //TODO: discuss
nodeCheckbox: 'p-tree-node-checkbox',
nodeIcon: 'p-tree-node-icon',
label: 'p-tree-node-label',
subgroup: 'p-tree-node-children'
nodeLabel: 'p-tree-node-label',
nodeChildren: 'p-tree-node-children'
};
export default BaseStyle.extend({