我正在尝试为我目前正在使用Angular创建的应用程序创建一个模拟时钟。
我需要根据当前时间全天候旋转秒/分钟/小时处理程序,但我不知道如何更新每个处理程序上的 style.transform
属性。
这是我到目前为止的代码:
import { Component, OnInit } from '@angular/core';
@Component({
selector: 'app-clock',
templateUrl: './clock.component.html',
styleUrls: ['./clock.component.css']
})
export class ClockComponent implements OnInit {
constructor() { }
ngOnInit() { }
}
body {
margin: 0;
}
.wrapper {
display: flex;
justify-content: center;
align-items: center;
height: 100vh;
width: 100%;
font-family: Verdana, Geneva, Tahoma, sans-serif;
}
.clock {
width: 150px;
height: 150px;
background-color: #20b7af;
border: 12px solid white;
box-shadow: 0 0 30px rgb(202, 202, 202);
border-radius: 50%;
position: relative;
}
#sec-hand {
width: 1px;
height: 50%;
background-color: rgb(255, 255, 255);
transform-origin: 50% 80%;
position: absolute;
top: 10%;
left: 50%;
}
#min-hand {
width: 5px;
height: 40%;
background-color: rgb(255, 255, 255);
transform-origin: 50% 80%;
position: absolute;
top: 18%;
left: calc(50% - 1px);
}
#hr-hand {
width: 3px;
height: 25%;
background-color: rgb(255, 255, 255);
transform-origin: 50% 80%;
position: absolute;
top: 30%;
left: calc(50% + -2px);
}
.num {
height: 100%;
position: absolute;
left: calc(50% - 0.5em);
font-size: 10px;
}
.num div {
width: 1em;
line-height: 2em;
color: rgb(255, 255, 255);
text-align: center;
vertical-align: middle;
}
.num1 {
transform: rotate(30deg);
}
.num1 div {
transform: rotate(-30deg);
}
.num2 {
transform: rotate(60deg);
}
.num2 div {
transform: rotate(-60deg);
}
.num3 {
transform: rotate(90deg);
}
.num3 div {
transform: rotate(-90deg);
}
.num4 {
transform: rotate(120deg);
}
.num4 div {
transform: rotate(-120deg);
}
.num5 {
transform: rotate(150deg);
}
.num5 div {
transform: rotate(-150deg);
}
.num6 {
transform: rotate(180deg);
}
.num6 div {
transform: rotate(-180deg);
}
.num7 {
transform: rotate(210deg);
}
.num7 div {
transform: rotate(-210deg);
}
.num8 {
transform: rotate(240deg);
}
.num8 div {
transform: rotate(-240deg);
}
.num9 {
transform: rotate(270deg);
}
.num9 div {
transform: rotate(-270deg);
}
.num10 {
transform: rotate(300deg);
}
.num10 div {
transform: rotate(-300deg);
}
.num11 {
transform: rotate(330deg);
}
.num11 div {
transform: rotate(-330deg);
}
.num12 {
transform: rotate(0deg);
}
.num12 div {
transform: rotate(-0deg);
}
.as-console-wrapper {
display: none !important;
}
<div class="wrapper">
<div class="clock" #clock>
<div class="num num1">
<div>1</div>
</div>
<div class="num num2">
<div>2</div>
</div>
<div class="num num3">
<div>3</div>
</div>
<div class="num num4">
<div>4</div>
</div>
<div class="num num5">
<div>5</div>
</div>
<div class="num num6">
<div>6</div>
</div>
<div class="num num7">
<div>7</div>
</div>
<div class="num num8">
<div>8</div>
</div>
<div class="num num9">
<div>9</div>
</div>
<div class="num num10">
<div>10</div>
</div>
<div class="num num11">
<div>11</div>
</div>
<div class="num num12">
<div>12</div>
</div>
<div id="hr-hand"></div>
<div id="min-hand"></div>
<div id="sec-hand"></div>
</div>
</div>
您可以在不同的元素(如 sec-hand
)上使用模板变量,然后在组件中获取对它的引用:
<div id="sec-hand" #secHand></div>
然后在组件中使用 @ViewChild
获取引用:
@ViewChild('secHand') el: ElementRef;
现在你可以访问 DOM 元素(参见 Stackblitz 中的工作示例)。 该示例只是添加一个类,因此您需要检查文档以了解您需要完成的内容,例如转换setStyle
。
import { Component, AfterViewInit, ViewChild, Renderer2, ElementRef } from '@angular/core';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: [ './app.component.css' ]
})
export class AppComponent implements AfterViewInit {
@ViewChild('secHand') el: ElementRef;
constructor(private renderer: Renderer2) {}
ngAfterViewInit() {
this.renderer.addClass(this.el.nativeElement, 'example');
}
}
将refs
添加到 3 只手中,因此在您的 HTML 模板中:
<div id="hr-hand" #hrHand></div>
<div id="min-hand" #minHand></div>
<div id="sec-hand" #secHand></div>
然后使用 @ViewChild
在组件中声明和初始化它们,并使用它们直接更新所需的 transform: rotate(...)
属性,或者更好的是使用 Renderer2
渲染器更新,这使您的应用程序更安全地抵御 XSS 攻击:
import { Component, OnInit, Renderer2 } from '@angular/core';
@Component({
selector: 'app-clock',
templateUrl: './clock.component.html',
styleUrls: ['./clock.component.css']
})
export class ClockComponent implements OnInit {
@ViewChild('hrHand') hrHandRef: ElementRef;
@ViewChild('minHand') minHandRef: ElementRef;
@ViewChild('secHand') secHandRef: ElementRef;
constructor(
private renderer: Renderer2
) { }
ngOnInit() {
...
}
updateHands() {
// Directly (bad):
// this.hrHandRef.nativeElement.style.transform = `rotate(${ hrAngle }deg)`;
// this.minHandRef.nativeElement.style.transform = `rotate(${ minAngle }deg)`;
// this.secHandRef.nativeElement.style.transform = `rotate(${ secAngle }deg)`;
// Using a renderer (good):
this.renderer.setStyle(this.hrHandRef.nativeElement, 'transform', `rotate(${ hrAngle }deg)`;
this.renderer.setStyle(this.minHandRef.nativeElement, 'transform', `rotate(${ minAngle }deg)`;
this.renderer.setStyle(this.secHandRef.nativeElement, 'transform', `rotate(${ secAngle }deg)`;
}
}
另一种选择可能是只在它们上添加ngStyle
,并在组件上添加 3 个具有每只手角度的属性。