我如何 return javascript 中延迟方法的值
How can I return the value of a deferred method in javascript
我正在尝试编写一个模块,将坐标投影到新的空间参考中,但是 javascript 语法再次打败了我。
这是模块当前的样子:
define(["esri/geometry/Point", ...],
function(Point, SpatialReference, ...){
var gmsvc = new GeometryService("http://server/maps/rest/services/Utilities/Geometry/GeometryServer");
/*...*/
return {
/*...*/
//transforms the current point on the map to the new wkid
transformCoordinates: function(point, newWkId) {
var param = new ProjectParameters();
var newPoint;
param.geometries = [point];
param.outSR = new SpatialReference({ wkid: newWkId});
gmsvc.project(param);
gmsvc.on('project-complete', function(result) {
newPoint = result.geometries[0];
});
return newPoint;
}
};
});
根据 documentation GeometryService.project(parameter)
标记为延迟,因此我尝试在 OnProjectComplete 事件中访问它的结果。此时 result.geometries[0]
是具有 x、y 和 SpatialReference 属性 的有效点。
将其分配给 newPoint
变量并 returning 它,导致 undefined
被 returned:
console.log(CoordinateTransUtils.transformCoordinates(evt.mapPoint, 5254));
> undefined
将代码更改为
return gmsvc.on('project-complete', function(result) {
return result.geometries[0];
});
导致 return 值为:
Object {id: 216, receiveArguments: true, previous: Object}advice: (){var b,c={},e=arguments.length;for(b=0;b<e;b++)c[f[b]]=arguments[b];c.target||(c.target=d);a.call(d,c)}id: 216next: Objectprevious: ObjectreceiveArguments: trueremove: (){if(h.advice){var c=h.previous,d=h.next;!d&&!c?delete b[e]:(c?c.next=d:b[e]=d,d&&(d.previous=c));b=a=h.advice=null}}__proto__: Object
这也不是重点。
因此,我的问题是,如何 return 存储在 result.geometries[0]
中的点,并解释我在这里做错了什么。
在您的示例中,newPoint
只会在 已经处理 return
语句后实际设置 ,因此当该行运行时它是未定义的。
通常,如果您的函数逻辑中的某些内容是异步的,那么您的函数本身也需要在本质上是异步的。通常在这些情况下,建议 return 一个承诺。例如:
transformCoordinates: function(point, newWkId) {
var dfd = new Deferred(); // (from dojo/Deferred)
var param = new ProjectParameters();
param.geometries = [point];
param.outSR = new SpatialReference({ wkid: newWkId});
gmsvc.project(param);
gmsvc.on('project-complete', function(result) {
dfd.resolve(result.geometries[0]);
});
// If there is an accompanying error event, you should also
// listen to that and call dfd.reject in its handler.
return dfd.promise;
}
我正在尝试编写一个模块,将坐标投影到新的空间参考中,但是 javascript 语法再次打败了我。
这是模块当前的样子:
define(["esri/geometry/Point", ...],
function(Point, SpatialReference, ...){
var gmsvc = new GeometryService("http://server/maps/rest/services/Utilities/Geometry/GeometryServer");
/*...*/
return {
/*...*/
//transforms the current point on the map to the new wkid
transformCoordinates: function(point, newWkId) {
var param = new ProjectParameters();
var newPoint;
param.geometries = [point];
param.outSR = new SpatialReference({ wkid: newWkId});
gmsvc.project(param);
gmsvc.on('project-complete', function(result) {
newPoint = result.geometries[0];
});
return newPoint;
}
};
});
根据 documentation GeometryService.project(parameter)
标记为延迟,因此我尝试在 OnProjectComplete 事件中访问它的结果。此时 result.geometries[0]
是具有 x、y 和 SpatialReference 属性 的有效点。
将其分配给 newPoint
变量并 returning 它,导致 undefined
被 returned:
console.log(CoordinateTransUtils.transformCoordinates(evt.mapPoint, 5254));
> undefined
将代码更改为
return gmsvc.on('project-complete', function(result) {
return result.geometries[0];
});
导致 return 值为:
Object {id: 216, receiveArguments: true, previous: Object}advice: (){var b,c={},e=arguments.length;for(b=0;b<e;b++)c[f[b]]=arguments[b];c.target||(c.target=d);a.call(d,c)}id: 216next: Objectprevious: ObjectreceiveArguments: trueremove: (){if(h.advice){var c=h.previous,d=h.next;!d&&!c?delete b[e]:(c?c.next=d:b[e]=d,d&&(d.previous=c));b=a=h.advice=null}}__proto__: Object
这也不是重点。
因此,我的问题是,如何 return 存储在 result.geometries[0]
中的点,并解释我在这里做错了什么。
在您的示例中,newPoint
只会在 已经处理 return
语句后实际设置 ,因此当该行运行时它是未定义的。
通常,如果您的函数逻辑中的某些内容是异步的,那么您的函数本身也需要在本质上是异步的。通常在这些情况下,建议 return 一个承诺。例如:
transformCoordinates: function(point, newWkId) {
var dfd = new Deferred(); // (from dojo/Deferred)
var param = new ProjectParameters();
param.geometries = [point];
param.outSR = new SpatialReference({ wkid: newWkId});
gmsvc.project(param);
gmsvc.on('project-complete', function(result) {
dfd.resolve(result.geometries[0]);
});
// If there is an accompanying error event, you should also
// listen to that and call dfd.reject in its handler.
return dfd.promise;
}