cbvirtua 1.0.26 → 1.0.28

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.
Files changed (105) hide show
  1. package/after/after.d.ts +3 -0
  2. package/after/after.index.d.ts +3 -0
  3. package/after/after.index.js +3 -0
  4. package/after/after.index.js.map +1 -0
  5. package/after/after.js +11 -0
  6. package/after/after.js.map +1 -0
  7. package/after/after.model.d.ts +9 -0
  8. package/after/after.model.js +2 -0
  9. package/after/after.model.js.map +1 -0
  10. package/after/after.spec.d.ts +1 -0
  11. package/after/after.spec.js +226 -0
  12. package/after/after.spec.js.map +1 -0
  13. package/after/afterify.d.ts +3 -0
  14. package/after/afterify.js +26 -0
  15. package/after/afterify.js.map +1 -0
  16. package/before/before.d.ts +3 -0
  17. package/before/before.index.d.ts +3 -0
  18. package/before/before.index.js +3 -0
  19. package/before/before.index.js.map +1 -0
  20. package/before/before.js +11 -0
  21. package/before/before.js.map +1 -0
  22. package/before/before.model.d.ts +4 -0
  23. package/before/before.model.js +2 -0
  24. package/before/before.model.js.map +1 -0
  25. package/before/before.spec.d.ts +1 -0
  26. package/before/before.spec.js +174 -0
  27. package/before/before.spec.js.map +1 -0
  28. package/before/beforify.d.ts +3 -0
  29. package/before/beforify.js +18 -0
  30. package/before/beforify.js.map +1 -0
  31. package/package.json +1 -1
  32. package/Autocomplete.vue.txt +0 -603
  33. package/md.txt +0 -24
  34. package/py/cn.js +0 -28
  35. package/py/decode.js +0 -33
  36. package/py/dict-cn.json +0 -1
  37. package/py/dict-tw.json +0 -1
  38. package/py/engine.js +0 -117
  39. package/py/tw.js +0 -28
  40. package/style/basic.less +0 -69
  41. package/style/index.less +0 -125
  42. package/style/index.tsx +0 -2
  43. package/style/mixin.less +0 -53
  44. package/style/rtl.less +0 -68
  45. package/vant/style/README.md +0 -79
  46. package/vant/style/README.zh-CN.md +0 -79
  47. package/vant/style/animation.less +0 -139
  48. package/vant/style/base.less +0 -10
  49. package/vant/style/clearfix.less +0 -5
  50. package/vant/style/demo/index.vue +0 -110
  51. package/vant/style/ellipsis.less +0 -13
  52. package/vant/style/hairline.less +0 -47
  53. package/vant/style/mixins/clearfix.less +0 -7
  54. package/vant/style/mixins/ellipsis.less +0 -15
  55. package/vant/style/mixins/hairline.less +0 -39
  56. package/vant/style/normalize.less +0 -38
  57. package/vant/style/reset.less +0 -171
  58. package/vant/style/var.less +0 -901
  59. package/vant/tab/README.md +0 -307
  60. package/vant/tab/README.zh-CN.md +0 -342
  61. package/vant/tab/demo/index.vue +0 -193
  62. package/vant/tab/index.js +0 -95
  63. package/vant/tab/index.less +0 -17
  64. package/vant/tab/test/__snapshots__/demo.spec.js.snap +0 -349
  65. package/vant/tab/test/__snapshots__/index.spec.js.snap +0 -352
  66. package/vant/tab/test/__snapshots__/insert.spec.js.snap +0 -63
  67. package/vant/tab/test/demo.spec.js +0 -4
  68. package/vant/tab/test/index.spec.js +0 -435
  69. package/vant/tab/test/insert.spec.js +0 -75
  70. package/vant/tabs/Content.js +0 -79
  71. package/vant/tabs/Title.js +0 -91
  72. package/vant/tabs/index.js +0 -453
  73. package/vant/tabs/index.less +0 -153
  74. package/vant/tabs/utils.ts +0 -53
  75. package/vant/utils/constant.ts +0 -11
  76. package/vant/utils/create/bem.ts +0 -45
  77. package/vant/utils/create/component.ts +0 -86
  78. package/vant/utils/create/i18n.ts +0 -16
  79. package/vant/utils/create/index.ts +0 -14
  80. package/vant/utils/deep-assign.ts +0 -27
  81. package/vant/utils/deep-clone.ts +0 -23
  82. package/vant/utils/dom/event.ts +0 -56
  83. package/vant/utils/dom/node.ts +0 -7
  84. package/vant/utils/dom/raf.ts +0 -40
  85. package/vant/utils/dom/reset-scroll.ts +0 -16
  86. package/vant/utils/dom/scroll.ts +0 -81
  87. package/vant/utils/dom/style.ts +0 -11
  88. package/vant/utils/format/number.ts +0 -52
  89. package/vant/utils/format/string.ts +0 -15
  90. package/vant/utils/format/unit.ts +0 -61
  91. package/vant/utils/functional.ts +0 -73
  92. package/vant/utils/index.ts +0 -79
  93. package/vant/utils/interceptor.ts +0 -27
  94. package/vant/utils/router.ts +0 -54
  95. package/vant/utils/test/bem.spec.js +0 -39
  96. package/vant/utils/test/index.spec.js +0 -152
  97. package/vant/utils/test/interceptor.spec.js +0 -50
  98. package/vant/utils/types.ts +0 -40
  99. package/vant/utils/validate/date.ts +0 -8
  100. package/vant/utils/validate/email.ts +0 -5
  101. package/vant/utils/validate/mobile.ts +0 -6
  102. package/vant/utils/validate/number.ts +0 -12
  103. package/vant/utils/validate/system.ts +0 -13
  104. package/vant/utils/vnodes.ts +0 -33
  105. package//346/226/260/345/273/272 /346/226/207/346/234/254/346/226/207/346/241/243.txt" +0 -85
