Nikola Brežnjak blog - Tackling software development with a dose of humor
  • Home
  • Daily Thoughts
  • Ionic
  • Stack Overflow
  • Books
  • About me
Home
Daily Thoughts
Ionic
Stack Overflow
Books
About me
  • Home
  • Daily Thoughts
  • Ionic
  • Stack Overflow
  • Books
  • About me
Nikola Brežnjak blog - Tackling software development with a dose of humor
Angular, Stack Overflow

Reference the inputs created with ng-repeat in angular based on the number of variable options

profile for Nikola at Stack Overflow, Q&A for professional and enthusiast programmers
I’m a big fan of Stack Overflow and I tend to contribute regularly (am currently in the top 0.X%). In this category (stackoverflow) of posts I will will be posting my top rated questions and answers. This, btw, is allowed as explained in the meta thread here.

My question was:

The problem I’m facing, as outlined in the code, is that I can’t seem to find out how to bind the second checkboxes (created with ng-repeat) to some model which I would then be able to use further down the code (showing/hiding yet another set of options). Also, I managed to show the additional number of inputs based on the count parameter in the $scope.availableOptions by using the $scope.getItterator function, but now I don’t see how would I access the values of these checkboxes? I know I have to somehow use the option “ng-model” but am failing to do so, so any help appreciated.

My code is here, but am showing it here too:

HTML:

<div ng-controller='MyCtrl'>
    Show additional options <input type="checkbox" ng-model="additionalOptions">
    <div ng-show="additionalOptions">
        <ul>
            <li ng-repeat="option in availableOptions">
                <label class="checkbox" for="opt_{{option.id}}">
                    <input type="checkbox" name="opt_{{option.id}}" id="opt_{{option.}}" />
                    {{option.name}}

                    <ul ng-show="if the upper checkbox is clicked">
                        <li>
                            <input type="text" ng-repeat="i in getItterator(option.count)" ng-model="SOME_VALUE_TO_BE_USED_BELOW"/>
                            Output the value based on what's entered above in the textboxes (SOME_VALUE_TO_BE_USED_BELOW)
                        </li>   
                    </ul>
                </label>
            </li>
        </ul>
    </div>
</div>

and my js:

function MyCtrl($scope) {
    $scope.availableOptions = [{"id":"1","name":"easy","count":"2"},{"id":"2","name":"medium","count":"3"},{"id":"3","name":"hard","count":"2"}];

    $scope.getItterator=function(n){
        var a = new Array();

        for(var i=1; i <= n; i++)
            a.push(i);

        return a;       
    };
}

The answer, by user Khanh TO, was:

Try ng-model="option.checked":

<input type="checkbox" name="opt_{{option.id}}" id="opt_{{option.}}" ng-model="option.checked"/>

And then you can access this property further below like this:

<ul ng-show="option.checked">

DEMO

If you need to also reference the text box inputs. You create a new property (values) on the option. Like this:

{"id":"1","name":"easy","count":"2",values:[]}

Html:

<div ng-repeat="i in getItterator(option.count)">
     <input type="text"  ng-model="option.values[$index]"/>
      {{option.values[$index]}}
</div>

DEMO

Angular

ng-wat is the funniest video about Angular you’ll ever see

ng-wat is the most awesome video I’ve seen presented at any official conference. It was presented by the ever so slightly awesome developer Shai Reznik.

Anyways, take a look and see for yourself, and if promise you, you’ll laugh like hell.

The line I like the most is:

Every time you want to complain, make a pull request instead.

Angular

Angular CodeSchool Notes

Here are my notes from a free CodeSchool tutorial sponsored by Google:

Things I wish I were told about Angular.js.

Binding

<!DOCTYPE html>
<html>
	<head>
		<title>AngularJS Tutorials</title>
	</head>
	<body>
		<div ng-app="">
			<input type="text" ng-model="data.message">
			<h1>{{data.message}}</h1>
		</div>
		<script type="text/javascript" src="angular.js"></script>
	</body>
</html>

Controllers

