Programmatically link an Angular JS model to a template using binding

When given an HTML template like the following:

<div class="info">
    <div class="title"><a href="property-detail.html">{{title}}</a></div>
    <div class="location">{{location}}</div>
    <div class="property-info clearfix">
        <div class="area"><i class="icon icon-normal-cursor-scale-up"></i>{{size}}<sup>2</sup></div>
        <div class="bedrooms"><i class="icon icon-normal-bed"></i>{{bedrooms}}</div>
        <div class="bathrooms"><i class="icon icon-normal-shower"></i>{{bathrooms}}</div>
    </div><div class="price">{{price}}</div>
    <div class="link">
        <a href="{{details}}">View more</a>
    </div>
</div>

If there is a model that aligns with this template (containing fields such as title, location, price, etc.), the goal is to dynamically bind the template to the model and store the rendered results in an array. A possible approach could be expressed using pseudo-code similar to the following:

var boxes= [];
 for (var i = 0; i < items.length; i++) {
    var results = bind(template, items[i]);
    boxes.push(results);
}

In this example, 'items' represents an array of data obtained from a database or another source, while 'bind' is a function responsible for populating the template with the corresponding model data.

An ideal solution might involve utilizing a directive, although the implementation details may require further exploration.

Is there a way to achieve this functionality using Angular? Any insights would be appreciated.

Answer №1

Typically, it's advised to avoid manipulating the DOM outside of a directive. However, there are times when flexibility trumps strict rules. If you find yourself needing a compiled template in string format (perhaps for third-party widget integration), you can create a service like the one below:

angular.module('app', []); 
angular.module('app').controller('MainCtrl', function ($scope, templateCompiler) { 
  var boxes = []; 
  var data = [{ 
      title: 'test', 
      location: 'location!', 
      size: 40, 
      bedrooms: 'yes', 
      bathrooms: 'uncertain', 
      price: 'if you have to ask...', 
      details: 'indeterminate' 
  },{ 
      title: 'test2', 
      location: 'somewhere', 
      size: 'a woman never tells', 
      bedrooms: 3.14, 
      bathrooms: null, 
      price: 1400, 
      details: 'forthcoming' 
  }]; 

  for (var i = 0; i < data.length; i++) { 
    var results = templateCompiler.bind(data[i]); 
    boxes.push(results); 
  } 
  
  $scope.boxes = boxes; 
}) 

