AngularJS指令未显示在模板上

时间:2013-11-22 11:16:31

标签: javascript angularjs angularjs-directive angularjs-scope

我的角度指令有一个小问题,现在正在工作,我不知道为什么。我认为这是一个相当简单的问题,我忽略了,也许你可以帮助我。

指令的定义如下:

angular.module('directives', [])
    .directive('my-directive', function () {
        return {
            restrict: 'AE',
            scope: {
                name: '=name'
            },
            template: '<h1>{{name}}</h1>'
        };
    });

然后index.cshtml:

<my-directive name="test"></my-directive>

的application.js:

var app = angular.module('MyApp', [
    ...,
    'directives'
]);

这是controllers.js

angular.module('controllers', ['apiServices', 'directives'])
    .controller('homecontroller', function($scope, $resource, webApiService, $log, $translate, $localStorage, $sessionStorage) {

确认已加载directives.js,否则application.js会对'未知模块'进行唠叨。控制台中没有错误消息,事情就是没有显示。有什么想法吗?


修改

正如所指出的,我将指令名称更改为camelCase,但仍然没有运气:

<my-directive name="John Doe"></my-directive>

.directive('myDirective', function () {

但还没有任何表现。

修改

问题是angular需要将对象传递给属性,而不是字符串文字。如果您创建了一个对象person = {name:'John'},请将该人传入,然后写{{person.name}}(假设我们将属性person + scope var person命名)。

5 个答案:

答案 0 :(得分:20)

规范化期间,Angular将-分隔的名称转换为camelCase。

因此在JS中指定指令时使用camelCase:

.directive('myDirective', function () {

Fiddle

答案 1 :(得分:8)

我确定您已经明白这一点,但是如果您将名称的范围定义更改为

scope: {
  name: '@'
}

然后你就可以传递一个字符串了。 &#39; @&#39; &#39; =&#39;插入属性。绑定它。此外,如果属性名称与范围变量相同,则不需要包含属性名称。

答案 2 :(得分:7)

问题似乎出现在指令定义中。你在问题中注意到Angular期望一个对象;对于&#34; =&#34;这是正确的。范围,但不适用于&#34; @&#34;范围。在&#34; @&#34;范围,Angular只需要一个字符串。我在下面创建了一个片段。

模块太多

除非您在多个应用程序中重用该指令,否则不要为它创建新模块。将指令定义添加到为应用程序创建的模块中。在下面的示例中,我使用&#34; angular.module(moduleName)&#34;来调用模块... ...当只使用一个参数时,Angular返回现有对象而不是创建新对象。这就是我们如何将代码分成许多文件。

注意事项

您会注意到以下内容:

  1. 您无需将模块加载到app变量中。每次调用Singleton实际上更安全,更容易进行内存管理。
  2. 正如您已经注意到的那样,该指令属于驼峰式情况。
  3. 我将name属性设置为字符串值而不是对象;这是因为&#34; @&#34;范围设定。
  4. div设置为ng-app =&#39; MyApp&#39;。这通常设置为html元素,但我不想在Stack Exchange上弄乱DOM。可以在任何元素上设置ng-app指令,并且与该模块关联的指令将应用于该元素范围内的所有元素。如果没有ng-app指令,Angular就不知道在页面上运行哪个模块。
  5. &#13;
    &#13;
    //app.js - this defines the module, it uses two parameters to tell the injector what to do.
    angular.module('MyApp',[]);
    
    //directive.js stored elsewhere
    //this calls back the module that has been created. It uses one parameter because the injector is no longer needed.
    angular.module('MyApp').directive('myDirective', function () {
           return {
             restrict: 'AE',
               scope: {
                 name: '@'
             },
             template: '<h1>{{name}}</h1>'
           };
    });
    &#13;
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
        
    <div ng-app="MyApp">
    <h1>Successful Load</h1>
    <my-directive name="test"></my-directive>
    <p>By applying the directive definition to the MyApp module, the MyApp module knows to activate the directive within this scope. In this form, it does not get injected.</p>
    </div>
    &#13;
    &#13;
    &#13;

    使用注入

    如果每个指令或控制器都有不同的模块,则必须将每个模块注入应用程序的模块定义中。这留下了很大的错误空间。作为最佳实践,仅在必要时创建新模块,并使模块成为一组相关功能的容器,而不是单个项目。

    下面的代码演示了正确的注射。

    &#13;
    &#13;
    angular.module( "MyApp", ['ReusableDirectives'] );
    angular.module( "MyApp" ).directive( "myDirective", function(){
      return {
        restrict: "AE",
        scope: { name: "@" },
        template: "<p>This is the directive I defined in the example above. It uses <u>the same module</u> as my main application, because it is not going to be reused over and over again. In fact, I will need it just for this application, so I don't need to complicate things with a new module.  This directive takes an attribute called 'name' and if it is a string allows me to manipulate the string within my templates scope to do things like this: {{'hello ' + name + '!'}}</p>"
      };
    } );
    angular.module( "ReusableDirectives", [] );
    angular.module( "ReusableDirectives" ).directive("reusableDirective", function(){
      return {
        restrict: "E",
        template: "<p>This is a directive that I intend to use in many, many applications. Because I will reuse it so much, I am putting it in a separate module from my main application, and I will inject this directive. This is the only reason that this directive is not in the same module as the one I defined above.</p>"
      };
    } ).directive("reusableDirective2", function(){
      return {
        restrict: "E",
        template: "<p>This is a second directive that I intend to use in multiple applications. I have stored it in a module with the first directive so that I can freely inject it into as many apps as I like.</p>"
      };
    } )
    &#13;
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
    
    <div ng-app="MyApp">
      <h1>Successful Load</h1>
      <my-directive name="Johnny"></my-directive>
      <p>By applying the directive definition to the MyApp module, the MyApp module knows to activate the directive within this scope. In this form, it does not get injected.</p>
      <h3>Injected Directives</h3>
      <reusable-directive></reusable-directive>
      <reusable-directive2></reusable-directive2>
    </div>
    &#13;
    &#13;
    &#13;

    保持简单。在您的应用程序的单个模块上定义指令。一旦你完成并完成了工作,如果你需要在另一个应用程序中再次使用这些指令,那么在你有更多的Angular练习之后,重构和尝试注射。

    你对Angular有一个光明的未来,保持良好的工作!

答案 3 :(得分:4)

你的指令必须是骆驼式的

    .directive('myDirective', function () {

然后在您的HTML中,您可以免费调用它my-directivemyDirective

两者都有效

<my-directive name="test"></my-directive>
<myDirective name="test"></myDirective>

答案 4 :(得分:1)

为了跟进这一点,我必须使用以下方法来使我的指令起作用。

<my-directive name="test"></my-directive>