所以目前我正致力于使用TypeScript和VS的打字机插件简化我的前端开发。
我目前遇到的问题是使用RequireJS在浏览器中处理我的模块加载。我已经在线阅读了几篇文章,并阅读了所使用的每种技术的文档,甚至阅读了大量的SO材料。我认为这就像复杂的算术,突然之间它会点击并成为一块蛋糕,但现在所有动人的作品让我的思绪处于意大利面状态。我真的可以在这里使用一些帮助。
我将使用一个复杂的类结构示例,因为我认为问题在于缺少导入和导出/命名空间和模块声明 - 但我不确定,因为我无法绕过一切还在这里..我将尽我所能使用实际的应用程序代码和结构提供全面的代码详细信息。
C#Class:
public class SnakeViewModel
{
// Project
public ProjectViewModel Project { get; set; }
public long ProjectId { get; set; }
// Workflow
public Workflow Workflow { get; set; }
public string EntityName { get; set; }
public List<Workflow> Workflows { get; set; }
// Workflow Phases
public List<WorkflowPhase> WorkflowPhases { get; set; }
//Contractors - Name and ID
public List<ContractorDetails> ContractorDetails { get; set; }
...
......
}
TypeWriter模板:
${
using Typewriter.Extensions.Types;
Template(Settings settings)
{
settings.IncludeAllProjects();
settings.OutputExtension = ".ts";
}
string KnockoutType(Property p) {
if (p.Type.IsEnumerable) {
return p.Type.Name.TrimEnd('[',']');
}
return p.Type;
}
string KnockoutValue(Property property) {
var type = KnockoutType(property);
if (IsEnumerableViewModel(property)) {
return $"ko.observableArray<Knockout{type}>([])";
} else if (property.Type.IsEnumerable) {
return $"ko.observableArray<{type}>([])";
}
return $"ko.observable<{type}>()";
}
bool IsEnumerableViewModel(Property p) {
string type = KnockoutType(p);
return p.Type.IsEnumerable && type.EndsWith("ViewModel");
}
}
namespace Sidewinder {
$Classes(RIOT.Mvc4.ViewModels.*)[
export interface $Name {
$Properties[
$name: $Type;]
}
export class Knockout$Name {
$Properties[
public $name = $KnockoutValue;]
constructor(model: $Name) {
this.map(model);
}
public map(model: $Name) {
$Properties(x => !IsEnumerableViewModel(x))[
this.$name(model.$name);]
$Properties(x => IsEnumerableViewModel(x))[
this.$name(model.$name.map(this.map$Name));]
}
$Properties(x => IsEnumerableViewModel(x))[
public map$Name(model: $KnockoutType) {
return new Knockout$KnockoutType(model);
}]
public getModel() {
return {
$Properties(x => !IsEnumerableViewModel(x))[
$name: this.$name(),]
$Properties(x => IsEnumerableViewModel(x))[
$name: this.$name().map(x => x.getModel())][,]
}
}
}]
}
TS输出:
namespace Sidewinder {
export interface SnakeViewModel {
project: ProjectViewModel;
projectId: number;
workflow: Workflow;
entityName: string;
workflows: Workflow[];
workflowPhases: WorkflowPhase[];
contractorDetails: ContractorDetails[];
...
......
}
export class KnockoutSnakeViewModel {
public project = ko.observable<ProjectViewModel>();
public projectId = ko.observable<number>();
public workflow = ko.observable<Workflow>();
public entityName = ko.observable<string>();
public workflows = ko.observableArray<Workflow>([]);
public workflowPhases = ko.observableArray<WorkflowPhase>([]);
public contractorDetails = ko.observableArray<ContractorDetails>([]);
...
......
constructor(model: SnakeViewModel) {
this.map(model);
}
public map(model: SnakeViewModel) {
this.project(model.project);
this.projectId(model.projectId);
this.workflow(model.workflow);
this.entityName(model.entityName);
this.workflows(model.workflows);
this.workflowPhases(model.workflowPhases);
this.contractorDetails(model.contractorDetails);
...
......
}
public getModel() {
return {
project: this.project(),
projectId: this.projectId(),
workflow: this.workflow(),
entityName: this.entityName(),
workflows: this.workflows(),
workflowPhases: this.workflowPhases(),
contractorDetails: this.contractorDetails(),
...
......
}
}
}
}
编译JS:
var Sidewinder;
(function (Sidewinder) {
var KnockoutSnakeViewModel = (function () {
function KnockoutSnakeViewModel(model) {
this.project = ko.observable();
this.projectId = ko.observable();
this.workflow = ko.observable();
this.entityName = ko.observable();
this.workflows = ko.observableArray([]);
this.workflowPhases = ko.observableArray([]);
this.contractorDetails = ko.observableArray([]);
...
......
this.map(model);
}
KnockoutSnakeViewModel.prototype.map = function (model) {
this.project(model.project);
this.projectId(model.projectId);
this.workflow(model.workflow);
this.entityName(model.entityName);
this.workflows(model.workflows);
this.workflowPhases(model.workflowPhases);
this.contractorDetails(model.contractorDetails);
...
......
};
KnockoutSnakeViewModel.prototype.getModel = function () {
return {
project: this.project(),
projectId: this.projectId(),
workflow: this.workflow(),
entityName: this.entityName(),
workflows: this.workflows(),
workflowPhases: this.workflowPhases(),
contractorDetails: this.contractorDetails(),
...
......
};
};
return KnockoutSnakeViewModel;
}());
Sidewinder.KnockoutSnakeViewModel = KnockoutSnakeViewModel;
})(Sidewinder || (Sidewinder = {}));
//# sourceMappingURL=SnakeViewModel.js.map
好的,这样就显示了我的所有编辑 - 接下来我将展示一些设置和当前结构的截图,然后显示RequireJS代码。
Screenshot of File Structure..
Screenshot of TS Compiler Settings..
所以现在需要的东西 - 目前非常简陋。
配置文件:
declare var require: any;
require.config({
baseUrl: "/Scripts"
});
全球包括:
@Scripts.Render("~/bundles/ScriptRequire")
<script src="~/Scripts/app/require-config.js"></script>
Snake.cshtml:
@section scripts{
<script>
require(["App/views/project/snake"]);
</script>
}
Snake.ts:
namespace Sidewinder {
export class ViewModel extends KnockoutSnakeViewModel {
constructor(model: SnakeViewModel) {
super(model);
}
getViewModel() {
}
}
$(function () {
let initModel = {
projId: $("#projId").val(),
wfId: $("#wfId").val()
}
$.post("/ProjectApi/ProjectSnakeView",
initModel,
data => {
if (data != null) {
console.log(data);
var model = new ViewModel(data);
ko.applyBindings(model);
}
});
});
}
Snake.js:
var __extends = (this && this.__extends) || (function () {
var extendStatics = Object.setPrototypeOf ||
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b;
}) ||
function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
};
return function (d, b) {
extendStatics(d, b);
function __() { this.constructor = d; }
d.prototype = b === null ? Object.create(b) : (__.prototype =
b.prototype, new __());
};
})();
var Sidewinder;
(function (Sidewinder) {
var ViewModel = (function (_super) {
__extends(ViewModel, _super);
function ViewModel(model) {
return _super.call(this, model) || this;
}
ViewModel.prototype.getViewModel = function () {
};
return ViewModel;
}(Sidewinder.KnockoutSnakeViewModel));
Sidewinder.ViewModel = ViewModel;
$(function () {
var initModel = {
projId: $("#projId").val(),
wfId: $("#wfId").val()
};
$.post("/ProjectApi/ProjectSnakeView", initModel, function (data) {
if (data != null) {
console.log(data);
var model = new ViewModel(data);
ko.applyBindings(model);
}
});
});
})(Sidewinder || (Sidewinder = {}));
//# sourceMappingURL=snake.js.map
好吧..所以应该是所有的代码。 html本身就是KO绑定的,我只是想让它连接绑定并显示返回的数据。我明显得到依赖错误,我不明白命名空间/模块/必须引用所有内容,即使它没有问题而且编译器也不会抱怨...呃。
RequireJS注入页面的唯一内容是Snake.Js文件,它显然应该注入viewmodel本身所需的所有子类。
这些前端的东西现在变得有点复杂。
我确定我已经把事情遗漏了,并没有遵循特定的规则来发球,所以请在提出标志之前通知我这篇文章的任何具体问题 - 非常愿意回答更多问题并了解更多。< / p>