angular.module('app').service('templateCompiler', function ($compile, $templateCache, $rootScope) { 
  var service = {} 
  var template = $templateCache.get('boxTemplate'); 
  var scope; 
   
  this.bind = function (data) { 
    scope = $rootScope.$new(); 
    angular.extend(scope, data); 
    var link = $compile(template); 
    var content = link(scope); 
    scope.$apply(); 
    return content.html(); 
  };  
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.22/angular.min.js"></script>
 
<div ng-app='app'> 
 
  <script type="text/ng-template" id="boxTemplate"> 
    <div class="info"> 
        <div class="title"><a href="property-detail.html">{{title}}</a></div> 
        <div class="location">{{location}}</div> 
        <div class="property-info clearfix"> 
            <div class="area"><i class="icon icon-normal-cursor-scale-up"></i>{{size}}<sup>2</sup></div> 
            <div class="bedrooms"><i class="icon icon-normal-bed"></i>{{bedrooms}}</div> 
            <div class="bathrooms"><i class="icon icon-normal-shower"></i>{{bathrooms}}</div> 
        </div><div class="price">{{price}}</div> 
        <div class="link"> 
            <a href="{{details}}">View more</a>  
    </div> 
  </div></script> 
 
  <!-- TO PROVE YOU GET THE DESIRED OUTPUT --> 
  <div ng-controller="MainCtrl">{{boxes}}</div> 
</div>

Additionally, it may be worth considering encapsulating your map widget within a directive.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Using Vue and vue-multiselect to create interactive options based on the selected language

I'm currently developing a Vue website with multilingual support. The chosen language is stored in a Vuex store and accessed through the computed property lang, like so: lang(){ return this.$store.state.lang } I use this lang property in v-if cond ...

Developing an uncomplicated Angular promise following the invocation of a service

Delving into the realm of Angular promises for the first time, I'm determined to grasp its concepts. In my MainController, I have a simple authentication process using myAuthSrv.authUser with a username and password. Upon successful authentication (. ...

Exploring the process of transforming a dynamic PDF into a static PDF using PHP or NodeJS

Issue I am looking for a PHP/NodeJS API that can convert editable PDF files to non-editable PDFs online. Our client application requires the user to download PDF files that cannot be modified using software like Foxit Reader or Adobe. We are currently us ...

The Selenium driver's execute_script method yields no result

One of the tasks I have is to determine if a specific element is within view. If it is, I want the script to return True; otherwise, False: driver.execute_script('window.pageYOffset + document.querySelector(arguments[0]).getBoundingClientRect().bottom ...

Display a confirmation modal before triggering $routeChangeStart in AngularJs, similar to the window.onbeforeunload event

When a user chooses to stay on the page as the route starts to change, the original route remains intact but the form directives are reloaded. This results in the loss of all checkbox and input values, resetting them to their defaults. If a user closes th ...

Default close x button not functioning to close modal dialog

When I click the [X] button in my modal dialog box, it doesn't close. Here is an example of my code: $('#apply_Compensation_Leave').show(); This is the modal code: <div class="modal" id="apply_Compensation_Leave" tabindex="-1" role="di ...

Is it possible to combine asynchronous and synchronous functions in the same code?

I've recently started experimenting with Node.js and I'm running into issues with asynchronous functions. While I was able to create a small game, the only way I could successfully integrate asynchronous functions with synchronous functions was b ...

What is the reason for the excessive width of the final column in this table?

I am currently working with a dataset that I am displaying using the handsontable library in the form of a table. One issue I am facing is that the last column of my table appears too wide even though I did not specify any width for it. Below you can see t ...

Tips for effectively invoking a method in a Vue component

As a Vue2 beginner, I am currently working with the Vue CLI and following the structure generated from it. My goal is to submit form data, but I keep encountering a warning and error: [Vue warn]: Property or method "onSubmit" is not defined on the insta ...

What is the best way to forward a file upload request from a Next.js API to another API?

Trying to crop an image within a Next.js application, then sending it through an API route within the app before reaching an external API endpoint is proving to be a challenge. The process works fine without going through the API route, but once that step ...

Tips on modifying the maxlength attributes for all "field answer" class elements

Looking for some help with adjusting the "maxlength" attribute in a class called "field answer." The current maxlength is set to 250, but I need it changed to 9999. Can someone guide me through this process? <div class="field answer"> &l ...

Error message: "An issue occurred: Unable to access undefined properties (specifically, borderRadius) in MUI react."

I recently created a navigation bar with an integrated search bar component. The styling for my search component was done using MUI styled from @emotion/styled in MUI library, where I applied a borderRadius: theme.shape.borderRadius. However, I encountere ...

How can I turn off credential suggestions in a React JS application?

Is there a way to disable managed credential suggestion on a React JS web page using a browser? I have tried using the autoComplete=off attribute and setting editable mode with an onFocus event, but the password suggestions are still appearing. Any help wo ...

Exclude items from AngularJS watch list

Is there a way to manually run a digest loop on specifically selected watches? Take, for example, the scenario where I need a directive that constantly displays the current time (including seconds), but without triggering the digest loop every second. One ...

When an item in the accordion is clicked, the modal's left side scroll bar automatically scrolls to the top. Is there a solution to prevent this behavior and

When I first load the page and click on the Sales accordion, then proceed to click on Total reported and forecasted sales, the scrollbar jumps back up to the top The marked ng-container is specifically for the UI of Total reported and forecasted sales He ...

Is there a way in AngularJS to trigger an event at a designated time?

I recently developed a webpage using AngularJS. I am looking to trigger certain actions on my webpage within a specified timeframe. For instance, If it is 2016-01-07 11:00:00, I want ng-show to execute some action. I am utilizing the Angular-timer for ...

Update the input value following a successful action

How can I update the value of an input field after a successful ajax call? I have tried the following approach but it doesn't seem to be working. The result from the alert is 80000 Here is the HTML input code: <input class="form-control" type=" ...

The error message "Error: 'x' is not a defined function or its output is not iterable"

While experimenting, I accidentally discovered that the following code snippet causes an error in V8 (Chrome, Node.js, etc): for (let val of Symbol()) { /*...*/ } TypeError: Symbol is not a function or its return value is not iterable I also found out ...

Find the JavaScript code that selects the previous value chosen

When working with a select in React, I am facing an issue where the console.log is returning the last value selected instead of the current one. For instance, if I select 4 followed by 3 and then 5, the code will display 1 (default value), then 4, and fin ...

An unspecified number of Ajax requests being made within a loop

Here is the dilemma I'm facing, despite trying different recommendations from StackOverflow: Situation: I am utilizing the Gitlab API to display all the "issues" in the bug tracker of a specific project on the system. Challenges: Everything wor ...