Skip to content

Commit c5ab33e

Browse files
committed
[migrate] upgrade Tab components
[fix] Count Down CSS
1 parent dbddaa0 commit c5ab33e

File tree

5 files changed

+127
-8
lines changed

5 files changed

+127
-8
lines changed

package.json

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "boot-cell",
3-
"version": "2.0.0-beta.12",
3+
"version": "2.0.0-beta.13",
44
"license": "LGPL-3.0",
55
"author": "[email protected]",
66
"description": "Web Components UI library based on WebCell v3, BootStrap v5, BootStrap Icon v1 & FontAwesome v6",
@@ -29,7 +29,7 @@
2929
"dom-renderer": "^2.0.6",
3030
"mobx": "^6.12.0",
3131
"regenerator-runtime": "^0.14.1",
32-
"web-cell": "^3.0.0-rc.8",
32+
"web-cell": "^3.0.0-rc.9",
3333
"web-utility": "^4.1.3"
3434
},
3535
"peerDependencies": {

pnpm-lock.yaml

+4-4
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

source/CountDown.tsx

+4-2
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,9 @@ interface TimeSection {
1313
label: string;
1414
}
1515

16-
const colors = Object.keys(Status).slice(0, 4);
16+
const colors = Object.keys(Status)
17+
.filter(color => color !== 'tertiary')
18+
.slice(0, 4);
1719

1820
export interface CountDownProps {
1921
endTime?: string | Date | number;
@@ -100,7 +102,7 @@ export class CountDown extends HTMLElement implements WebCell<CountDownProps> {
100102
{this.timeSections.map(({ value, label }, index) => (
101103
<li
102104
key={value}
103-
className={`list-inline-item display-4 bg-${colors[index]} d-inline-flex align-items-center justify-content-center rounded-5`}
105+
className={`list-inline-item fs-4 bg-${colors[index]} d-inline-flex align-items-center justify-content-center rounded-3`}
104106
style={{ width: '5.5rem', height: '5.5rem' }}
105107
>
106108
<small>

source/Tabs.tsx

+116
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
import { JsxChildren } from 'dom-renderer';
2+
import { observable } from 'mobx';
3+
import {
4+
WebCell,
5+
attribute,
6+
component,
7+
observer,
8+
on,
9+
reaction
10+
} from 'web-cell';
11+
import { CustomElement } from 'web-utility';
12+
13+
import { Nav, NavLink } from './Nav';
14+
15+
export interface TabProps {
16+
caption: JsxChildren;
17+
}
18+
19+
export interface Tab extends WebCell<TabProps> {}
20+
21+
@component({ tagName: 'tab-pane' })
22+
export class Tab extends HTMLElement implements WebCell<TabProps> {
23+
caption: JsxChildren;
24+
25+
connectedCallback() {
26+
this.classList.add('tab-pane', 'fade');
27+
this.role = 'tabpanel';
28+
}
29+
}
30+
31+
@component({
32+
tagName: 'tabs-box',
33+
mode: 'open'
34+
})
35+
@observer
36+
export class Tabs extends HTMLElement implements CustomElement {
37+
@observable
38+
accessor tabMeta: TabProps[] = [];
39+
40+
@attribute
41+
@observable
42+
accessor currentIndex = 0;
43+
44+
connectedCallback() {
45+
this.turnPaneTo(this.currentIndex);
46+
}
47+
48+
@on('slotchange', 'slot')
49+
handleSlotChange(_: Event, slot: HTMLSlotElement) {
50+
const tabs = slot.assignedElements() as Tab[];
51+
52+
if (this.tabMeta.length !== tabs.length)
53+
this.tabMeta = tabs.map(({ caption }) => ({ caption }));
54+
}
55+
56+
@on('click', '.nav-tabs > .nav-link')
57+
handleTabClick(
58+
event: MouseEvent,
59+
{ dataset: { index } }: HTMLAnchorElement
60+
) {
61+
event.preventDefault();
62+
event.stopPropagation();
63+
64+
this.currentIndex = +index;
65+
}
66+
67+
@reaction(({ currentIndex }) => currentIndex)
68+
turnPaneTo(index: number) {
69+
const previous = this.querySelector<Tab>('tab-pane.active');
70+
71+
if (previous) {
72+
previous.hidden = true;
73+
previous.classList.remove('active', 'show');
74+
}
75+
const next = this.children[index] as Tab;
76+
77+
next.hidden = false;
78+
next.classList.add('active', 'show');
79+
}
80+
81+
renderContent() {
82+
const { tabMeta, currentIndex } = this;
83+
84+
return (
85+
<>
86+
<Nav className="nav-tabs" role="tablist">
87+
{tabMeta.map(({ caption }, index) => (
88+
<NavLink
89+
role="tab"
90+
data-index={index}
91+
className={currentIndex === index ? 'active' : ''}
92+
ariaSelected={`${currentIndex === index}`}
93+
>
94+
{caption}
95+
</NavLink>
96+
))}
97+
</Nav>
98+
<div className="tab-content">
99+
<slot />
100+
</div>
101+
</>
102+
);
103+
}
104+
105+
render() {
106+
return (
107+
<>
108+
<link
109+
rel="stylesheet"
110+
href="https://unpkg.com/[email protected]/dist/css/bootstrap.min.css"
111+
/>
112+
{this.renderContent()}
113+
</>
114+
);
115+
}
116+
}

source/index.ts

+1
Original file line numberDiff line numberDiff line change
@@ -19,5 +19,6 @@ export * from './Carousel';
1919
export * from './Nav';
2020
export * from './Navbar';
2121
export * from './Offcanvas';
22+
export * from './Tabs';
2223
export * from './CountDown';
2324
export * from './MonthCalendar';

0 commit comments

Comments
 (0)