<html>
	<body>
		<div ng-app="">
			<div ng-controller="FirstCtrl">
				<h1>{{data.message + " world"}}</h1>
				<div class="{{data.message}}">
					Msg...
				</div>
			</div>
		</div>
		<script type="text/javascript" src="angular.js"></script>
		<script type="text/javascript" src="main.js"></script>
	</body>
</html>
//main.js
function FirstCtrl($scope){
$scope.data = {message: "Hello"};
}

Dot

https://www.youtube.com/watch?v=DTx23w4z6Kc

The initial setup:

<div ng-app="">
  <input type="text" ng-model="data.message">
  <h1>{{ data.message }}</h1>

  <div ng-controller="FirstCtrl">
    <input type="text" ng-model="data.message">
    <h1>{{ data.message }}</h1>
  </div>

  <div ng-controller="SecondCtrl">
    <input type="text" ng-model="data.message">
    <h1>{{ data.message }}</h1>
  </div>
</div>
function FirstCtrl($scope) {

}

function SecondCtrl($scope) {

}

In this setup, all three instances of data.message are bound to each other through the first data.message, which is in the scope of the entire application.

If we were to replace the instances of data.message with just message,

<div ng-app="">
  <input type="text" ng-model="message">
  <h1>{{ message }}</h1>

  <div ng-controller="FirstCtrl">
    <input type="text" ng-model="message">
    <h1>{{ message }}</h1>
  </div>

  <div ng-controller="SecondCtrl">
    <input type="text" ng-model="message">
    <h1>{{ message }}</h1>
  </div>
</div>

It breaks the scope inheritance that was binding all the data.message instances. Now, each new ng-model of message is creating a new instance of message, and so each model will be an unbound instance. So, important to note here is the data.message which will be available to all of the controllers!

Sharing data between controllers

https://www.youtube.com/watch?v=HXpHV5gWgyk

The initial setup:

<div ng-app="">
  <input type="text" ng-model="data.message">
  <h1>{{ data.message }}</h1>

  <div ng-controller="FirstCtrl">
    <input type="text" ng-model="data.message">
    <h1>{{ data.message }}</h1>
  </div>

  <div ng-controller="SecondCtrl">
    <input type="text" ng-model="data.message">
    <h1>{{ data.message }}</h1>
  </div>
</div>
function FirstCtrl($scope) {

}

function SecondCtrl($scope) {

}

With this setup, data.message is defined outside of either controller, scoped to the entire ng-app. The bindings within each of the controller divs both point to that ‘parent’ model. Because of this, all 3 instances of the data.message input are bound to each other because of the first instance, which is globally scoped in the application.

If one were to remove the first model that does not reside in a controller, there is no parent model for either controller to bind to, so each instance of data.message will be scoped within its respective controller. Thus, neither data.message will be bound to the other.

We’d like to share the data model between the two controllers without creating a parent scope. This requires a service within a formally defined Angular application.

<div ng-app="myApp">

  <div ng-controller="FirstCtrl">
var myApp = angular.module('myApp', []);

myApp.factory('Data', function () {
  return { message: "I'm data from a service" };
});

