import { Component, OnInit, ViewChild, ElementRef, NgZone } from '@angular/core'; import * as graph3DLib from 'graph3D'; import { GHCIService } from '../../../shared/services/ghci.service'; import { formatJSON, AnimationProps, Zoom3DType, GraphProps, Default_GraphProps, debounce } from './graph3D.helper'; @Component({ selector: 'graph3d-component', templateUrl: './graph3D.component.html', styleUrls: ['./graph3D.component.scss'], host: { '(window:resize)': 'onResize($event)' } }) export class Graph3DComponent { private ghciServiceSub: any; @ViewChild('graph3DElement') private graph3DRef: ElementRef; private graphProps : GraphProps = Default_GraphProps; private animationProps : AnimationProps = { visible: false, playing: false, value: 0, speed: 1000 }; constructor(ghciService: GHCIService, private zone: NgZone) { this.ghciServiceSub = ghciService.messages.subscribe( message => { if (message.tipo == "canvas3D") { const figures = JSON.parse(formatJSON(message.resultado)); graph3DLib.drawFigures(figures); } else if (message.tipo == "animacion3D") { const frames = message.resultado.map((frame) => JSON.parse(formatJSON(frame))); this.animationProps.visible = true; this.animationProps.playing = true; this.animationProps.value = 0; graph3DLib.clear(); graph3DLib.initializeAnimation(frames, (value) => this.animationProps.value = value ); graph3DLib.playAnimation(); } } ) } ngAfterViewInit() { // this.zone.runOutsideAngular(() => { graph3DLib.initialize(this.graph3DRef.nativeElement); //}) } ngOnDestroy() { if (this.ghciServiceSub) { this.ghciServiceSub.unsubscribe(); } } onResize(event){ const {width, height} = this.graph3DRef.nativeElement.getBoundingClientRect(); graph3DLib.changeSize({width, height}); } onAnimationChangeSpeed = (value) => { this.animationProps.speed = parseInt(value); graph3DLib.changeSpeedAnimation(parseInt(value)); } onAnimationTogglePlay = () => { if (this.animationProps.playing) { graph3DLib.pauseAnimation(); } else { graph3DLib.playAnimation(); } this.animationProps.playing = !this.animationProps.playing; } public changeZoomType = (type: Zoom3DType = null) => { if (type != null) { this.graphProps.zoomType = type; } else { this.graphProps.zoomType = (this.graphProps.zoomType % 4) + 1; } graph3DLib.changeZoomType(this.graphProps.zoomType); } public changeAxesVisibility = () => { this.graphProps.showAxes = !this.graphProps.showAxes; graph3DLib.showAxes(this.graphProps.showAxes); } handleAxesRangeDebounced = debounce(function () { setTimeout(() => graph3DLib.changeAxesSize(this.graphProps.range) ); }, 500); public onChangeAxesSize = (v, event) => { let value = this.graphProps.range[v]; const min = parseInt(event.target.min); const max = parseInt(event.target.max); if (value == null) { value = v.search('Min') ? min : max; this.graphProps.range[v] = value; } if (value < min) { this.graphProps.range[v] = min; } if (value > max) { this.graphProps.range[v] = max; } this.handleAxesRangeDebounced(); //graph3DLib.changeAxesSize(this.graphProps.range) } public onChangeQuality = () => { const value = this.graphProps.quality; if (value == null || value <= 1) { this.graphProps.quality = 30; } else { this.graphProps.quality = value; } graph3DLib.changeOptions({quality: value}); } public zoomIn = () => { graph3DLib.changeZoom(true); } public zoomOut = () => { graph3DLib.changeZoom(false); } public clear = () => { this.animationProps.visible = false; graph3DLib.clear(); } public center = () => { this.graphProps = Default_GraphProps; graph3DLib.reset(); } public getZoom3DTypeName = (type: Zoom3DType) => { switch (type) { case Zoom3DType.Normal: return 'Normal'; case Zoom3DType.XAxis: return 'Eje x'; case Zoom3DType.YAxis: return 'Eje y'; case Zoom3DType.ZAxis: return 'Eje z'; } } }