import { AfterViewInit, Component, ElementRef, Input, OnDestroy, ViewChild } from "@angular/core"; import { Subscription, debounceTime, fromEvent } from "rxjs"; @Component({ selector: "app-scale-image", templateUrl: "./scale-image.component.html", styleUrls: ["./scale-image.component.less"], standalone: true, }) export class ScaleImageComponent implements AfterViewInit, OnDestroy { @Input({ required: true }) imageSrc: string = ""; @ViewChild("container", { static: true }) containerRef: ElementRef | null = null; @ViewChild("image", { static: true }) imageRef: ElementRef | null = null; private resizeSubscription: Subscription = new Subscription(); ngAfterViewInit(): void { this.setupResizeListener(); } ngOnDestroy(): void { if (this.resizeSubscription) this.resizeSubscription.unsubscribe(); } onImageLoad() { this.scaleImage(); } private setupResizeListener() { this.resizeSubscription = fromEvent(window, "resize") .pipe(debounceTime(200)) .subscribe(() => this.scaleImage()); } private scaleImage() { if (this.containerRef && this.imageRef) { const container = this.containerRef.nativeElement; const img = this.imageRef.nativeElement; const containerWidth = container.clientWidth; const containerHeight = container.clientHeight; const imgRatio = img.naturalWidth / img.naturalHeight; const containerRatio = containerWidth / containerHeight; let newWidth, newHeight; if (imgRatio > containerRatio) { newWidth = containerWidth; newHeight = containerWidth / imgRatio; } else { newHeight = containerHeight; newWidth = containerHeight * imgRatio; } newWidth = Math.min(newWidth, img.naturalWidth); newHeight = Math.min(newHeight, img.naturalHeight); if (img.naturalHeight / img.naturalWidth >= 5) { img.style.width = "100%"; img.style.height = "auto"; } else { img.style.width = `${newWidth}px`; img.style.height = `${newHeight}px`; } } } }