【问题标题】:Angular 2 - Load a component dynamically from a stringAngular 2 - 从字符串动态加载组件
【发布时间】:2016-10-06 20:06:36
【问题描述】:

我正在构建一个应用程序,它可以静态分析组件(来自 Angular 应用程序)并在 Angular 应用程序中呈现它们,这是一种样式指南,但在其中包含有关输入和组件其他方面的信息等的更多信息。

该应用程序使用 webpack 并分析一个组件并返回到一个“前端”(另一个 Angular 应用程序)关于一个组件的信息,包括它的源代码,我想在那个应用程序中呈现这个组件。

动态组件加载器要求您已导入组件并具有对它的引用(类型),我没有,因为此信息在运行时传递给应用程序。

我对如何渲染这个有点卡住了,angular2 是否有某种机制可以从字符串编译?使用某种代码生成,或者有更好的方法吗?

为了更清楚,我有:

{
"id": 0,
"name": "carte-blanche-angular2",
"kind": 0,
"flags": {},
"children": [
    {
        "id": 1,
        "name": "\"component\"",
        "kind": 1,
        "kindString": "External module",
        "flags": {
            "isExported": true
        },
        "originalName": "node_modules/carte-blanche-angular2/tmp/component.ts",
        "children": [
            {
                "id": 2,
                "name": "NameComponent",
                "kind": 128,
                "kindString": "Class",
                "flags": {
                    "isExported": true
                },
                "decorators": [
                    {
                        "name": "Component",
                        "type": {
                            "type": "reference",
                            "name": "Component"
                        },
                        "arguments": {
                            "obj": "{\n    selector: 'cb-name', // <name></name>\n    styles: [`\n    div{\n        color: red; \n        font-style:italic;\n    }\n    `],\n    // The template for our name component\n    template: `\n    <div>name : {{name}}</div>\n    `\n}"
                        }
                    }
                ],
                "children": [
                    {
                        "id": 4,
                        "name": "constructor",
                        "kind": 512,
                        "kindString": "Constructor",
                        "flags": {
                            "isExported": true
                        },
                        "signatures": [
                            {
                                "id": 5,
                                "name": "new NameComponent",
                                "kind": 16384,
                                "kindString": "Constructor signature",
                                "flags": {},
                                "type": {
                                    "type": "reference",
                                    "name": "NameComponent",
                                    "id": 2
                                }
                            }
                        ]
                    },
                    {
                        "id": 3,
                        "name": "name",
                        "kind": 1024,
                        "kindString": "Property",
                        "flags": {
                            "isExported": true
                        },
                        "decorators": [
                            {
                                "name": "Input",
                                "type": {
                                    "type": "reference",
                                    "name": "Input"
                                },
                                "arguments": {}
                            }
                        ],
                        "type": {
                            "type": "instrinct",
                            "name": "string"
                        }
                    }
                ],
                "groups": [
                    {
                        "title": "Constructors",
                        "kind": 512,
                        "children": [
                            4
                        ]
                    },
                    {
                        "title": "Properties",
                        "kind": 1024,
                        "children": [
                            3
                        ]
                    }
                ]
            }
        ],
        "groups": [
            {
                "title": "Classes",
                "kind": 128,
                "children": [
                    2
                ]
            }
        ]
    }
],
"groups": [
    {
        "title": "External modules",
        "kind": 1,
        "children": [
            1
        ]
    }
]
}

生成的 typedoc 是什么:

