0

I have data being added in through a json feed and that data goes through a filter to tidy it up / add some extra elements which all works fine. However I've added a new filter to find images and add ng-click to the markup to do full screen modal images, annoyingly the click event never fires.

 .filter('html_filters', function ($sce) {
        return function (text) {
            var htmlObject = document.createElement('div');
            htmlObject.innerHTML = text;

            var imgs = htmlObject.getElementsByTagName('img');
            for (var i = 0; i < imgs.length; i++) {
                var link = imgs[i].getAttribute('src');
                imgs[i].setAttribute('ng-click', 'loadImage("' + link + '")');
            }

            return $sce.trustAsHtml(htmlObject.outerHTML);
        }
    })

HTML:

<p class="postcon arrow-list" ng-if="content" ng-bind-html="content | html_filters"></p>

Rendered HTML:

<img class="aligncenter" src="http://www.sdssdsdsdsd.co.uk/connect/wp-content/uploads/2016/08/sdsdsd-August-20162-1.jpg" alt="Exhibit 1" ng-click="loadImage(&quot;http://www.sdssdsdsdsd.co.uk/connect/wp-content/uploads/2016/08/sdsdsd-August-20162-1.jpg&quot;)">

Click Event:

 $scope.loadImage = function (url) {
        console.log("Loading Image");
    }

That log event never fires

MissCoder87
  • 2,669
  • 10
  • 47
  • 82
  • 1
    This job must be done using Directives and not Filters. Any DOM creation/updation/deletion using data must be handled using directives. – Harsh Gupta Dec 06 '16 at 11:35
  • As stated DOM manipulation are for the directives to do and to bind dynamically created HTML you will also need to use `$compile`, you can [check this question](http://stackoverflow.com/questions/19267979/ng-click-not-working-from-dynamically-generated-html) for an example. – GillesC Dec 06 '16 at 11:37
  • You also seem to have an encoding issue `"` instead of proper quote would generate more error when the click handler try to run. – GillesC Dec 06 '16 at 11:38

1 Answers1

0

DOM manipulation should be done inside a directive and not a filter. You can still use a filter inside a directive and leverage the compile phase which will cause your html to be rendered correctly with events and everything.

here is a good explanation of their difference and how to use them:

http://www.c-sharpcorner.com/UploadFile/cd7c2e/directive-and-filter-service-in-angularjs/

UPDATE:

Alright let's make this a bit simpler by looking at your problem from a different angel.

What you are trying to do is iterate over a list of objects you are getting from your json feed and create a bunch of html elements (p and img and ...).

I am going to write this using an ng-repeat (which is a directive right?):

<div ng-repeat="content in jsonList">
    <p class="postcon arrow-list" ng-if="content" ng-bind="content.text"></p>
    <img class="aligncenter" ng-src="content.url" alt="{{contnt.alt}}" ng-click="loadImage(content.url)">
</div>

So now we have our list of elements when the page is rendered. So what happens to your tidying up logic here. Now is the time to look at filters. Let's suppose you have a filter like below which gets your list and returns the tided up one:

app.filter('myFilter', function () {
   return function (jsonList) {
     var modifiedList = [];
     //your logic goes here
     return;
   };
});

Now if you want to use this to modify your initial array before parsing the html you can use it like this (by adding it as a filter after your ng-repeat):

<div ng-repeat="content in jsonList | myFilter">

Hope this makes since.

BTW: I didn't want you to change your logic or anything. This is just to let you know the differences and where to use each of them.

Yaser
  • 5,609
  • 1
  • 15
  • 27
  • Sorry I don't quite understand, I get the logic but I don't understand how I would replace a filter with a directive, or use them side by side? – MissCoder87 Dec 06 '16 at 11:49