混合Typescript,Knockout,Amplify和RequireJs时的“this”关键字

时间:2013-04-01 15:12:41

标签: knockout.js this typescript amplifyjs

我有一个mvc应用程序,我在TypeScript中编写客户端代码,以及使用几个众所周知的javascript库,包括knockout,amplifyjs和requirejs。我遇到了预期行为不会发生的情况。

export class OrganizationOverviewViewModel{

    openedAssessments = ko.observableArray();
    availableSurveys = ko.observableArray();

    organizationAgentId = ko.observable();
    organizationName = ko.observable();

    selectedSurvey = ko.observable();

    public addSurvey() {
        if (this.selectedSurvey() === undefined) {
            mh.MessageHub.showError("Please Select a Survey", "what");
        }
        else {
            // we can do the post.
            // get the selected survey
            var surveyId = this.selectedSurvey();
            // call the server to add the survey

            amplify.request("addSurveyToOrganization", {
                "surveyId": surveyId,
                "organizationAgentId": this.organizationAgentId()
            },
            function (data) {
                var context = ko.contextFor($('#mainContent')[0]).$data;
                context.openedAssessments.push({ surveyId: data.SurveyId, SurveyName: data.SurveyName, NumberOfResponses: data.ResponseCount });
                context.availableSurveys.remove(function (item) { return item.SurveyId == surveyId; });
            });
        }
    }

}

问题出在addSurvey()中。在放大请求中,我希望'this'关键字仍然指向类的实例。相反,它指向整个窗口。我有一个解决方法,就是使用knockout来从DOM中获取上下文,但这看起来似乎不是一个好主意。

使用打字稿有更好的方法吗?

2 个答案:

答案 0 :(得分:5)

在Typescript中,“this”关键字遵循javascript语义而不是C#等OO语言的语义(现在?)

“this”正确指向对象的唯一位置是通过构造函数。所以你需要写这样的东西:

export class OrganizationOverviewViewModel{

    public addSurvey;

    constructor() {
        this.addSurvey = () => {
           // you can safely use 'this' in here
           ...
        }
    }
    :
}

编辑:新版本(0.9.1)允许您对lambda字段初始值设定项使用“this”( NOT函数)。因此,您可以使用以下内容转换为上面的代码。

export class OrganizationOverviewViewModel{

    public addSurvey = () => {
        // you can safely use 'this' in a field initializer
    }

    public badSurvey_dont_use_this() {
        // 'this' is probably not the 'this' you're looking for
    }
}

答案 1 :(得分:0)

看看TypeScript and Knockout binding to 'this' issue - lambda function needed? - 这与Ray提到的看似正确的方法相同