bellini/ts_catalog/elements/bellini-articlelist.ts

235 lines
5.6 KiB
TypeScript
Raw Normal View History

2025-02-03 11:31:40 +01:00
import {
DeesElement,
property,
state,
html,
customElement,
type TemplateResult,
css,
cssManager,
} from '@design.estate/dees-element';
import { ExtendedDate } from '@push.rocks/smarttime';
import * as belliniApi from '@bellini/api';
import '@design.estate/dees-catalog';
import * as helpers from '../helpers/index.js';
@customElement('bellini-articlelist')
export class BelliniArticlelist extends DeesElement {
// STATIC
public static demo = () => html``;
// INSTANCE
@property({ type: Array })
articles: belliniApi.IBelliniClientState['articles'] = [];
constructor() {
super();
}
public static styles = [
cssManager.defaultStyles,
css`
:host {
color: #fff;
}
#main {
position: relative;
padding-bottom: 20px;
transition: opacity 0.2s;
opacity: 1;
}
#main.hidden {
opacity: 0;
}
.articleRow {
border-top: 1px solid ${cssManager.bdTheme('#ffffff', ' #444444')};
position: relative;
z-index: 0;
height: 230px;
background: ${cssManager.bdTheme('#ffffff', '#212121')};
border-radius: 3px;
margin-bottom: 15px;
box-shadow: 0px 0px 5px ${cssManager.bdTheme('rgba(0, 0, 0, 0.2)', 'rgba(0, 0, 0, 0.5)')};
overflow: hidden;
display: grid;
grid-template-columns: calc(100% / 3) calc(100% / 3) calc(100% / 3);
}
a {
color: ${cssManager.bdTheme('#333333', '#fafafa')};
text-decoration: none;
}
.articleRow .articleImage {
height: inherit;
}
.articleRow .articleImage::after {
box-shadow: inset 0px 0px 100px
${cssManager.bdTheme('rgba(0, 0, 0, 0.5)', 'rgba(0, 0, 0, 0.8)')};
}
.articleRow .articleImage img {
width: calc(100% - 10px);
height: calc(100% - 10px);
margin: 5px;
border-radius: 3px;
object-fit: cover;
}
.articleRow .articleTitle,
.articleRow .articleDescription {
z-index: 1;
position: relative;
padding: 10px;
}
.articleRow .articleTitle {
padding: 15px 20px;
}
.articleRow .articleTitle h1 {
margin: 0px;
font-family: "Roboto Slab";
font-size: 25px;
font-weight: 400;
border-radius: 3px;
}
.articleRow .articleTitle h2 {
margin: 0px;
margin-top: 10px;
font-family: 'Roboto Slab';
font-size: 18px;
font-weight: 300;
color: ${cssManager.bdTheme('#444', '#CCC')};
padding-left: 10px;
border-left: 5px dotted ${cssManager.bdTheme('#00000020', '#ffffff20')};
}
.articleRow .articleDescription {
padding: 20px;
}
${cssManager.cssForTablet(css`
.articleRow {
display: grid;
grid-template-columns: calc(100% / 3) calc(100% / 3 * 2);
}
.articleRow .articleTitle {
padding: 20px;
grid-row: 1;
grid-column: 2;
}
.articleRow .articleTitle h1 {
font-size: 22px;
}
.articleRow .articleTitle h2 {
font-size: 18px;
}
.articleRow .articleDescription {
display: none;
}
`)}
${cssManager.cssForPhablet(css`
.articleRow {
height: 120px;
}
.articleRow .articleTitle {
padding: 10px;
}
.articleRow .articleTitle h1 {
font-size: 16px;
}
.articleRow .articleTitle h2 {
font-size: 12px;
}
`)}
${cssManager.cssForPhone(css`
.articleRow {
height: 160px;
}
.articleRow .articleTitle {
padding: 10px;
}
.articleRow .articleTitle h1 {
font-size: 16px;
}
.articleRow .articleTitle h2 {
font-size: 12px;
}
`)}
`,
];
public render(): TemplateResult {
return html`
<style></style>
<div id="main">
${this.articles.map((articleArg) => {
return html`
<a
href="${articleArg.url}"
@click="${(eventArg: MouseEvent) => {
this.handleArticleClick(eventArg, articleArg);
}}"
>
<div class="articleRow">
<div class="articleImage">
<img
loading="lazy"
src="${articleArg.featuredImageUrl
.replace('q=80', 'q=50')
.replace('w=2000', 'w=800')}"
/>
</div>
<div class="articleTitle">
<h1>${articleArg.title}</h1>
<h2>${articleArg.content.split('.')[0]}.</h2>
</div>
<div class="articleDescription">Click to read more.</div>
</div>
</a>
`;
})}
</div>
`;
}
private async handleArticleClick(
eventArg: MouseEvent,
articleArg: belliniApi.IBelliniClientState['articles'][0]
) {
eventArg.preventDefault();
const domtoolsInstance = await this.domtoolsPromise;
domtoolsInstance.router.pushUrl(helpers.articlehelpers.getArticleUrl(articleArg));
}
public async show(boolArg: boolean) {
const domtoolsInstance = await this.domtoolsPromise;
const mainDiv = this.shadowRoot.querySelector('#main');
if (!boolArg) {
mainDiv.classList.add('hidden');
} else {
mainDiv.classList.remove('hidden');
}
await domtoolsInstance.convenience.smartdelay.delayFor(300);
}
}