function FirstCtrl($scope) {

This Data service can be injected into each of the controllers as a parameter. By doing this, we are now attaching the data.model to an app service, which repairs the binding between the two controller models.

Stackoverflow thread on this.

<!DOCTYPE html>
<html>
<head>
	<title></title>
</head>
<body ng-app="myApp">
	<div ng-controller="FirstCtrl">
		<input type="text" ng-model="data.message">
		<h1>{{ data.message }}</h1>
	</div>

	<div ng-controller="SecondCtrl">
		<input type="text" ng-model="data.message">
		<h1>{{ data.message }}</h1>
	</div>
	
	<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.min.js"></script>
	<script type="text/javascript" charset="utf-8">
		angular.module('myApp', [])

		.factory('Data', function () {
		  return { message: "I'm data from a service" };
		})

		.controller('FirstCtrl', function ($scope, Data){
			$scope.data = Data;
		})

		.controller('SecondCtrl', function ($scope, Data){
			$scope.data = Data;
		});
	</script>
</body>
</html>

Method on a scope

function SecondCtrl($scope, Data) {
  $scope.data = Data;

  $scope.reversedMessage = function() {
    return $scope.data.message.split("").reverse().join("");
  };
}

Bootstraping https://docs.angularjs.org/guide/bootstrap

Changing the data in the service and then showing it again, the ultimate example which eluded me for some time (Plunkr):

<!DOCTYPE html>
<html>
<head>
	<title></title>
</head>
<body ng-app="myApp">
	<div ng-controller="FirstCtrl">
		<input type="text" ng-model="data.msg">
		<h1>{{ data.msg }}</h1>

		<button type="" ng-click="sayItBack()"></button>
	</div>

	<div ng-controller="SecondCtrl">
		<input type="text" ng-model="data.msg">
		<h1>{{ data.msg }}</h1>
	</div>
	
	<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.min.js"></script>
	<script type="text/javascript" charset="utf-8">
		angular.module('myApp', [])

		.service('Data', function () {
			this.data = {};
			this.data.msg = "Howdy!";

			this.getMsg = function() {
			    return this.data;
			};

			this.setMsg = function(city){
				this.data.msg = city;
			};
		})

		.controller('FirstCtrl', function ($scope, Data){
			$scope.data = Data.getMsg();

			$scope.sayItBack = function(){
				Data.setMsg("Hello to you too!");
			}			
		})

		.controller('SecondCtrl', function ($scope, Data){
			$scope.data = Data.getMsg();
		});
	</script>
</body>
</html>
Angular

Speeding up Angular development with Yeoman

Yeoman helps you to kickstart new projects, prescribing best practices and tools to help you stay productive.

To do so, we provide a generator ecosystem. A generator is basically a plugin that can be run with the `yo` command to scaffold complete projects or useful parts…

First, install Yeoman with npm:

npm install yo -g

Now you need a “generator”, and most likely you’ll need grunt:

npm install -g generator-angular grunt

If you get the error like The package generator-karma does not satisfy its siblings’ peerDependencies requirements then try uninstalling generator-karma:

npm uninstall -g generator-karma

and running the previous npm install command again.

Btw,  you can use Yeoman’s CLI (by first executing yo) to search and install any of the existing generators.

To scaffold a new app, create some folder and execute the following command:

yo angular myApp

Yeoman will ask you few questions to which you can all give a default answer and it will start the installation process. After the installation is done you can do:

grunt serve

to actually see a live preview of your scaffolded app.

If you get an error like Warning: Couldn’t find the `compass` binary. Make sure it’s installed and in your $PATH Use –force to continue install it with (if you’re on Mac):

sudo gem install compass

Additional cool thing is that this generator comes with extra tools for quick scaffolding of routes, controllers, views, directives, services, filters… Be sure to check the project on GitHub for more info.

For example, the following command generates a controller and a view, and configures a route in app/scripts/app.js connecting them.

yo angular:route myroute

 

Recent posts

  • Discipline is also a talent
  • Play for the fun of it
  • The importance of failing
  • A fresh start
  • Perseverance

Categories

  • Android (3)
  • Books (114)
    • Programming (22)
  • CodeProject (35)
  • Daily Thoughts (77)
  • Go (3)
  • iOS (5)
  • JavaScript (127)
    • Angular (4)
    • Angular 2 (3)
    • Ionic (61)
    • Ionic2 (2)
    • Ionic3 (8)
    • MEAN (3)
    • NodeJS (27)
    • Phaser (1)
    • React (1)
    • Three.js (1)
    • Vue.js (2)
  • Leadership (1)
  • Meetups (8)
  • Miscellaneou$ (77)
    • Breaking News (8)
    • CodeSchool (2)
    • Hacker Games (3)
    • Pluralsight (7)
    • Projects (2)
    • Sublime Text (2)
  • PHP (6)
  • Quick tips (40)
  • Servers (8)
    • Heroku (1)
    • Linux (3)
  • Stack Overflow (81)
  • Unity3D (9)
  • Windows (8)
    • C# (2)
    • WPF (3)
  • Wordpress (2)

"There's no short-term solution for a long-term result." ~ Greg Plitt

"Everything around you that you call life was made up by people that were no smarter than you." ~ S. Jobs

"Hard work beats talent when talent doesn't work hard." ~ Tim Notke

© since 2016 - Nikola Brežnjak