wkjp-list-page 1.0.28 → 1.0.29

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "wkjp-list-page",
3
- "version": "1.0.28",
3
+ "version": "1.0.29",
4
4
  "description": "Vue2 + ElementUI CommonListPage component",
5
5
  "main": "src/index.js",
6
6
  "module": "src/index.js",
@@ -6,6 +6,19 @@
6
6
  :key="searchItemKey(item, index)"
7
7
  >
8
8
  <slot v-if="item.type === 'slot'" :name="item.slot" :item="item" :filters="filters"></slot>
9
+ <floating-search-input
10
+ v-else-if="isSearchInputWithAppend(item)"
11
+ :label="floatingLabelFor(item)"
12
+ :value="resolveInputString(item)"
13
+ :style="{ width: `${item.width || 150}px` }"
14
+ :maxlength="item.maxlength != null ? item.maxlength : ''"
15
+ :height="item.height || '32px'"
16
+ :clearable="item.clearable !== false"
17
+ :search-icon="item.searchIcon || 'el-icon-search'"
18
+ :search-button-title="item.searchButtonTitle || '查询'"
19
+ @input="(v) => handleSearchInput(item, v)"
20
+ @search="emitQuery"
21
+ />
9
22
  <floating-input
10
23
  v-else-if="item.type === 'input'"
11
24
  :label="floatingLabelFor(item)"
@@ -134,6 +147,7 @@
134
147
  :column="col"
135
148
  :resolve-cell-text="resolveCellText"
136
149
  :column-bind="tableColumnBind"
150
+ :parent-scoped-slots="$scopedSlots"
137
151
  />
138
152
  <el-table-column
139
153
  v-else-if="col.type !== 'slot' && isBuiltinCellColumn(col)"
@@ -309,6 +323,7 @@
309
323
 
310
324
  <script>
311
325
  import FloatingInput from "./FloatingInput.vue";
326
+ import FloatingSearchInput from "./FloatingSearchInput.vue";
312
327
  import FloatingSelect from "./FloatingSelect.vue";
313
328
  import FloatingDatePicker from "./FloatingDatePicker.vue";
314
329
  import FloatingCascader from "./FloatingCascader.vue";