@@ -1,453 +0,0 @@
1
- // Utils
2
- import { createNamespace, isDef, addUnit } from '../utils';
3
- import { scrollLeftTo, scrollTopTo } from './utils';
4
- import { route } from '../utils/router';
5
- import { isHidden } from '../utils/dom/style';
6
- import { on, off } from '../utils/dom/event';
7
- import { unitToPx } from '../utils/format/unit';
8
- import { BORDER_TOP_BOTTOM } from '../utils/constant';
9
- import { callInterceptor } from '../utils/interceptor';
10
- import {
11
- getScroller,
12
- getVisibleTop,
13
- getElementTop,
14
- getVisibleHeight,
15
- setRootScrollTop,
16
- } from '../utils/dom/scroll';
17
-
18
- // Mixins
19
- import { ParentMixin } from '../mixins/relation';
20
- import { BindEventMixin } from '../mixins/bind-event';
21
-
22
- // Components
23
- import Title from './Title';
24
- import Sticky from '../sticky';
25
- import Content from './Content';
26
-
27
- const [createComponent, bem] = createNamespace('tabs');
28
-
29
- export default createComponent({
30
- mixins: [
31
- ParentMixin('vanTabs'),
32
- BindEventMixin(function (bind) {
33
- if (!this.scroller) {
34
- this.scroller = getScroller(this.$el);
35
- }
36
-
37
- bind(window, 'resize', this.resize, true);
38
-
39
- if (this.scrollspy) {
40
- bind(this.scroller, 'scroll', this.onScroll, true);
41
- }
42
- }),
43
- ],
44
-
45
- inject: {
46
- vanPopup: {
47
- default: null,
48
- },
49
- },
50
-
51
- model: {
52
- prop: 'active',
53
- },
54
-
55
- props: {
56
- color: String,
57
- border: Boolean,
58
- sticky: Boolean,
59
- animated: Boolean,
60
- swipeable: Boolean,
61
- scrollspy: Boolean,
62
- background: String,
63
- lineWidth: [Number, String],
64
- lineHeight: [Number, String],
65
- beforeChange: Function,
66
- titleActiveColor: String,
67
- titleInactiveColor: String,
68
- type: {
69
- type: String,
70
- default: 'line',
71
- },
72
- active: {
73
- type: [Number, String],
74
- default: 0,
75
- },
76
- ellipsis: {
77
- type: Boolean,
78
- default: true,
79
- },
80
- duration: {
81
- type: [Number, String],
82
- default: 0.3,
83
- },
84
- offsetTop: {
85
- type: [Number, String],
86
- default: 0,
87
- },
88
- lazyRender: {
89
- type: Boolean,
90
- default: true,
91
- },
92
- swipeThreshold: {
93
- type: [Number, String],
94
- default: 5,
95
- },
96
- },
97
-
98
- data() {
99
- return {
100
- position: '',
101
- currentIndex: null,
102
- lineStyle: {
103
- backgroundColor: this.color,
104
- },
105
- };
106
- },
107
-
108
- computed: {
109
- // whether the nav is scrollable
110
- scrollable() {
111
- return this.children.length > this.swipeThreshold || !this.ellipsis;
112
- },
113
-
114
- navStyle() {
115
- return {
116
- borderColor: this.color,
117
- background: this.background,
118
- };
119
- },
120
-
121
- currentName() {
122
- const activeTab = this.children[this.currentIndex];
123
-
124
- if (activeTab) {
125
- return activeTab.computedName;
126
- }
127
- },
128
-
129
- offsetTopPx() {
130
- return unitToPx(this.offsetTop);
131
- },
132
-
133
- scrollOffset() {
134
- if (this.sticky) {
135
- return this.offsetTopPx + this.tabHeight;
136
- }
137
- return 0;
138
- },
139
- },
140
-
141
- watch: {
142
- color: 'setLine',
143
-
144
- active(name) {
145
- if (name !== this.currentName) {
146
- this.setCurrentIndexByName(name);
147
- }
148
- },
149
-
150
- children() {
151
- this.setCurrentIndexByName(this.active);
152
- this.setLine();
153
-
154
- this.$nextTick(() => {
155
- this.scrollIntoView(true);
156
- });
157
- },
158
-
159
- currentIndex() {
160
- this.scrollIntoView();
161
- this.setLine();
162
-
163
- // scroll to correct position
164
- if (this.stickyFixed && !this.scrollspy) {
165
- setRootScrollTop(Math.ceil(getElementTop(this.$el) - this.offsetTopPx));
166
- }
167
- },
168
-
169
- scrollspy(val) {
170
- if (val) {
171
- on(this.scroller, 'scroll', this.onScroll, true);
172
- } else {
173
- off(this.scroller, 'scroll', this.onScroll);
174
- }
175
- },
176
- },
177
-
178
- mounted() {
179
- this.init();
180
-
181
- // https://github.com/vant-ui/vant/issues/7959
182
- if (this.vanPopup) {
183
- this.vanPopup.onReopen(() => {
184
- this.setLine();
185
- });
186
- }
187
- },
188
-
189
- activated() {
190
- this.init();
191
- this.setLine();
192
- },
193
-
194
- methods: {
195
- // @exposed-api
196
- resize() {
197
- this.setLine();
198
- },
199
-
200
- init() {
201
- this.$nextTick(() => {
202
- this.inited = true;
203
- this.tabHeight = getVisibleHeight(this.$refs.wrap);
204
- this.scrollIntoView(true);
205
- });
206
- },
207
-
208
- // update nav bar style
209
- setLine() {
210
- const shouldAnimate = this.inited;
211
-
212
- this.$nextTick(() => {
213
- const { titles } = this.$refs;
214
-
215
- if (
216
- !titles ||
217
- !titles[this.currentIndex] ||
218
- this.type !== 'line' ||
219
- isHidden(this.$el)
220
- ) {
221
- return;
222
- }
223
-
224
- const title = titles[this.currentIndex].$el;
225
- const { lineWidth, lineHeight } = this;
226
- const left = title.offsetLeft + title.offsetWidth / 2;
227
-
228
- const lineStyle = {
229
- width: addUnit(lineWidth),
230
- backgroundColor: this.color,
231
- transform: `translateX(${left}px) translateX(-50%)`,
232
- };
233
-
234
- if (shouldAnimate) {
235
- lineStyle.transitionDuration = `${this.duration}s`;
236
- }
237
-
238
- if (isDef(lineHeight)) {
239
- const height = addUnit(lineHeight);
240
- lineStyle.height = height;
241
- lineStyle.borderRadius = height;
242
- }
243
-
244
- this.lineStyle = lineStyle;
245
- });
246
- },
247
-
248
- // correct the index of active tab
249
- setCurrentIndexByName(name) {
250
- const matched = this.children.filter((tab) => tab.computedName === name);
251
- const defaultIndex = (this.children[0] || {}).index || 0;
252
- this.setCurrentIndex(matched.length ? matched[0].index : defaultIndex);
253
- },
254
-
255
- setCurrentIndex(currentIndex) {
256
- const newIndex = this.findAvailableTab(currentIndex);
257
-
258
- if (!isDef(newIndex)) {
259
- return;
260
- }
261
-
262
- const newTab = this.children[newIndex];
263
- const newName = newTab.computedName;
264
- const shouldEmitChange = this.currentIndex !== null;
265
-
266
- this.currentIndex = newIndex;
267
-
268
- if (newName !== this.active) {
269
- this.$emit('input', newName);
270
-
271
- if (shouldEmitChange) {
272
- this.$emit('change', newName, newTab.title);
273
- }
274
- }
275
- },
276
-
277
- findAvailableTab(index) {
278
- const diff = index < this.currentIndex ? -1 : 1;
279
-
280
- while (index >= 0 && index < this.children.length) {
281
- if (!this.children[index].disabled) {
282
- return index;
283
- }
284
-
285
- index += diff;
286
- }
287
- },
288
-
289
- // emit event when clicked
290
- onClick(item, index) {
291
- const { title, disabled, computedName } = this.children[index];
292
- if (disabled) {
293
- this.$emit('disabled', computedName, title);
294
- } else {
295
- callInterceptor({
296
- interceptor: this.beforeChange,
297
- args: [computedName],
298
- done: () => {
299
- this.setCurrentIndex(index);
300
- this.scrollToCurrentContent();
301
- },
302
- });
303
-
304
- this.$emit('click', computedName, title);
305
- route(item.$router, item);
306
- }
307
- },
308
-
309
- // scroll active tab into view
310
- scrollIntoView(immediate) {
311
- const { titles } = this.$refs;
312
-
313
- if (!this.scrollable || !titles || !titles[this.currentIndex]) {
314
- return;
315
- }
316
-
317
- const { nav } = this.$refs;
318
- const title = titles[this.currentIndex].$el;
319
- const to = title.offsetLeft - (nav.offsetWidth - title.offsetWidth) / 2;
320
-
321
- scrollLeftTo(nav, to, immediate ? 0 : +this.duration);
322
- },
323
-
324
- onSticktScroll(params) {
325
- this.stickyFixed = params.isFixed;
326
- this.$emit('scroll', params);
327
- },
328
-
329
- // @exposed-api
330
- scrollTo(name) {
331
- this.$nextTick(() => {
332
- this.setCurrentIndexByName(name);
333
- this.scrollToCurrentContent(true);
334
- });
335
- },
336
-
337
- scrollToCurrentContent(immediate = false) {
338
- if (this.scrollspy) {
339
- const target = this.children[this.currentIndex];
340
- const el = target?.$el;
341
-
342
- if (el) {
343
- const to = getElementTop(el, this.scroller) - this.scrollOffset;
344
-
345
- this.lockScroll = true;
346
- scrollTopTo(this.scroller, to, immediate ? 0 : +this.duration, () => {
347
- this.lockScroll = false;
348
- });
349
- }
350
- }
351
- },
352
-
353
- onScroll() {
354
- if (this.scrollspy && !this.lockScroll) {
355
- const index = this.getCurrentIndexOnScroll();
356
- this.setCurrentIndex(index);
357
- }
358
- },
359
-
360
- getCurrentIndexOnScroll() {
361
- const { children } = this;
362
-
363
- for (let index = 0; index < children.length; index++) {
364
- const top = getVisibleTop(children[index].$el);
365
-
366
- if (top > this.scrollOffset) {
367
- return index === 0 ? 0 : index - 1;
368
- }
369
- }
370
-
371
- return children.length - 1;
372
- },
373
- },
374
-
375
- render() {
376
- const { type, animated, scrollable } = this;
377
-
378
- const Nav = this.children.map((item, index) => (
379
- <Title
380
- ref="titles"
381
- refInFor
382
- type={type}
383
- dot={item.dot}
384
- info={item.badge ?? item.info}
385
- title={item.title}
386
- color={this.color}
387
- style={item.titleStyle}
388
- class={item.titleClass}
389
- isActive={index === this.currentIndex}
390
- disabled={item.disabled}
391
- scrollable={scrollable}
392
- activeColor={this.titleActiveColor}
393
- inactiveColor={this.titleInactiveColor}
394
- scopedSlots={{
395
- default: () => item.slots('title'),
396
- }}
397
- onClick={() => {
398
- this.onClick(item, index);
399
- }}
400
- />
401
- ));
402
-
403
- const Wrap = (
404
- <div
405
- ref="wrap"
406
- class={[
407
- bem('wrap', { scrollable }),
408
- { [BORDER_TOP_BOTTOM]: type === 'line' && this.border },
409
- ]}
410
- >
411
- <div
412
- ref="nav"
413
- role="tablist"
414
- class={bem('nav', [type, { complete: this.scrollable }])}
415
- style={this.navStyle}
416
- >
417
- {this.slots('nav-left')}
418
- {Nav}
419
- {type === 'line' && (
420
- <div class={bem('line')} style={this.lineStyle} />
421
- )}
422
- {this.slots('nav-right')}
423
- </div>
424
- </div>
425
- );
426
-
427
- return (
428
- <div class={bem([type])}>
429
- {this.sticky ? (
430
- <Sticky
431
- container={this.$el}
432
- offsetTop={this.offsetTop}
433
- onScroll={this.onSticktScroll}
434
- >
435
- {Wrap}
436
- </Sticky>
437
- ) : (
438
- Wrap
439
- )}
440
- <Content
441
- count={this.children.length}
442
- animated={animated}
443
- duration={this.duration}
444
- swipeable={this.swipeable}
445
- currentIndex={this.currentIndex}
446
- onChange={this.setCurrentIndex}
447
- >
448
- {this.slots()}
449
- </Content>
450
- </div>
451
- );
452
- },
453
- });
@@ -1,153 +0,0 @@
1
- @import '../style/var';
2
-
3
- .van-tab {
4
- position: relative;
5
- display: flex;
6
- flex: 1;
7
- align-items: center;
8
- justify-content: center;
9
- box-sizing: border-box;
10
- padding: 0 @padding-base;
11
- color: @tab-text-color;
12
- font-size: @tab-font-size;
13
- line-height: @tab-line-height;
14
- cursor: pointer;
15
-
16
- &--active {
17
- color: @tab-active-text-color;
18
- font-weight: @font-weight-bold;
19
- }
20
-
21
- &--disabled {
22
- color: @tab-disabled-text-color;
23
- cursor: not-allowed;
24
- }
25
-
26
- &__text {
27
- &--ellipsis {
28
- display: -webkit-box;
29
- overflow: hidden;
30
- -webkit-line-clamp: 1;
31
- -webkit-box-orient: vertical;
32
- }
33
- }
34
-
35
- &__text-wrapper {
36
- position: relative;
37
- }
38
- }
39
-
40
- .van-tabs {
41
- position: relative;
42
-
43
- &__wrap {
44
- overflow: hidden;
45
-
46
- &--page-top {
47
- position: fixed;
48
- }
49
-
50
- &--content-bottom {
51
- top: auto;
52
- bottom: 0;
53
- }
54
-
55
- &--scrollable {
56
- .van-tab {
57
- flex: 1 0 auto;
58
- padding: 0 @padding-sm;
59
- }
60
-
61
- .van-tabs__nav {
62
- overflow-x: auto;
63
- overflow-y: hidden;
64
- -webkit-overflow-scrolling: touch;
65
-
66
- &::-webkit-scrollbar {
67
- display: none;
68
- }
69
- }
70
- }
71
- }
72
-
73
- &__nav {
74
- position: relative;
75
- display: flex;
76
- background-color: @tabs-nav-background-color;
77
- user-select: none;
78
-
79
- &--line {
80
- box-sizing: content-box;
81
- height: 100%;
82
- padding-bottom: 15px; /* 15px padding to hide scrollbar in mobile safari */
83
- }
84
-
85
- &--line&--complete {
86
- padding-right: @padding-xs;
87
- padding-left: @padding-xs;
88
- }
89
-
90
- &--card {
91
- box-sizing: border-box;
92
- height: @tabs-card-height;
93
- margin: 0 @padding-md;
94
- border: @border-width-base solid @tabs-default-color;
95
- border-radius: @border-radius-sm;
96
-
97
- .van-tab {
98
- color: @tabs-default-color;
99
- border-right: @border-width-base solid @tabs-default-color;
100
-
101
- &:last-child {
102
- border-right: none;
103
- }
104
-
105
- &.van-tab--active {
106
- color: @white;
107
- background-color: @tabs-default-color;
108
- }
109
-
110
- &--disabled {
111
- color: @tab-disabled-text-color;
112
- }
113
- }
114
- }
115
- }
116
-
117
- &__line {
118
- position: absolute;
119
- bottom: 15px;
120
- left: 0;
121
- z-index: 1;
122
- width: @tabs-bottom-bar-width;
123
- height: @tabs-bottom-bar-height;
124
- background-color: @tabs-bottom-bar-color;
125
- border-radius: @tabs-bottom-bar-height;
126
- }
127
-
128
- &__track {
129
- position: relative;
130
- display: flex;
131
- width: 100%;
132
- height: 100%;
133
- will-change: left;
134
- }
135
-
136
- &__content {
137
- &--animated {
138
- overflow: hidden;
139
- }
140
- }
141
-
142
- &--line {
143
- .van-tabs__wrap {
144
- height: @tabs-line-height;
145
- }
146
- }
147
-
148
- &--card {
149
- > .van-tabs__wrap {
150
- height: @tabs-card-height;
151
- }
152
- }
153
- }
@@ -1,53 +0,0 @@
1
- import { raf } from '../utils/dom/raf';
2
- import { getScrollTop, setScrollTop } from '../utils/dom/scroll';
3
-
4
- export function scrollLeftTo(
5
- scroller: HTMLElement,
6
- to: number,
7
- duration: number
8
- ) {
9
- let count = 0;
10
- const from = scroller.scrollLeft;
11
- const frames = duration === 0 ? 1 : Math.round((duration * 1000) / 16);
12
-
13
- function animate() {
14
- scroller.scrollLeft += (to - from) / frames;
15
-
16
- if (++count < frames) {
17
- raf(animate);
18
- }
19
- }
20
-
21
- animate();
22
- }
23
-
24
- export function scrollTopTo(
25
- scroller: HTMLElement,
26
- to: number,
27
- duration: number,
28
- callback: Function
29
- ) {
30
- let current = getScrollTop(scroller);
31
-
32
- const isDown = current < to;
33
- const frames = duration === 0 ? 1 : Math.round((duration * 1000) / 16);
34
- const step = (to - current) / frames;
35
-
36
- function animate() {
37
- current += step;
38
-
39
- if ((isDown && current > to) || (!isDown && current < to)) {
40
- current = to;
41
- }
42
-
43
- setScrollTop(scroller, current);
44
-
45
- if ((isDown && current < to) || (!isDown && current > to)) {
46
- raf(animate);
47
- } else if (callback) {
48
- raf(callback as FrameRequestCallback);
49
- }
50
- }
51
-
52
- animate();
53
- }
@@ -1,11 +0,0 @@
1
- // color
2
- export const RED = '#ee0a24';
3
-
4
- // border
5
- export const BORDER = 'van-hairline';
6
- export const BORDER_TOP = `${BORDER}--top`;
7
- export const BORDER_LEFT = `${BORDER}--left`;
8
- export const BORDER_BOTTOM = `${BORDER}--bottom`;
9
- export const BORDER_SURROUND = `${BORDER}--surround`;
10
- export const BORDER_TOP_BOTTOM = `${BORDER}--top-bottom`;
11
- export const BORDER_UNSET_TOP_BOTTOM = `${BORDER}-unset--top-bottom`;
@@ -1,45 +0,0 @@
1
- /**
2
- * bem helper
3
- * b() // 'button'
4
- * b('text') // 'button__text'
5
- * b({ disabled }) // 'button button--disabled'
6
- * b('text', { disabled }) // 'button__text button__text--disabled'
7
- * b(['disabled', 'primary']) // 'button button--disabled button--primary'
8
- */
9
-
10
- export type Mod = string | { [key: string]: any };
11
- export type Mods = Mod | Mod[];
12
-
13
- function gen(name: string, mods?: Mods): string {
14
- if (!mods) {
15
- return '';
16
- }
17
-
18
- if (typeof mods === 'string') {
19
- return ` ${name}--${mods}`;
20
- }
21
-
22
- if (Array.isArray(mods)) {
23
- return mods.reduce<string>((ret, item) => ret + gen(name, item), '');
24
- }
25
-
26
- return Object.keys(mods).reduce(
27
- (ret, key) => ret + (mods[key] ? gen(name, key) : ''),
28
- ''
29
- );
30
- }
31
-
32
- export function createBEM(name: string) {
33
- return function (el?: Mods, mods?: Mods): Mods {
34
- if (el && typeof el !== 'string') {
35
- mods = el;
36
- el = '';
37
- }
38
-
39
- el = el ? `${name}__${el}` : name;
40
-
41
- return `${el}${gen(el, mods)}`;
42
- };
43
- }
44
-
45
- export type BEM = ReturnType<typeof createBEM>;