mirror of
https://gitlab.com/openstapps/openstapps.git
synced 2026-05-09 22:49:20 +00:00
95 lines
3.1 KiB
TypeScript
95 lines
3.1 KiB
TypeScript
/*
|
|
* Copyright (C) 2022 StApps
|
|
* This program is free software: you can redistribute it and/or modify it
|
|
* under the terms of the GNU General Public License as published by the Free
|
|
* Software Foundation, version 3.
|
|
*
|
|
* This program is distributed in the hope that it will be useful, but WITHOUT
|
|
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
|
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
|
* more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License along with
|
|
* this program. If not, see <https://www.gnu.org/licenses/>.
|
|
*/
|
|
|
|
import {Component, ElementRef, HostListener, Input, OnChanges, OnInit, ViewChild} from '@angular/core';
|
|
import {SCThings} from '@openstapps/core';
|
|
import {SCIcon} from '../../../util/ion-icon/icon';
|
|
|
|
const AccordionButtonState = {
|
|
collapsed: SCIcon.expand_more,
|
|
expanded: SCIcon.expand_less,
|
|
};
|
|
|
|
@Component({
|
|
selector: 'stapps-title-card',
|
|
templateUrl: './title-card.component.html',
|
|
styleUrls: ['./title-card.component.scss'],
|
|
})
|
|
export class TitleCardComponent implements OnInit, OnChanges {
|
|
/**
|
|
* The item whose title (and description) to display
|
|
*/
|
|
@Input() item: SCThings;
|
|
|
|
@ViewChild('accordionTextArea') accordionTextArea: ElementRef;
|
|
|
|
buttonState: (typeof AccordionButtonState)[keyof typeof AccordionButtonState] =
|
|
AccordionButtonState.collapsed;
|
|
|
|
buttonShown = true;
|
|
|
|
descriptionLinesShown: number;
|
|
|
|
descriptionLinesTotal: number;
|
|
|
|
descriptionPreviewLines = 3;
|
|
|
|
descriptionLinesToDisplay = 0;
|
|
|
|
ngOnInit(): void {
|
|
if (this.item.description) {
|
|
this.descriptionLinesToDisplay = this.descriptionPreviewLines;
|
|
setTimeout(() => this.checkTextElipsis(), 100);
|
|
}
|
|
}
|
|
|
|
ngOnChanges() {
|
|
this.checkTextElipsis();
|
|
}
|
|
|
|
@HostListener('window:resize', ['$event'])
|
|
checkTextElipsis() {
|
|
if (this.accordionTextArea === undefined) {
|
|
return;
|
|
}
|
|
const element = this.accordionTextArea.nativeElement as HTMLElement;
|
|
|
|
const lineHeight = Number.parseInt(getComputedStyle(element).getPropertyValue('line-height'));
|
|
this.descriptionLinesTotal = element?.scrollHeight / lineHeight;
|
|
this.descriptionLinesShown = element?.offsetHeight / lineHeight;
|
|
if (this.buttonState === AccordionButtonState.expanded) {
|
|
this.descriptionLinesToDisplay = this.descriptionLinesTotal;
|
|
}
|
|
const isElipsed = element?.offsetHeight < element?.scrollHeight;
|
|
this.buttonShown =
|
|
(isElipsed && this.buttonState === AccordionButtonState.collapsed) ||
|
|
(!isElipsed && this.buttonState === AccordionButtonState.expanded);
|
|
}
|
|
|
|
toggleDescriptionAccordion() {
|
|
if (this.descriptionLinesToDisplay > 0) {
|
|
this.descriptionLinesToDisplay =
|
|
this.descriptionLinesToDisplay === this.descriptionPreviewLines
|
|
? this.descriptionLinesTotal
|
|
: this.descriptionPreviewLines;
|
|
}
|
|
this.buttonState =
|
|
this.buttonState === AccordionButtonState.collapsed
|
|
? AccordionButtonState.expanded
|
|
: AccordionButtonState.collapsed;
|
|
setTimeout(() => this.checkTextElipsis(), 0);
|
|
}
|
|
}
|