【问题标题】:Angular2 two-way binding stop work after google maps callback谷歌地图回调后Angular2双向绑定停止工作
【发布时间】:2017-06-20 17:24:39
【问题描述】:

我在 Angular 2 应用程序上工作。我有一个谷歌地图,带有自动完成功能。我有一个输入(带有谷歌自动完成)和一个搜索按钮。当我点击搜索按钮时,我将输入数据发送到谷歌地理编码,并在地图上放置一个标记。这听起来很简单,但在此之后,angular2 数据绑定就停止工作了。输入没有得到格式化的地址,addressIsValid 没有开启 true。

HTML:

<div class="input-group">
<input autocorrect="off" autocapitalize="off" spellcheck="off" type="text"
       class="form-control" [(ngModel)]="addressInput" #search id="address" (keydown)="addressChanged()">
<div class="input-group-btn">
    <button id="addressSubmitButton" type="submit" class="btn btn-default" [class.btn-success]="addressIsValid"
            (click)="submited(search.value)">
        {{ (addressIsValid ? 'addressInput.success' : 'addressInput.search') | translate }}
    </button>
</div>

代码:

export class AddressInputComponent implements OnInit {
public map: google.maps.Map;
public autocomplete: google.maps.places.Autocomplete;
private geocoder: google.maps.Geocoder = new google.maps.Geocoder();
public marker: google.maps.Marker;
public defaultZoom: number;
public defaultLat: number;
public defaultLng: number;
public errorCode: number;
private addressIsValid: boolean;
@Input('address') private addressInput: string;
@Output() addressUpdated: EventEmitter<string> = new EventEmitter();

@ViewChild("search")
public searchElementRef: ElementRef;

constructor() {
    this.addressIsValid = false;
}

ngOnInit() {
    this.defaultZoom = 7;
    this.defaultLat = 47.338941;
    this.defaultLng = 19.396167;
    this.errorCode = null;

    this.autocomplete = new google.maps.places.Autocomplete(this.searchElementRef.nativeElement, {
        types: ["address"]
    });

    this._setMapToDefault();

    this.autocomplete.bindTo('bounds', this.map);

    this.autocomplete.addListener('place_changed', () => {
        this.addressInput = this.autocomplete.getPlace().formatted_address;
    })
}

private _setMapToDefault() {
    this.map = new google.maps.Map(document.getElementById('map'), {
        center: {lat: this.defaultLat, lng: this.defaultLng},
        zoom: this.defaultZoom,
        scrollwheel: false,
    });

    this.marker = new google.maps.Marker();
    this.marker.setMap(this.map);
}

submited() {
    this.geocoder.geocode( { 'address': this.addressInput}, (results, status) => {
        if (status == google.maps.GeocoderStatus.OK) {
            setInterval(this._changeInput(results[0]), 200);
        } else {
            this.addressIsValid = false;
            this.errorCode = 1;
            this._setMapToDefault();
        }
    });
}

private _changeInput(result) {
    this.errorCode = null;

    if (result.address_components[0].types[0] != "street_number") {
        this.addressIsValid = false;
        this.errorCode = 2;
        this._setMapToDefault();
        return;
    }

    // jQuery('#address').val(result.formatted_address);
    this.addressInput = result.formatted_address;
    this.addressUpdated.emit(this.addressInput);
    this.addressIsValid = true;

    this.map.setCenter(result.geometry.location);
    this.map.setZoom(17);
    this.marker.setPosition(result.geometry.location);
    this.marker.setVisible(true);
}

private addressChanged() {
    if (this.addressIsValid == true) {
        this.addressIsValid = false;
        this._setMapToDefault();
    }
}

}

【问题讨论】:

    标签: javascript angularjs google-maps angular


    【解决方案1】:

    不会触发更改检测,因为google.maps 使用自己的事件集/addListener 调用。这些事件不是由zone.js 修补的所谓猴子,因此不会在 Angular 区域中运行,这在逻辑上不会触发更改检测周期。

    所以你可以通过在你的组件中注入ngZone服务来解决这个问题,你可以使用run方法重新进入角度区域:

    constructor(private ngZone: NgZone) {}
    
    ngOnInit() {
        //...
        this.autocomplete.addListener('place_changed', () => {
            this.ngZone.run(() => {
                this.addressInput = this.autocomplete.getPlace().formatted_address;
            });  
        })
    }
    

    【讨论】:

    • 我面临着完全相同的问题,我快要失去理智了。
    猜你喜欢
    • 2018-05-01
    • 2015-09-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-01-10
    • 2010-11-25
    • 2013-12-10
    • 1970-01-01
    相关资源
    最近更新 更多