Newer
Older
import {Component, ComponentInterface, Element, Prop, h, Listen} from '@stencil/core';

Ekaterina Kondareva
committed
import {LinkBoxVariants} from '../../utils/utils';
@Component({
tag: 'hy-link-box',
styleUrl: 'link-box.scss',
Ekaterina Kondareva
committed
shadow: true,
})
export class LinkBox implements ComponentInterface {

Ekaterina Kondareva
committed
@Prop() variant: LinkBoxVariants = LinkBoxVariants.default;
@Prop() imageUrl: string = null;
@Prop() imageAlt: string = null;
@Prop() textTitle?: string;
@Prop() textDescription: string = null;
@Prop() url?: string;
@Prop() isExternal: boolean = false;
Ekaterina Kondareva
committed
@Prop() headerstyle: string = 'common';
@Element() el: HTMLElement;
componentDidLoad() {
let hyMainDiv = this.el.closest('.hy-main');
if (hyMainDiv) {
if (!hyMainDiv.classList.contains('with-sidebar')) {
this.headerstyle = 'large';
}
}
}
@Listen('click')
handleClick(event) {
this.openLink(event.currentTarget);
}
@Listen('keydown')
handleKeyDown(event) {
const key = (event as KeyboardEvent).code;
if (key == keys.enter) {
this.openLink(event.currentTarget);
}
}
openLink(linkbox) {
let card = linkbox.shadowRoot.querySelector('.hy-link-box-container');
window.open(card.dataset.location, card.dataset.target);
}
@Listen('mouseenter')
handleMouseEnter(event) {
this.manageHoverEffect(event.currentTarget);
}
@Listen('mouseleave')
handleMouseLeave(event) {
this.manageHoverEffect(event.currentTarget, false);
}
@Listen('focusin')
handleOnFocusIn(event) {
this.manageHoverEffect(event.currentTarget);
}
@Listen('focusout')
handleOnFocusOut(event) {
this.manageHoverEffect(event.currentTarget, false);
}
manageHoverEffect(linkbox, hoverOn = true) {
let title = linkbox.shadowRoot.querySelector('h3.hy-link-box__text-container__title');
let boxLink = linkbox.shadowRoot.querySelector('.hy-link-box-link');
if (hoverOn) {
(title as HTMLElement).classList.add('hy-link-box__text-container__title__hover');
(boxLink as HTMLElement).classList.add('hy-link-box-link__hover');
} else {
(title as HTMLElement).classList.remove('hy-link-box__text-container__title__hover');
(boxLink as HTMLElement).classList.remove('hy-link-box-link__hover');
}
}
Ekaterina Kondareva
committed
render() {
const classContainerAttributes = ['hy-link-box-container'].join(' ');
Ekaterina Kondareva
committed
const classAttributes = [
'hy-link-box',
this.variant,
Ekaterina Kondareva
committed
this.headerstyle,
Ekaterina Kondareva
committed
this.imageUrl ? 'hy-link-box--with-image' : null,
].join(' ');
const classLinkAttributes = [
'hy-link-box-link',
`hy-link-box-link__${this.variant}`,
`hy-link-box-link__${this.headerstyle}`,
this.headerstyle,
].join(' ');

Ekaterina Kondareva
committed
const classTextContainer = ['hy-link-box__text-container', this.imageUrl ? 'hy-link-box--with-image' : null].join(
' '
);
const classTitle = [
'hy-link-box__text-container__title',
`hy-link-box__text-container__title__${this.variant}`,
`hy-link-box__text-container__title__${this.headerstyle}`,
this.imageUrl ? 'hy-link-box__text-container__title__image' : '',
this.imageUrl ? 'image' : '',
].join(' ');
const classDescription = [
'hy-link-box__text-container__description',
`hy-link-box__text-container__description__${this.variant}`,
`hy-link-box__text-container__description__${this.headerstyle}`,
].join(' ');
Ekaterina Kondareva
committed
const target = this.isExternal ? '_blank' : '_self';
Ekaterina Kondareva
committed
const aspectRatioWidth = 16;
const aspectRatioHeight = 10;

Ekaterina Kondareva
committed
const aspect = (aspectRatioHeight / aspectRatioWidth) * 100;
const aspectRatio = {
Ekaterina Kondareva
committed
'--aspectRatio': `${aspect}%` as 'aspectRatio',

Ekaterina Kondareva
committed
};
<article class={classContainerAttributes} tabindex="0" data-target={target} data-location={this.url}>
<div class={classAttributes} aria-label={this.scLabel}>
Ekaterina Kondareva
committed
{this.imageUrl && (
<div class="hy-link-box__image-container" style={aspectRatio}>
<img aria-hidden="true" src={this.imageUrl} alt={this.imageAlt} />
</div>
)}

Ekaterina Kondareva
committed
<div class={classTextContainer}>
<h3 class={classTitle}>{this.textTitle}</h3>
{this.textDescription && <div class={classDescription}>{this.textDescription}</div>}
</div>
<a class={classLinkAttributes} href={this.url} target={target} aria-label={this.scLabel} tabindex="-1">
<hy-icon icon={'hy-icon-arrow-right'} size={32} />

Ekaterina Kondareva
committed
</a>