在 Nativescript 中使用开关实现单选按钮行为 (angular 2)
Implementing radio button behavior using a switch in Nativescript (angular 2)
我正在尝试模仿 nativescript 中的单选按钮行为,但我遇到了绑定问题。下面的代码几乎可以工作,但是如果我 "long tap" 或轻扫其中一个开关,我不相信绑定有效,因为当我点击另一个开关时它不会取消选择。
<StackLayout orientation="horizontal" *ngFor="let site of sites">
<Label [text]="site.station_name" class="medium-spacing" (tap)="goToObserve()"></Label>
<Switch text="" [checked]="isSiteSelected(site)" (tap)="toggleSite(site)"></Switch>
</StackLayout>
这里是组件函数
toggleSite(site) {
setTimeout(() => {
for(var s of this.sites) {
if(s.station_id == site.station_id) {
s.selected = true;
}
else {
s.selected = false;
}
}
}, 50);
}
关于正确实施的任何想法?我尝试了使用 [ngModel] 和 (propertyChange)="toggleSite(site)" 的各种迭代,但似乎没有任何效果。 setTimeout 也看起来很老套,但如果没有它,开关似乎总是在开关后面。
解决方案 我使用的是基于@Nikolay Tsonev 的回答。我很高兴我可以摆脱 setTimeout。我将两个参数都传递给 toggleSite($event, site) 可能是不正确的,但它似乎有效。
<StackLayout orientation="vertical">
<StackLayout orientation="vertical" class="data-grid">
<StackLayout class="grid-header" orientation="horizontal">
<Label text="Sites" class="left-column" width="70%"></Label>
<Label text="Selected" class="right-column" width="30%"></Label>
</StackLayout>
<ScrollView height="50%">
<StackLayout>
<StackLayout orientation="horizontal" *ngFor="let site of sites" height="50">
<Label text="{{ cameraIcon }}" (tap)="viewSitePhoto()" class="icon" width="10%"></Label>
<Label [text]="site.station_name" class="medium-spacing" (tap)="viewSiteObservations()" width="60%" text-align="left"></Label>
<Switch text="" [checked]="site.selected" (checkedChange)="toggleSite($event, site)" width="30%" text-align="right"></Switch>
</StackLayout>
</StackLayout>
</ScrollView>
</StackLayout>
</StackLayout>
在我的组件中我有:
toggleSite(event, site) {
let newSwitchValue = event.value;
if(newSwitchValue) {
for(var s of this.sites) {
if(s.station_id == site.station_id) {
s.selected = true;
}
else {
s.selected = false;
}
}
}
}
您可以使用 Switch checkedChange
事件,它会在组件的值发生更改时通知您。我附上示例代码。如需进一步帮助,您可以查看这些示例 - examples.
app.component.html
<StackLayout orientation="horizontal" >
<Label text="station_name" class="medium-spacing"></Label>
<Switch checked="isSiteSelected" (checkedChange)="selectedvalueChanged($event)"></Switch>
</StackLayout>
app.component.ts
import {Component} from "@angular/core";
@Component({
selector: "my-app",
templateUrl: "app.component.html",
})
export class AppComponent {
public counter: number = 16;
public get message(): string {
if (this.counter > 0) {
return this.counter + " taps left";
} else {
return "Hoorraaay! \nYou are ready to start building!";
}
}
public onTap() {
this.counter--;
}
public selectedvalueChanged(args) {
console.log(args.object.checked)
}
}
我正在尝试模仿 nativescript 中的单选按钮行为,但我遇到了绑定问题。下面的代码几乎可以工作,但是如果我 "long tap" 或轻扫其中一个开关,我不相信绑定有效,因为当我点击另一个开关时它不会取消选择。
<StackLayout orientation="horizontal" *ngFor="let site of sites">
<Label [text]="site.station_name" class="medium-spacing" (tap)="goToObserve()"></Label>
<Switch text="" [checked]="isSiteSelected(site)" (tap)="toggleSite(site)"></Switch>
</StackLayout>
这里是组件函数
toggleSite(site) {
setTimeout(() => {
for(var s of this.sites) {
if(s.station_id == site.station_id) {
s.selected = true;
}
else {
s.selected = false;
}
}
}, 50);
}
关于正确实施的任何想法?我尝试了使用 [ngModel] 和 (propertyChange)="toggleSite(site)" 的各种迭代,但似乎没有任何效果。 setTimeout 也看起来很老套,但如果没有它,开关似乎总是在开关后面。
解决方案 我使用的是基于@Nikolay Tsonev 的回答。我很高兴我可以摆脱 setTimeout。我将两个参数都传递给 toggleSite($event, site) 可能是不正确的,但它似乎有效。
<StackLayout orientation="vertical">
<StackLayout orientation="vertical" class="data-grid">
<StackLayout class="grid-header" orientation="horizontal">
<Label text="Sites" class="left-column" width="70%"></Label>
<Label text="Selected" class="right-column" width="30%"></Label>
</StackLayout>
<ScrollView height="50%">
<StackLayout>
<StackLayout orientation="horizontal" *ngFor="let site of sites" height="50">
<Label text="{{ cameraIcon }}" (tap)="viewSitePhoto()" class="icon" width="10%"></Label>
<Label [text]="site.station_name" class="medium-spacing" (tap)="viewSiteObservations()" width="60%" text-align="left"></Label>
<Switch text="" [checked]="site.selected" (checkedChange)="toggleSite($event, site)" width="30%" text-align="right"></Switch>
</StackLayout>
</StackLayout>
</ScrollView>
</StackLayout>
</StackLayout>
在我的组件中我有:
toggleSite(event, site) {
let newSwitchValue = event.value;
if(newSwitchValue) {
for(var s of this.sites) {
if(s.station_id == site.station_id) {
s.selected = true;
}
else {
s.selected = false;
}
}
}
}
您可以使用 Switch checkedChange
事件,它会在组件的值发生更改时通知您。我附上示例代码。如需进一步帮助,您可以查看这些示例 - examples.
app.component.html
<StackLayout orientation="horizontal" >
<Label text="station_name" class="medium-spacing"></Label>
<Switch checked="isSiteSelected" (checkedChange)="selectedvalueChanged($event)"></Switch>
</StackLayout>
app.component.ts
import {Component} from "@angular/core";
@Component({
selector: "my-app",
templateUrl: "app.component.html",
})
export class AppComponent {
public counter: number = 16;
public get message(): string {
if (this.counter > 0) {
return this.counter + " taps left";
} else {
return "Hoorraaay! \nYou are ready to start building!";
}
}
public onTap() {
this.counter--;
}
public selectedvalueChanged(args) {
console.log(args.object.checked)
}
}