@@ -319,6 +334,7 @@ export default {
319
334
  name: "CommonListPage",
320
335
  components: {
321
336
  FloatingInput,
337
+ FloatingSearchInput,
322
338
  FloatingSelect,
323
339
  FloatingDatePicker,
324
340
  FloatingCascader,
@@ -775,6 +791,12 @@ export default {
775
791
  const id = item && (item.slot || item.prop || item.type || "");
776
792
  return "search-" + id + "-" + index;
777
793
  },
794
+ /** `type: 'inputSearch'` 或 `type: 'input'` 且 `appendSearch: true` */
795
+ isSearchInputWithAppend(item) {
796
+ if (!item) return false;
797
+ if (item.type === "inputSearch") return true;
798
+ return item.type === "input" && item.appendSearch === true;
799
+ },
778
800
  emitQuery() {
779
801
  this.$emit("query");
780
802
  },
@@ -1803,6 +1825,25 @@ export default {
1803
1825
  color: #409eff;
1804
1826
  }
1805
1827
 
1828
+ .common-list-page /deep/ .el-button--primary.is-disabled,
1829
+ .common-list-page /deep/ .el-button--primary.is-disabled:hover,
1830
+ .common-list-page /deep/ .el-button--primary.is-disabled:focus,
1831
+ .common-list-page /deep/ .el-button--primary:disabled {
1832
+ background-color: #a0cfff;
1833
+ border-color: #a0cfff;
1834
+ color: #fff;
1835
+ cursor: not-allowed;
1836
+ }
1837
+
1838
+ .common-list-page /deep/ .el-button--primary.is-plain.is-disabled,
1839
+ .common-list-page /deep/ .el-button--primary.is-plain.is-disabled:hover,
1840
+ .common-list-page /deep/ .el-button--primary.is-plain:disabled {
1841
+ background-color: #ecf5ff;
1842
+ border-color: #ebeef5;
1843
+ color: #a0cfff;
1844
+ cursor: not-allowed;
1845
+ }
1846
+
1806
1847
  /* ---------- 列表表格(极细外框兜底:空数据区不塌陷、无粗网格线) ---------- */
1807
1848
  .common-list-page /deep/ .el-table {
1808
1849
  overflow: hidden;
@@ -1911,6 +1952,28 @@ export default {
1911
1952
  color: #66b1ff;
1912
1953
  }
1913
1954
 
1955
+ .common-list-page /deep/ .el-table .cell .el-button--text.is-disabled,
1956
+ .common-list-page /deep/ .el-table .cell .el-button--text.is-disabled:hover,
1957
+ .common-list-page /deep/ .el-table .cell .el-button--text.is-disabled:focus,
1958
+ .common-list-page /deep/ .el-table .cell .el-button--text:disabled {
1959
+ color: #c0c4cc !important;
1960
+ cursor: not-allowed;
1961
+ }
1962
+
1963
+ .common-list-page /deep/ .el-table .cell .el-button--text.el-button--danger.is-disabled,
1964
+ .common-list-page /deep/ .el-table .cell .el-button--text.el-button--danger.is-disabled:hover,
1965
+ .common-list-page /deep/ .el-table .cell .el-button--text.el-button--danger:disabled {
1966
+ color: #fab6b6 !important;
1967
+ cursor: not-allowed;
1968
+ }
1969
+
1970
+ .common-list-page /deep/ .el-table .cell .el-button--text.el-button--warning.is-disabled,
1971
+ .common-list-page /deep/ .el-table .cell .el-button--text.el-button--warning.is-disabled:hover,
1972
+ .common-list-page /deep/ .el-table .cell .el-button--text.el-button--warning:disabled {
1973
+ color: #f3d19e !important;
1974
+ cursor: not-allowed;
1975
+ }
1976
+
1914
1977
  .common-list-page /deep/ .el-pagination {
1915
1978
  margin-top: 14px;
1916
1979
  padding-right: 4px;
@@ -0,0 +1,303 @@
1
+ <template>
2
+ <div
3
+ class="floating-label-wrap floating-search-input"
4
+ :class="{
5
+ 'is-focused': isFocused,
6
+ 'has-value': hasValue,
7
+ 'has-clear-btn': clearable && hasValue,
8
+ }"
9
+ >
10
+ <div class="floating-search-input__group">
11
+ <div class="floating-search-input__field">
12
+ <input
13
+ ref="input"
14
+ :type="type"
15
+ placeholder=" "
16
+ :value="value"
17
+ class="text-box"
18
+ :style="inputStyle"
19
+ :maxlength="maxlength"
20
+ @input="handleInput"
21
+ @focus="handleFocus"
22
+ @blur="handleBlur"
23
+ @keyup.enter="handleEnter"
24
+ />
25
+ <button
26
+ v-if="clearable && hasValue"
27
+ type="button"
28
+ class="floating-input__clear"
29
+ tabindex="-1"
30
+ aria-label="清除"
31
+ @mousedown.prevent
32
+ @click="clearInput"
33
+ >
34
+ <i class="el-icon-circle-close"></i>
35
+ </button>
36
+ </div>
37
+ <button
38
+ type="button"
39
+ class="floating-search-input__append"
40
+ tabindex="-1"
41
+ :title="searchButtonTitle"
42
+ @click="handleSearch"
43
+ >
44
+ <i :class="searchIcon"></i>
45
+ </button>
46
+ </div>
47
+ <label class="floating-label">{{ label }}</label>
48
+ </div>
49
+ </template>
50
+
51
+ <script>
52
+ export default {
53
+ name: "FloatingSearchInput",
54
+ props: {
55
+ type: {
56
+ type: String,
57
+ default: "text",
58
+ },
59
+ label: {
60
+ type: String,
61
+ required: true,
62
+ },
63
+ value: {
64
+ type: String,
65
+ default: "",
66
+ },
67
+ maxlength: {
68
+ type: [String, Number],
69
+ default: "",
70
+ },
71
+ height: {
72
+ type: [String, Number],
73
+ default: "32px",
74
+ },
75
+ clearable: {
76
+ type: Boolean,
77
+ default: true,
78
+ },
79
+ searchIcon: {
80
+ type: String,
81
+ default: "el-icon-search",
82
+ },
83
+ searchButtonTitle: {
84
+ type: String,
85
+ default: "查询",
86
+ },
87
+ },
88
+ data() {
89
+ return {
90
+ isFocused: false,
91
+ hasValue: false,
92
+ };
93
+ },
94
+ computed: {
95
+ inputStyle() {
96
+ const height =
97
+ typeof this.height === "number" ? `${this.height}px` : this.height;
98
+ return {
99
+ height: height,
100
+ lineHeight: height,
101
+ };
102
+ },
103
+ },
104
+ methods: {
105
+ handleInput(event) {
106
+ const value = event.target.value;
107
+ this.hasValue = !!value;
108
+ this.$emit("input", value);
109
+ },
110
+ handleFocus() {
111
+ this.isFocused = true;
112
+ },
113
+ handleBlur() {
114
+ this.isFocused = false;
115
+ },
116
+ clearInput() {
117
+ this.hasValue = false;
118
+ this.$emit("input", "");
119
+ this.$nextTick(() => {
120
+ if (this.$refs.input) this.$refs.input.focus();
121
+ });
122
+ },
123
+ handleEnter() {
124
+ this.$emit("enter");
125
+ },
126
+ handleSearch() {
127
+ this.$emit("search");
128
+ },
129
+ checkValue() {
130
+ this.hasValue = !!this.value;
131
+ },
132
+ },
133
+ mounted() {
134
+ this.checkValue();
135
+ },
136
+ watch: {
137
+ value() {
138
+ this.checkValue();
139
+ },
140
+ },
141
+ };
142
+ </script>
143
+
144
+ <style scoped>
145
+ .floating-search-input {
146
+ width: 100%;
147
+ }
148
+
149
+ .floating-search-input__group {
150
+ display: flex;
151
+ align-items: stretch;
152
+ width: 100%;
153
+ border-radius: 4px;
154
+ border: 1px solid #dcdfe6;
155
+ background: #fff;
156
+ box-sizing: border-box;
157
+ overflow: hidden;
158
+ transition: border-color 0.2s ease, box-shadow 0.2s ease;
159
+ }
160
+
161
+ .floating-search-input__field {
162
+ position: relative;
163
+ flex: 1;
164
+ min-width: 0;
165
+ }
166
+
167
+ .floating-search-input .text-box {
168
+ width: 100%;
169
+ padding: 0 12px;
170
+ border: none;
171
+ border-radius: 0;
172
+ background: transparent;
173
+ box-sizing: border-box;
174
+ font-size: 13px;
175
+ color: #303133;
176
+ font-family: inherit;
177
+ }
178
+
179
+ .floating-search-input.has-clear-btn .text-box {
180
+ padding-right: 30px;
181
+ }
182
+
183
+ /* 与普通 FloatingInput 清除按钮一致 */
184
+ .floating-search-input .floating-input__clear {
185
+ position: absolute;
186
+ right: 8px;
187
+ top: 50%;
188
+ transform: translateY(-50%);
189
+ z-index: 3;
190
+ display: flex;
191
+ align-items: center;
192
+ justify-content: center;
193
+ width: 22px;
194
+ height: 22px;
195
+ padding: 0;
196
+ margin: 0;
197
+ border: none;
198
+ background: transparent;
199
+ color: #c0c4cc;
200
+ cursor: pointer;
201
+ border-radius: 50%;
202
+ line-height: 1;
203
+ }
204
+
205
+ .floating-search-input .floating-input__clear:hover {
206
+ color: #909399;
207
+ }
208
+
209
+ .floating-search-input .floating-input__clear i {
210
+ font-size: 14px;
211
+ }
212
+
213
+ .floating-search-input__append {
214
+ flex-shrink: 0;
215
+ display: flex;
216
+ align-items: center;
217
+ justify-content: center;
218
+ width: 36px;
219
+ margin: 0;
220
+ padding: 0;
221
+ border: none;
222
+ border-left: 1px solid #dcdfe6;
223
+ background: #f5f7fa;
224
+ color: #909399;
225
+ cursor: pointer;
226
+ line-height: 1;
227
+ }
228
+
229
+ .floating-search-input__append:hover {
230
+ color: #409eff;
231
+ background: #ecf5ff;
232
+ }
233
+
234
+ .floating-search-input__append i {
235
+ font-size: 14px;
236
+ }
237
+
238
+ .floating-search-input > .floating-label {
239
+ position: absolute;
240
+ left: 12px;
241
+ top: 50%;
242
+ transform: translateY(-50%);
243
+ font-size: 13px;
244
+ font-weight: 400;
245
+ color: #909399;
246
+ pointer-events: none;
247
+ transition: color 0.2s ease, transform 0.2s ease, top 0.2s ease,
248
+ left 0.2s ease, font-size 0.2s ease, background 0.2s ease,
249
+ padding 0.2s ease, box-shadow 0.2s ease;
250
+ background: transparent;
251
+ line-height: 1.2;
252
+ z-index: 4;
253
+ white-space: nowrap;
254
+ max-width: calc(100% - 52px);
255
+ overflow: hidden;
256
+ text-overflow: ellipsis;
257
+ }
258
+
259
+ .floating-search-input.is-focused > .floating-label,
260
+ .floating-search-input.has-value > .floating-label {
261
+ top: 0;
262
+ left: 10px;
263
+ transform: translateY(-50%);
264
+ font-size: 12px;
265
+ font-weight: 500;
266
+ color: #409eff;
267
+ padding: 0 6px;
268
+ background: #fff;
269
+ border-radius: 4px;
270
+ box-shadow: 0 0 0 1px #fff;
271
+ }
272
+
273
+ .floating-search-input__group:hover {
274
+ border-color: #c0c4cc;
275
+ }
276
+
277
+ .floating-search-input.is-focused .floating-search-input__group {
278
+ border-color: #409eff;
279
+ box-shadow: 0 0 0 2px rgba(64, 158, 255, 0.18);
280
+ }
281
+
282
+ .floating-search-input .text-box:focus {
283
+ outline: none;
284
+ }
285
+ </style>
286
+
287
+ <style>
288
+ .el-form-item.is-error .floating-search-input.is-focused .floating-label,
289
+ .el-form-item.is-error .floating-search-input.has-value .floating-label {
290
+ color: #f56c6c !important;
291
+ box-shadow: 0 0 0 1px #fff;
292
+ }
293
+
294
+ .el-form-item.is-error .floating-search-input .floating-search-input__group {
295
+ border-color: #f56c6c !important;
296
+ box-shadow: none !important;
297
+ }
298
+
299
+ .el-form-item.is-error .floating-search-input.is-focused .floating-search-input__group {
300
+ border-color: #f56c6c !important;
301
+ box-shadow: 0 0 0 2px rgba(245, 108, 108, 0.2) !important;
302
+ }
303
+ </style>
@@ -1,7 +1,7 @@
1
1
  <template>
2
2
  <div class="floating-label-wrap">
3
3
  <el-select
4
- :value="value"
4
+ :value="selectValue"
5
5
  v-bind="$attrs"
6
6
  :multiple="multiple"
7
7
  :clearable="clearable"
@@ -53,6 +53,19 @@ export default {
53
53
  };
54
54
  },
55
55
  computed: {
56
+ selectValue() {
57
+ if (Array.isArray(this.value)) {
58
+ return this.value.length ? this.value : undefined;
59
+ }
60
+ if (
61
+ this.value === "" ||
62
+ this.value === null ||
63
+ this.value === undefined
64
+ ) {
65
+ return undefined;
66
+ }
67
+ return this.value;
68
+ },
56
69
  hasValue() {
57
70
  if (Array.isArray(this.value)) {
58
71
  return this.value.length > 0;