|
1 | 1 | <template>
|
2 | 2 | <div class="text-right py-3 px-0 text-color-text-primary">
|
3 |
| - <template v-if="internalLayout"> |
4 |
| - <template v-if="!(hideOnSinglePage && (!internalPageCount || internalPageCount === 1))"> |
5 |
| - <template v-for="(item, index) in internalLayout.split(',')"> |
6 |
| - <!-- 总数显示 --> |
| 3 | + <template v-for="(item, index) in internalLayout.split(',')"> |
| 4 | + <!-- 总数显示 --> |
| 5 | + <div |
| 6 | + v-if="item.trim() === 'total' && typeof internalTotal === 'number'" |
| 7 | + :key="'total' + index" |
| 8 | + class="inline-block align-middle text-xs h-7 leading-7 float-left" |
| 9 | + > |
| 10 | + <div v-if="showTotalLoading" class="h-7 leading-7 text-xs text-color-text-primary"> |
7 | 11 | <div
|
8 |
| - v-if="item.trim() === 'total' && typeof internalTotal === 'number'" |
9 |
| - :key="'total' + index" |
10 |
| - class="inline-block align-middle text-xs h-7 leading-7 float-left" |
11 |
| - > |
12 |
| - <div v-if="showTotalLoading" class="h-7 leading-7 text-xs text-color-text-primary"> |
| 12 | + data-tag="tiny-pager-total-loading" |
| 13 | + class="inline-block align-baseline h-3.5 w-3.5 mr-1.5 top-0.5 [&_[data-tag=tiny-loading-icon]]:h-3.5 [&_[data-tag=tiny-loading-icon]]:w-3.5" |
| 14 | + ></div> |
| 15 | + <span class="text-color-text-secondary">{{ t('ui.page.loadingTotals') }}</span> |
| 16 | + </div> |
| 17 | + <div v-else class="h-7 leading-7 text-xs text-color-text-primary"> |
| 18 | + <span>{{ t('ui.page.total') }}</span> |
| 19 | + <span class="my-0 mx-1"> |
| 20 | + {{ customTotal ? totalText : internalTotal }} |
| 21 | + </span> |
| 22 | + <span>{{ t('ui.page.item') }}</span> |
| 23 | + </div> |
| 24 | + </div> |
| 25 | + |
| 26 | + <!-- 每页条数选择器 --> |
| 27 | + <div |
| 28 | + v-else-if="item.trim() === 'sizes'" |
| 29 | + :key="'sizes' + index" |
| 30 | + data-tag="tiny-pager-popover" |
| 31 | + class="hidden sm:inline-block align-middle text-xs h-7 text-xs text-color-text-primary relative -top-px" |
| 32 | + > |
| 33 | + <popover |
| 34 | + ref="sizesList" |
| 35 | + placement="bottom-start" |
| 36 | + :append-to-body="popperAppendToBody" |
| 37 | + trigger="click" |
| 38 | + :popper-class=" |
| 39 | + 'w-24 sm:p-0 sm:!mt-1 sm:!mb-1 data-tag-pager-selector' + (popperClass ? ' ' + popperClass : '') |
| 40 | + " |
| 41 | + :visible-arrow="false" |
| 42 | + :disabled="disabled" |
| 43 | + @show="showSizes = true" |
| 44 | + @hide="showSizes = false" |
| 45 | + > |
| 46 | + <template #reference> |
| 47 | + <div class="m-0 ml-2" @click.stop> |
13 | 48 | <div
|
14 |
| - data-tag="tiny-pager-total-loading" |
15 |
| - class="inline-block align-baseline h-3.5 w-3.5 mr-1.5 top-0.5 [&_[data-tag=tiny-loading-icon]]:h-3.5 [&_[data-tag=tiny-loading-icon]]:w-3.5" |
16 |
| - ></div> |
17 |
| - <span class="text-color-text-secondary">{{ t('ui.page.loadingTotals') }}</span> |
18 |
| - </div> |
19 |
| - <div v-else class="h-7 leading-7 text-xs text-color-text-primary"> |
20 |
| - <span>{{ t('ui.page.total') }}</span> |
21 |
| - <span class="my-0 mx-1"> |
22 |
| - {{ customTotal ? totalText : internalTotal }} |
23 |
| - </span> |
24 |
| - <span>{{ t('ui.page.item') }}</span> |
25 |
| - </div> |
26 |
| - </div> |
27 |
| - |
28 |
| - <!-- 每页条数选择器 --> |
29 |
| - <div |
30 |
| - v-else-if="item.trim() === 'sizes'" |
31 |
| - :key="'sizes' + index" |
32 |
| - data-tag="tiny-pager-popover" |
33 |
| - class="hidden sm:inline-block align-middle text-xs h-7 text-xs text-color-text-primary relative -top-px" |
34 |
| - > |
35 |
| - <popover |
36 |
| - ref="sizesList" |
37 |
| - placement="bottom-start" |
38 |
| - :append-to-body="popperAppendToBody" |
39 |
| - trigger="click" |
40 |
| - :popper-class=" |
41 |
| - 'w-24 sm:p-0 sm:!mt-1 sm:!mb-1 data-tag-pager-selector' + (popperClass ? ' ' + popperClass : '') |
42 |
| - " |
43 |
| - :visible-arrow="false" |
44 |
| - :disabled="disabled" |
45 |
| - @show="showSizes = true" |
46 |
| - @hide="showSizes = false" |
47 |
| - > |
48 |
| - <template #reference> |
49 |
| - <div class="m-0 ml-2" @click.stop> |
50 |
| - <div |
51 |
| - ref="pageSize" |
52 |
| - :class="[ |
53 |
| - 'min-w-[theme(spacing.18)] max-w-[theme(spacing.40)] relative text-left h-7 leading-7 border border-solid border-color-border rounded text-xs py-0 pr-1 pl-3 block whitespace-nowrap transition-[border] duration-300 outline-0 box-border select-none', |
54 |
| - showSizes |
55 |
| - ? 'border-color-border-focus bg-color-fill-6 text-color-border-focus [&_svg]:rotate-180 [&_svg]:fill-color-brand-hover' |
56 |
| - : '', |
57 |
| - disabled |
58 |
| - ? 'bg-color-border-disabled text-color-border cursor-not-allowed [&_svg]:fill-color-icon-disabled [&_svg]:cursor-not-allowed' |
59 |
| - : 'bg-color-bg-1 text-color-text-primary hover:bg-color-border-disabled hover:border-color-border active:border-color-border-focus active:bg-color-fill-6 active:text-color-brand' |
60 |
| - ]" |
61 |
| - > |
62 |
| - <span class="text-xs mr-1 relative -top-px">{{ internalPageSize }}</span> |
63 |
| - <span class="relative -top-px">{{ t('ui.page.page') }}</span> |
64 |
| - <div |
65 |
| - class="w-7 h-7 leading-7 relative float-right -top-px outline-0 box-border text-center overflow-hidden cursor-pointer" |
66 |
| - > |
67 |
| - <tiny-icon-chevron-down |
68 |
| - class="fill-color-text-primary text-sm absolute top-0 left-0 right-0 bottom-0 m-auto hover:fill-color-icon-hover transition-transform duration-300" |
69 |
| - /> |
70 |
| - </div> |
71 |
| - </div> |
| 49 | + ref="pageSize" |
| 50 | + :class="[ |
| 51 | + 'min-w-[theme(spacing.18)] max-w-[theme(spacing.40)] relative text-left h-7 leading-7 border border-solid border-color-border rounded text-xs py-0 pr-1 pl-3 block whitespace-nowrap transition-[border] duration-300 outline-0 box-border select-none', |
| 52 | + showSizes |
| 53 | + ? 'border-color-border-focus bg-color-fill-6 text-color-border-focus [&_svg]:rotate-180 [&_svg]:fill-color-brand-hover' |
| 54 | + : '', |
| 55 | + disabled |
| 56 | + ? 'bg-color-border-disabled text-color-border cursor-not-allowed [&_svg]:fill-color-icon-disabled [&_svg]:cursor-not-allowed' |
| 57 | + : 'bg-color-bg-1 text-color-text-primary hover:bg-color-border-disabled hover:border-color-border active:border-color-border-focus active:bg-color-fill-6 active:text-color-brand' |
| 58 | + ]" |
| 59 | + > |
| 60 | + <span class="text-xs mr-1 relative -top-px">{{ internalPageSize }}</span> |
| 61 | + <span class="relative -top-px">{{ t('ui.page.page') }}</span> |
| 62 | + <div |
| 63 | + class="w-7 h-7 leading-7 relative float-right -top-px outline-0 box-border text-center overflow-hidden cursor-pointer" |
| 64 | + > |
| 65 | + <tiny-icon-chevron-down |
| 66 | + class="fill-color-text-primary text-sm absolute top-0 left-0 right-0 bottom-0 m-auto hover:fill-color-icon-hover transition-transform duration-300" |
| 67 | + /> |
72 | 68 | </div>
|
73 |
| - </template> |
74 |
| - <div class="max-h-[theme(spacing.72)] overflow-y-auto overflow-x-hidden"> |
75 |
| - <ul> |
76 |
| - <li |
77 |
| - v-for="sizeItem in pageSizes" |
78 |
| - :key="String(sizeItem)" |
79 |
| - :class="[ |
80 |
| - 'min-h-[theme(spacing.8)] py-0 px-2 leading-8 max-w-full cursor-pointer overflow-hidden text-ellipsis text-center whitespace-nowrap m-1 rounded', |
81 |
| - sizeItem === internalPageSize |
82 |
| - ? 'text-color-brand bg-color-fill-6' |
83 |
| - : 'hover:bg-color-bg-2 text-color-text-primary' |
84 |
| - ]" |
85 |
| - :data-value="sizeItem" |
86 |
| - :title="String(sizeItem)" |
87 |
| - @click="handleSizeChange(Number(sizeItem))" |
88 |
| - > |
89 |
| - {{ sizeItem }} |
90 |
| - </li> |
91 |
| - </ul> |
92 | 69 | </div>
|
93 |
| - </popover> |
| 70 | + </div> |
| 71 | + </template> |
| 72 | + <div class="max-h-[theme(spacing.72)] overflow-y-auto overflow-x-hidden"> |
| 73 | + <ul> |
| 74 | + <li |
| 75 | + v-for="sizeItem in pageSizes" |
| 76 | + :key="String(sizeItem)" |
| 77 | + :class="[ |
| 78 | + 'min-h-[theme(spacing.8)] py-0 px-2 leading-8 max-w-full cursor-pointer overflow-hidden text-ellipsis text-center whitespace-nowrap m-1 rounded', |
| 79 | + sizeItem === internalPageSize |
| 80 | + ? 'text-color-brand bg-color-fill-6' |
| 81 | + : 'hover:bg-color-bg-2 text-color-text-primary' |
| 82 | + ]" |
| 83 | + :data-value="sizeItem" |
| 84 | + :title="String(sizeItem)" |
| 85 | + @click="handleSizeChange(Number(sizeItem))" |
| 86 | + > |
| 87 | + {{ sizeItem }} |
| 88 | + </li> |
| 89 | + </ul> |
94 | 90 | </div>
|
95 |
| - |
96 |
| - <!-- 上一页按钮 --> |
97 |
| - <button |
98 |
| - v-else-if="item.trim() === 'prev'" |
99 |
| - :key="'prev' + index" |
100 |
| - type="button" |
101 |
| - class="group min-w-[theme(spacing.7)] h-7 text-xs py-0 px-1 text-color-text-primary bg-color-bg-1 rounded-sm outline-0 ml-0 sm:ml-2 align-bottom cursor-pointer hover:border-color-icon-primary disabled:cursor-default" |
102 |
| - :disabled="disabled || internalCurrentPage <= 1" |
103 |
| - @click="prev" |
104 |
| - > |
105 |
| - <span |
106 |
| - v-if="prevText" |
107 |
| - class="group-disabled:text-color-text-disabled group-disabled:cursor-not-allowed group-hover:text-color-icon-hover" |
108 |
| - > |
109 |
| - {{ prevText }} |
110 |
| - </span> |
111 |
| - <tiny-icon-chevron-left |
112 |
| - v-else |
113 |
| - class="align-sub group-disabled:fill-color-icon-disabled group-disabled:cursor-not-allowed group-hover:fill-color-icon-active" |
114 |
| - /> |
115 |
| - </button> |
116 |
| - |
117 |
| - <!-- 分页器 --> |
118 |
| - <pager |
119 |
| - v-else-if="item.trim() === 'pager'" |
120 |
| - :key="'pager' + index" |
121 |
| - :is-before-page-change="isBeforePageChange" |
122 |
| - @before-page-change="beforePagerChangeHandler" |
123 |
| - :current-page="internalCurrentPage" |
124 |
| - :page-count="internalPageCount || 0" |
125 |
| - :pager-count="pagerCount" |
126 |
| - @change="handleCurrentChange" |
| 91 | + </popover> |
| 92 | + </div> |
| 93 | + |
| 94 | + <!-- 上一页按钮 --> |
| 95 | + <button |
| 96 | + v-else-if="item.trim() === 'prev'" |
| 97 | + :key="'prev' + index" |
| 98 | + type="button" |
| 99 | + class="group min-w-[theme(spacing.7)] h-7 text-xs py-0 px-1 text-color-text-primary bg-color-bg-1 rounded-sm outline-0 ml-0 sm:ml-2 align-bottom cursor-pointer hover:border-color-icon-primary disabled:cursor-default" |
| 100 | + :disabled="disabled || internalCurrentPage <= 1" |
| 101 | + @click="prev" |
| 102 | + > |
| 103 | + <span |
| 104 | + v-if="prevText" |
| 105 | + class="group-disabled:text-color-text-disabled group-disabled:cursor-not-allowed group-hover:text-color-icon-hover" |
| 106 | + > |
| 107 | + {{ prevText }} |
| 108 | + </span> |
| 109 | + <tiny-icon-chevron-left |
| 110 | + v-else |
| 111 | + class="align-sub group-disabled:fill-color-icon-disabled group-disabled:cursor-not-allowed group-hover:fill-color-icon-active" |
| 112 | + /> |
| 113 | + </button> |
| 114 | + |
| 115 | + <!-- 分页器 --> |
| 116 | + <pager |
| 117 | + v-else-if="item.trim() === 'pager'" |
| 118 | + :key="'pager' + index" |
| 119 | + :is-before-page-change="isBeforePageChange" |
| 120 | + @before-page-change="beforePagerChangeHandler" |
| 121 | + :current-page="internalCurrentPage" |
| 122 | + :page-count="internalPageCount || 0" |
| 123 | + :pager-count="pagerCount" |
| 124 | + @change="handleCurrentChange" |
| 125 | + :disabled="disabled" |
| 126 | + /> |
| 127 | + |
| 128 | + <!-- 下一页按钮 --> |
| 129 | + <button |
| 130 | + v-else-if="item.trim() === 'next'" |
| 131 | + :key="'next' + index" |
| 132 | + type="button" |
| 133 | + class="group min-w-[theme(spacing.7)] h-7 text-xs py-0 px-1 text-color-text-primary bg-color-bg-1 rounded-sm outline-0 ml-0 sm:ml-2 align-bottom cursor-pointer hover:border-color-icon-primary disabled:cursor-default" |
| 134 | + :disabled="disabled || internalCurrentPage === internalPageCount || internalPageCount === 0" |
| 135 | + @click="next" |
| 136 | + > |
| 137 | + <span |
| 138 | + v-if="nextText" |
| 139 | + class="group-disabled:text-color-text-disabled group-disabled:cursor-not-allowed group-hover:text-color-icon-hover" |
| 140 | + > |
| 141 | + {{ nextText }} |
| 142 | + </span> |
| 143 | + <tiny-icon-chevron-right |
| 144 | + v-else |
| 145 | + class="align-sub group-disabled:fill-color-icon-disabled group-disabled:cursor-not-allowed group-hover:fill-color-icon-active" |
| 146 | + /> |
| 147 | + </button> |
| 148 | + |
| 149 | + <!-- 跳转器 --> |
| 150 | + <div |
| 151 | + v-else-if="item.trim() === 'jumper'" |
| 152 | + :key="'jumper' + index" |
| 153 | + class="h-7 leading-7 inline-block align-middle text-xs" |
| 154 | + > |
| 155 | + <div class="text-[0] h-7"> |
| 156 | + <span class="text-xs pl-4 pr-2 text-color-text-primary">{{ t('ui.page.jump') }}</span> |
| 157 | + <input |
| 158 | + ref="jumperInput" |
| 159 | + type="tel" |
127 | 160 | :disabled="disabled"
|
| 161 | + class="w-8 h-7 text-center align-top rounded-sm inline-block border border-solid border-color-border hover:text-color-icon-primary hover:border-color-icon-primary text-color-text-primary text-xs transition-[border] duration-300 outline-0 box-border mr-0 focus:border-color-border-focus" |
| 162 | + :value="jumperValue" |
| 163 | + @focus="handleJumperFocus" |
| 164 | + @input="handleJumperInput" |
| 165 | + @change="handleJumperChange" |
128 | 166 | />
|
| 167 | + </div> |
| 168 | + </div> |
129 | 169 |
|
130 |
| - <!-- 下一页按钮 --> |
131 |
| - <button |
132 |
| - v-else-if="item.trim() === 'next'" |
133 |
| - :key="'next' + index" |
134 |
| - type="button" |
135 |
| - class="group min-w-[theme(spacing.7)] h-7 text-xs py-0 px-1 text-color-text-primary bg-color-bg-1 rounded-sm outline-0 ml-0 sm:ml-2 align-bottom cursor-pointer hover:border-color-icon-primary disabled:cursor-default" |
136 |
| - :disabled="disabled || internalCurrentPage === internalPageCount || internalPageCount === 0" |
137 |
| - @click="next" |
138 |
| - > |
139 |
| - <span |
140 |
| - v-if="nextText" |
141 |
| - class="group-disabled:text-color-text-disabled group-disabled:cursor-not-allowed group-hover:text-color-icon-hover" |
142 |
| - > |
143 |
| - {{ nextText }} |
144 |
| - </span> |
145 |
| - <tiny-icon-chevron-right |
146 |
| - v-else |
147 |
| - class="align-sub group-disabled:fill-color-icon-disabled group-disabled:cursor-not-allowed group-hover:fill-color-icon-active" |
148 |
| - /> |
149 |
| - </button> |
150 |
| - |
151 |
| - <!-- 跳转器 --> |
152 |
| - <div |
153 |
| - v-else-if="item.trim() === 'jumper'" |
154 |
| - :key="'jumper' + index" |
155 |
| - class="h-7 leading-7 inline-block align-middle text-xs" |
156 |
| - > |
157 |
| - <div class="text-[0] h-7"> |
158 |
| - <span class="text-xs pl-4 pr-2 text-color-text-primary">{{ t('ui.page.jump') }}</span> |
159 |
| - <input |
160 |
| - ref="jumperInput" |
161 |
| - type="tel" |
162 |
| - :disabled="disabled" |
163 |
| - class="w-8 h-7 text-center align-top rounded-sm inline-block border border-solid border-color-border hover:text-color-icon-primary hover:border-color-icon-primary text-color-text-primary text-xs transition-[border] duration-300 outline-0 box-border mr-0 focus:border-color-border-focus" |
164 |
| - :value="jumperValue" |
165 |
| - @focus="handleJumperFocus" |
166 |
| - @input="handleJumperInput" |
167 |
| - @change="handleJumperChange" |
168 |
| - /> |
169 |
| - </div> |
170 |
| - </div> |
171 |
| - |
172 |
| - <!-- 默认插槽 --> |
173 |
| - <slot v-else-if="item.trim() === 'slot'" :key="'slot' + index"> |
174 |
| - <template v-if="$parent?.$slots.default"> |
175 |
| - <template v-if="typeof $parent.$slots.default === 'function'"> |
176 |
| - {{ $parent.$slots.default() }} |
177 |
| - </template> |
178 |
| - <template v-else> |
179 |
| - {{ $parent.$slots.default }} |
180 |
| - </template> |
181 |
| - </template> |
182 |
| - </slot> |
183 |
| - </template> |
184 |
| - </template> |
| 170 | + <!-- 默认插槽 --> |
| 171 | + <slot v-else-if="item.trim() === 'slot'" :key="'slot' + index"></slot> |
185 | 172 | </template>
|
186 | 173 | </div>
|
187 | 174 | </template>
|
@@ -270,7 +257,7 @@ export default defineComponent({
|
270 | 257 | changeCompat: Boolean
|
271 | 258 | },
|
272 | 259 | setup(props, { emit }) {
|
273 |
| - const { ref, reactive, computed, watch, onMounted, nextTick } = hooks |
| 260 | + const { ref, reactive, computed, watch, onMounted, nextTick, toRefs } = hooks |
274 | 261 | const sizesList = ref<{ hide: () => void } | null>(null)
|
275 | 262 |
|
276 | 263 | // 响应式数据
|
@@ -767,7 +754,7 @@ export default defineComponent({
|
767 | 754 |
|
768 | 755 | return {
|
769 | 756 | // 状态
|
770 |
| - ...state, |
| 757 | + ...toRefs(state), |
771 | 758 | // 方法
|
772 | 759 | t,
|
773 | 760 | handleJumperFocus,
|
|
0 commit comments