0

I'd like to avoid repeating myself with my page header as much as possible. So, I'm thinking doing something like this:

<header>
    <title>Forms</title>
    <actions>
        <action ng-click="showNewFormModal()">New Form</action>
        <action ng-click="showHelp()">?</action>
    </actions>
</header>

which would desirably result in

<div class="page-header">
    <div class="left">
        <h3>Forms</h3>
    </div>

    <div class="right">
        <a class="btn btn-default" role="button" ng-click="showNewFormModal()">New Form</a>
        <a class="btn btn-default" role="button">?</a>
    </div>

    <div class="clearfix"></div>
</div>

As you can see, <header> contains custom elements, <title>, <actions>, and <action>, which are specific to only the <header> element.

Is such a thing possible in Angular? How would I accomplish this?

4
  • 2
    Yes, can can do this with directives. You can even create custom attributes and mix them with different custom elements. Have a go through on their directives tutorial. It's kind of amazing how flexible it is. Commented Apr 7, 2014 at 18:53
  • 1
    Yup as rampage says you can do this all with custom directives. I'm working on a similar structure for creating galleries with categories. The next step is to create each of the directives you need and setup the require property to get access the the controllers of other directives. So say header is required by title and actions and then have title and actions call a function on the controller of header to set some properties on the header elements scope, then basically use your original code as the template and fill things in. Commented Apr 7, 2014 at 19:16
  • Just to note as was mentioned in the answer below using header and title might be problematic since these are already HTML tags and so using something a bit more custom with a prefix might make things simpler. If you have trouble working through this provide a plunkr as well and you can get some interactive help. Commented Apr 7, 2014 at 20:21
  • Yeah, definitely. Need to use a prefix. Commented Apr 7, 2014 at 20:41

1 Answer 1

1

See this jsbin I put together which shows how it can be done with custom directives. I had trouble using the names header and title (though I'm almost positive it can be done), for the example, I've user my-header and my-title

Anyways, I've put together the first two elements, the rest will follow the same convention. You can also set up dependencies and scope on each directive, i.e. an action must be inside of an actions parent element

app.directive('myHeader', function() {
  return {
    restrict: "E",
    transclude: true,
    template: "<div class='page-header'><div ng-transclude></div></div>"
  };
});

app.directive('myTitle', function() {
  return {
    restrict: "E",
    transclude: true,
    template: "<div class='left'><div ng-transclude></div></div>"
  };
});

Your HTML will look like:

<my-header>
    <my-title>Forms</my-title>
</my-header>

And the generated HTML will look like:

<my-header>
    <div class="page-header">
        <div ng-transclude="">
            <my-title class="ng-scope">
                <div class="left">
                    <div ng-transclude="">
                        <span class="ng-scope">Forms</span>
                    </div>
                </div>
            </my-title>
        </div>
    </div>
</my-header>
Sign up to request clarification or add additional context in comments.

2 Comments

Would it be wise to also use require '^myHeader' for the myTitle directive? I understand this would require my-title to be inside my-header; see sitepoint.com/practical-guide-angularjs-directives-part-two. Though I could be interpreting the purpose of "require" incorrectly.
If you only ever want to use my-title's in my-header's, then yes, you can reguire: '^myHeader'. This will also give you access to the contoller of the myHeader directive in the fourth parameter of the link function of myTitle, if you so choose to use it.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.