"{
"id": 0,
"name": "carte-blanche-angular2",
"kind": 0,
"flags": {},
"children": [
    {
        "id": 1,
        "name": "\"component\"",
        "kind": 1,
        "kindString": "External module",
        "flags": {
            "isExported": true
        },
        "originalName": "node_modules/carte-blanche-angular2/tmp/component.ts",
        "children": [
            {
                "id": 2,
                "name": "NameComponent",
                "kind": 128,
                "kindString": "Class",
                "flags": {
                    "isExported": true
                },
                "decorators": [
                    {
                        "name": "Component",
                        "type": {
                            "type": "reference",
                            "name": "Component"
                        },
                        "arguments": {
                            "obj": "{\n    selector: 'cb-name', // <name></name>\n    styles: [`\n    div{\n        color: red; \n        font-style:italic;\n    }\n    `],\n    // The template for our name component\n    template: `\n    <div>name : {{name}}</div>\n    `\n}"
                        }
                    }
                ],
                "children": [
                    {
                        "id": 4,
                        "name": "constructor",
                        "kind": 512,
                        "kindString": "Constructor",
                        "flags": {
                            "isExported": true
                        },
                        "signatures": [
                            {
                                "id": 5,
                                "name": "new NameComponent",
                                "kind": 16384,
                                "kindString": "Constructor signature",
                                "flags": {},
                                "type": {
                                    "type": "reference",
                                    "name": "NameComponent",
                                    "id": 2
                                }
                            }
                        ]
                    },
                    {
                        "id": 3,
                        "name": "name",
                        "kind": 1024,
                        "kindString": "Property",
                        "flags": {
                            "isExported": true
                        },
                        "decorators": [
                            {
                                "name": "Input",
                                "type": {
                                    "type": "reference",
                                    "name": "Input"
                                },
                                "arguments": {}
                            }
                        ],
                        "type": {
                            "type": "instrinct",
                            "name": "string"
                        }
                    }
                ],
                "groups": [
                    {
                        "title": "Constructors",
                        "kind": 512,
                        "children": [
                            4
                        ]
                    },
                    {
                        "title": "Properties",
                        "kind": 1024,
                        "children": [
                            3
                        ]
                    }
                ]
            }
        ],
        "groups": [
            {
                "title": "Classes",
                "kind": 128,
                "children": [
                    2
                ]
            }
        ]
    }
],
"groups": [
    {
        "title": "External modules",
        "kind": 1,
        "children": [
            1
        ]
    }
]
}"

这是我提到的字符串。

谢谢,

最好的问候 若昂·加林

【问题讨论】:

  • 真的是动态组件加载的问题吗?还是动态路由的问题?
  • 现在,解决方案绕过嵌入第一个应用程序(组件所属的应用程序)的包的 iframe。但是,是的,谈到动态加载和我认为可能 angular 有一些魔力可以获取一些代表组件的字符串并渲染它;Peheh

标签: angularjs angular


【解决方案1】:

您可以将此组件索引为服务中的字符串,如下所示:

export class ComponentIndexerService{
private clazzNames: Array<string>;
classes: Array<new (...args:any[]) => any>

public registerComponent(componentName : string, componentClass : new (...args[]) => any)
  {
     this.classNames.push(componentName);
     this.classes.push(componentClass);
  }
}

public get(componentName : string) {
    let index : number = this.classNames.indexOf(componentName);
    if(index > -1) {
        return this.classes[index];
    }
}

然后注册:

componentIndexerService.register("someName", ComponentClass);
componentIndexerService.register("someName2", ComponentClass2);
componentIndexerService.register("someName3", ComponentClass3);

最后使用:

constructor(dcl: DynamicComponentLoader, viewContainerRef: ViewContainerRef, componentIndexerService : ComponentIndexerService) {
    let clazz : (...args:[]) => any = componentIndexerService.get("someName");
    dcl.loadNextToLocation(clazz, viewContainerRef);
}

【讨论】:

  • 我认为该示例假定组件都在类对象中定义,并且我在字符串中确实有一些信息,例如装饰器之类的东西。所以不幸的是,不要认为这对我有用。我试过了,但我认为你发送“ClassItself”的地方只是一个实际的类,所以你可以从中直接实例化它。
  • 类本身就是注册被Angular实例化的组件类。我给ComponentClass改个名字,我觉得更好。
  • 但问题是我没有正确的类..我有类的字符串表示形式,作为字符串。不是作为一个实际的类..
  • 我也有像 @component 装饰器这样的装饰器,我需要它来渲染它的实际模板。
  • 基本上我所拥有的是创建组件的源文件的表示(因此该文件中所有内容的字符串),并且我也有一个 typedoc 生成的该组件的对象。 typedoc 生成的对象非常复杂,但我想它可以用来构建一个组件并使用动态加载器来加载它。
猜你喜欢
  • 2022-08-17
  • 1970-01-01
  • 1970-01-01
  • 2020-01-25
  • 2018-02-06
  • 1970-01-01
  • 2021-06-24
  • 2017-12-15
  • 1970-01-01
相关资源
最近更新 更多