I am trying to make items not in list but in div and if an item is clicked, the div will be in different colors and the item will be added into a column but if the item is clicked again, the item will changed to original color and in the column the item will be gone. I just can't think how to do it in angular way. I came to another option to be able to add in the column and to remove the item, there's a remove button but I am still curious how the select and deselect can be done.
This is what I have in my html (ignore my btn btn-primary classes I was using button to give it a try in the first place)
<!--Select App Features-->
<div class="panel-heading" ng-controller="FeaturesController as featuresCtrl">
<h1 class="text-center">App Features</h1>
<div class="text-center">
<div ng-repeat="app in featuresCtrl.apps" class="btn btn-primary platform-btn-style" ng-click="featuresCtrl.addPrices(app.name, app.price)">{{ app.name }}</div><br>
</div>
<div>
<table class="table table-striped table-hover">
<thead>
<tr>
<th>Device Added</th>
<th>Device Price</th>
<th></th>
</tr>
</thead>
<tr ng-repeat="appList in featuresCtrl.listAppPrices">
<td>{{ appList.name }}</td>
<td>{{ appList.price }}</td>
<td><button class="btn btn-default" ng-click="featuresCtrl.remove($index)">Remove</button></td>
</tr>
</table>
<div>Total : {{ featuresCtrl.totalAppPrice() }}</div>
</div>
</div><!-- end select app features / FeaturesController-->
My controller in js
//Controller for app features
app.controller("FeaturesController", function(){
this.apps = features;
this.listAppPrices = [];
// add name and price into the new array which is used to show in the table
this.addPrices = function(name, price){
//Checks if the exact name, price property exists in the array and return boolean
var found = this.listAppPrices.some(function (e){
console.log(e.name);
return ((e.name === name) && (e.price === price)) ;
});
//If found not true then push the new values into the array
if(!found){
this.listAppPrices.push({name: name, price: price});
}
};
// adds all the prices of the array which gives the total
this.totalAppPrice = function(){
var total = 0;
for(var i = 0; i < this.listAppPrices.length; i++){
total += this.listAppPrices[i].price;
}
return total;
};
// remove the whole object in the array when remove is clicked
this.remove = function(index) {
this.listAppPrices.splice(index, 1);
};
});
I kind of having the idea of how this can be done but I just can't think of the code to write it.
P.S. the codes are simple, I just learned it in code school and wanted to created something for fun to educate myself. Thanks in advance people
angular.module("stack", [])
.controller("FeaturesController", function($scope) {
// this.apps = features;
this.listAppPrices = [];
this.apps = [{ "name": "a1", "price": "12" }, { "name": "a2", "price": "13" }, { "name": "a3", "price": "14" }];
$scope.dummyArray = [];
var f = 0,
x = 0,
rem = false;
this.setSelected = function(app, index) {
console.log("app ", app);
//remove an item
if (app.selected) {
console.log(" list ", $scope.dummyArray);
$scope.dummyArray.forEach(function(e, ind) {
if (e.name === app.name) {
console.log(ind, " e ", e);
rem = true;
$scope.dummyArray.splice(ind, 1);
}
});
console.log("dumm ", $scope.dummyArray);
this.listAppPrices = $scope.dummyArray;
} else {
rem = false;
}
//used to select a div and change its colour
app.selected ? app.selected = false : app.selected = true;
//add an item
if (!rem) {
if ($scope.dummyArray.length) {
$scope.dummyArray.forEach(function(each) {
console.log("each ");
if (each.name !== app.name) {
console.log("inside if ");
f = 1;
}
});
} else {
console.log("inside else ");
$scope.dummyArray.push(app);
}
if (f === 1) {
f = 0;
console.log("push");
$scope.dummyArray.push(app);
}
console.log(" list--> ", $scope.dummyArray.length);
this.listAppPrices = $scope.dummyArray;
}
}
});
.selected {
background-color: gray;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0-rc.0/angular.min.js"></script>
<!DOCTYPE html>
<html ng-app="stack">
<head>
<title>stack</title>
<link rel="stylesheet" type="text/css" href="style.css">
</head>
<body>
<div class="panel-heading" ng-controller="FeaturesController as featuresCtrl">
<h1 class="text-center x">App Features</h1>
<div class="text-center">
<div ng-repeat="app in featuresCtrl.apps track by $index" class="btn btn-primary platform-btn-style" ng-click="featuresCtrl.setSelected(app,$index)" ng-class="{selected: app.selected}">{{ app.name }}</div>
<!-- <div ng-if="(c%2===0)" ng-repeat="app in featuresCtrl.apps" class="btn btn-primary platform-btn-style" ng-click="featuresCtrl.setSelected(app)">{{ app.name }}</div> -->
<br>
</div>
<div>
<table class="table table-striped table-hover">
<thead>
<tr>
<th>Device Added</th>
<th>Device Price</th>
<th></th>
</tr>
</thead>
<tr ng-repeat="appList in featuresCtrl.listAppPrices">
<td>{{ appList.name }}</td>
<td>{{ appList.price }}</td>
<td>
<button class="btn btn-default" ng-click="featuresCtrl.remove($index)">Remove</button>
</td>
</tr>
</table>
<div>Total : {{ featuresCtrl.totalAppPrice() }}</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0-rc.0/angular.min.js"></script>
<script type="text/javascript" src="controller.js"></script>
</body>
</html>
I haven't added the functionality of remove button.I also haven't count the totalAppPrice. Otherwise your problem is solved :) .
Related
First I must say that I'm a complete newbie in coding and Vue it's the first framework I'm learning and I'm terrible working with arrays at the moment. In the practice I am doing I am displaying the first five elements of the array in a table (I've filtered them in a new variable to do the v-for).
Now I need to add a button that when clicked will show me a new row of the original array, but I'm a bit stuck on how to do it. As u may see in the code below, contactList is the variable that has all the data, but I have no clue how to link it to the filtered one to show more data when clicked.
<template>
<h1 class="display-1 text-primary">Contacts</h1>
<button type="button" class="btn btn-outline-primary btn-lg" #click="addRandom">Add random</button>
<div class="container container__pos">
<table class="table table-hover">
<thead>
<tr>
<th class="col col__style">Picture</th>
<th class="col col__style">Name</th>
<th class="col col__style">Popularity</th>
<th class="col col__style">Won an Oscar</th>
<th class="col col__style">Won an Emmy</th>
</tr>
</thead>
<tbody>
<tr v-for="(element, index) of contactListed" :key="index">
<td scope="row">
<img
:src="element.pictureUrl"
:alt="element.name + ` image`"
class="image"
/>
</td>
<td> {{ element.name }}</td>
<td>{{ element.popularity }}</td>
<td>{{ wonAward(element.wonOscar) }}</td>
<td>{{ wonAward(element.wonEmmy) }}</td>
</tr>
</tbody>
</table>
</div>
</template>
<script>
import contacts from "./contacts.json";
export default {
data() {
return {
contactList: contacts,
contactListed: contacts.slice(0, 5),
};
},
methods: {
wonAward(element) {
if (element === true || element === true){
return "winner";
} else {
return "";
}
},
},
};
</script>
You can use a computed variable that holds the first N elements of the array, and have your button increment the value of N, like this:
<script>
import contacts from "./contacts.json";
export default {
data() {
return {
contactList: contacts,
nItems: 5
};
},
computed: {
contactListed() {
return this.contacts.slice(0, this.nItems)
}
},
methods: {
addRow() {
this.nItems++;
},
wonAward(element) {
if (element === true || element === true){
return "winner";
} else {
return "";
}
},
},
};
</script>
<template>
...
<button #click="addRow()" />
</template>
For creating table I am using ng-repeat to render table row. onchange of dropdown I am calling a function which will run have some conditions on basis of that condition I am pushing an object to an array which bind to a scope variable.
My HTML
<div class="col-md-12" >
<div class="portlet light" >
<div class="portlet-title">
<div class="caption">Installment Structure </div>
</div>
<div class="portlet-body">
<div class="row">
<div class="col-md-12">
<table id="instalmentStructure" class="table table-bordered">
<tbody>
<tr>
<th style="width:20%;">From Installment
</th>
<th style="width:20%;">To Installment</th>
<th style="width:20%;">Installment Amount
</th>
<th style="width:20%;"></th>
</tr>
<tr class="quoteVal" ng-repeat="item in installmentLists">
<td >{{item.fromInst}}</td>
<td >{{item.toInst}}</td>
<td contenteditable="true" class="quoteVal">{{item.amtInst}}</td>
<td>
<span class="col-md-6">
<center>
<a ng-click="editRecord(item,$index)">
<i class="fa fa-pencil"></i>
</a>
</center>
</span>
<span class="col-md-6">
<center>
<a ng-click="deleteRecord(item,$index)">
<i class="fa fa-trash"></i>
</a>
</center>
</span>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
</div>
My Controller Code:
$scope.createInstallments = function () {
console.log("will create installments");
if (trialCalculCntrl.emiCalQde.bulletFreq == 12) {
console.log("Bullet Frequency is Yearly");
var bulletFreq = trialCalculCntrl.emiCalQde.bulletFreq;
$scope.installmentLists = [];
$scope.installmentObj = {
'fromInst': "",
'toInst': "",
'amtInst': ""
};
var remainder = tenure % 12;
if (remainder == 0) {
var numofrows = ((tenure * 2) / 12).toFixed(0);
for (var i = 1; i <= numofrows; i++) {
if (i == 1) {
$scope.installmentObj = {
'fromInst': i,
'toInst': bulletFreq - 1,
'amtInst': ""
};
$scope.installmentLists.push($scope.installmentObj);
} else if (i % 2 == 0) {
console.log("EVEN i: ", i);
var preval = $('tr.quoteVal').eq(i - 2).find('td:eq(1)').text();
console.log("Previous Val ", preval);
} else {
console.log("ODD i: ", i);
// var preval = $('tr.quoteVal').eq(i-1).find('td:eq(2)').text();
// console.log("Previous Val ",preval);
}
}
console.log("Instalment list : ", $scope.installmentLists);
} else {
var numofrows = (((tenure * 2) / 12) + 1).toFixed(0);
for (var i = 0; i < numofrows; i++) {
$scope.installmentObj = {
'fromInst': "",
'toInst': "",
'amtInst': ""
};
$scope.installmentLists.push($scope.installmentObj);
}
console.log("Instalment list : ", $scope.installmentLists);
}
}
};
Inside for loop after first run I am pushing the object to $scope.installmentLists array but it is not showing in to HTML so I am not able to read the array object in second run of for loop. I am using jQuery selectors to read, so console.log("Previous Val ", preval); gives me an empty string.
Place your jquery about console.log in setTimeout when changed $scope. Otherwise the jquery selector does not return expected because the HTML has not been rendered.
setTimeout(function() {
onsole.log("EVEN i: ", i);
var preval = $('tr.quoteVal').eq(i - 2).find('td:eq(1)').text();
console.log("Previous Val ", preval);
}, 500);
I'm trying display list of institutions from my API, where I want to display only 10 and when load more button is clicked it should display remaining and load more button contain nextpage url i.e., remaining list in json format
html code is as follows
<div class="container text-center">
<h1 class="text-center">Existing Institutions </h1>
<div class="row row-centered">
<div class="col-md-10 col-md-offset-1">
<div class="col-md-12">
<div class="table-responsive">
<table id="claimList" class="table table-bordered table-hover table-striped tablesorter">
<thead>
<tr>
<th class="header"> Institute Name <i class="icon-sort"></i></th>
<th class="header"> Address <i class="icon-sort"></i></th>
<th class="header"> Location <i class="icon-sort"></i></th>
</tr>
</thead>
<tbody>
{% for key in data %}
<tr>
<td>{{ key.displayName }}</td>
<td>{{ key.businessAddress }}</td>
<td>{{ key.businessLocation }}</td>
</tr>
{% endfor %}
</tbody>
</table>
<ul class="pager">
<li class="next"><button name="load_more" id="load_more" onsubmit="loadMore({{ nextPage }});">Load More</button></li>
</ul>
</div>
</div>
</div>
</div>
</div>
my ajax code is
function loadMore(url) {
alert(url);
$.ajax({
dataType: "json",
url: url,
success: function (data) {
alert(data);
var table = document.getElementById("claimList");
for (var i=0; i < data.length; i++) {
var row = table.insertRow(-1);
var cell1 = row.insertCell(0);
var cell2 = row.insertCell(1);
var cell3 = row.insertCell(2);
cell3.style.width = '25px';
cell1.innerHTML = '<td>{{ data.displayName }}</td>';
cell2.innerHTML = '<td>{{ data.businessAddress }}</td>';
cell3.innerHTML = '<td>{{ data.businessLocation }}</td>';
}
},
error: function (request, error) {
console.log(arguments);
alert(" Can't load more because " + error);
},
});
}
i'm getting the data which resides in data. now how to parse data and display in the html table
data table integration
put it in HTML make sure jquery is added.
https://cdn.datatables.net/1.10.13/css/jquery.dataTables.min.css
https://cdn.datatables.net/1.10.13/js/jquery.dataTables.min.js
<table class="table table-bordered table-condensed details">
<input type="hidden" name="data_source_url" value="{% url'institutions'%}"
<thead>
<tr>
<th class="header"> Institute Name <i class="icon-sort"></i></th>
<th class="header"> Address <i class="icon-sort"></i></th>
<th class="header"> Location <i class="icon-sort"></i></th>
</tr>
</thead>
<tbody>
</tbody>
</table>
javascript:
$(document).ready(function() {
$("a.toggle_hidden_details").on("click", function(e) {
var top_div = $(this).closest('div.td_details');
var hidden_div = top_div.find('div.hidden_details');
var icon = top_div.find('i')
if (hidden_div.is(':visible')) {
hidden_div.slideUp();
icon.removeClass('icon-minus');
icon.addClass('icon-plus');
} else {
hidden_div.slideDown();
icon.removeClass('icon-plus');
icon.addClass('icon-minus');
}
});
if ($("input[name='data_source_url']").length > 0) {
var source = $("input[name='data_source_url']").val();
$('table.admin_details').dataTable({
"bProcessing": true,
"bServerSide": true,
"sAjaxSource": source
});
} else {
$('table.details').dataTable();
}
datatable integration in views.py make sure have added the urls for this.
import json
def issue_history_data(request):
search = request.GET.get("sSearch")
institutions = MODEL_NAME.objects.all()
institutions_list = list(set(institutions))
# ordering
sort_column = int(request.GET.get("iSortCol_0"))
sort_dir = request.GET.get("sSortDir_0")
# page filter
start = request.GET.get("iDisplayStart")
length = request.GET.get("iDisplayLength")
instituties = institutions_list
if length != -1:
page = int(start) // int(length) + 1 if start else 1
paginator = Paginator(institutions_list, length)
issues = paginator.page(page)
institutionsData = []
for insti in instituties:
try:
institutionsData.append([
'name',
insti.businessAddress,
insti.businessLocation,
])
except Exception as e:
log.debug('possible bad issue' + str(issue.pk), exc_info=True)
returnDict = {
"sEcho": request.GET.get("sEcho"),
"iTotalRecords": len(institutions_list),
"iTotalDisplayRecords": len(institutions_list),
"aaData": institutionsData
}
return HttpResponse(json.dumps(returnDict))
If you want to load content on the go, you should use AJAX, and since you're using jQuery, you can use jQuery.getJSON(URL, callback).
function loadMore(page) {
// This is assuming that your data is at the specified path
// you should edit it to fit your needs.
$.getJSON('/path/to/data?page=' + page, function (data) {
/* Process the data */
});
}
I am trying to use a Factory Service function in my app to add a movie to my list. I have been able to remove a movie from the list, but I am having trouble figuring out why I can't add a movie to the current list.
var app = angular.module('application', []);
app.factory("MoviesService",[function(){
var movies = [
{title:"Avengers: Age of Ultron",rating:"PG-13",year:"2015"},
{title:"Ant-Man",rating:"PG-13",year:"2015"},
{title:"The Martian",rating:"PG-13",year:"2015"},
{title:"San Andreas",rating:"PG-13",year:"2015"},
{title:"Jurassic Park",rating:"PG-13",year:"2015"},
{title:"Dope",rating:"PG-13",year:"2015"}
];
var factory = {};
factory.getMovies = function(){
return movies;
};
factory.addMovie = function(){
var newMovie = {
title: movie.title,
rating: movie.rating,
year: movie.year
}
movies.push(newMovie);
};
factory.removeMovie = function(movie){
var index = movies.indexOf(movie);
movies.splice(index,1);
};
return factory;
}]);
app.controller('CustomerController',['$scope','MoviesService',function($scope,MoviesService){
$scope.movies = MoviesService.getMovies();
$scope.removeMovie = function(movie){
MoviesService.removeMovie();
};
$scope.addMovie = function(){
MoviesService.addMovie();
}
<link href="http://maxcdn.bootstrapcdn.com/bootstrap/3.3.1/css/bootstrap.min.css" rel="stylesheet"/>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<body ng-app = "application">
<div class = "row">
<div class = "col-md-12" ng-controller = "CustomerController">
<table class="table">
<caption>Optional table caption.</caption>
<thead>
<tr>
<th>#</th>
<th>Title</th>
<th>Year</th>
<th>Rating</th>
<th>Options</th>
</tr>
<tr>
<th>Add</th>
<th><input ng-model="movie.title" class="form-control"></th>
<th><input ng-model="movie.year" class="form-control"></th>
<th><input ng-model="movie.rating" class="form-control"></th>
<th>
<button class = "btn btn-success" ng-click="addMovie()"><span class = "glyphicon glyphicon-plus"></span></button>
</th>
</tr>
</thead>
<tbody>
<tr ng-repeat = "movie in movies">
<th scope="row">{{$index}}</th>
<td>{{movie.title}}</td>
<td>{{movie.year}}</td>
<td>{{movie.rating}}</td>
<td>
<button ng-click="removeMovie(movie)" class="btn btn-danger">
<span class="glyphicon glyphicon-remove"></span>
</button>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</body>
First off, your addMovie function doesn't have access to movie, so it's probably throwing an error in the console. Change this:
factory.addMovie = function(){
to
factory.addMovie = function(movie) {
and change this:
$scope.addMovie = function(){
MoviesService.addMovie();
}
to:
$scope.addMovie = function() {
MoviesService.addMovie($scope.movie);
}
always pay attention to console errors. I made a working plunker of this in action:
http://plnkr.co/edit/AXNhovhKrW24FLOt9KGM?p=preview
Inside your addMovie function, you trying to add a movie from a movie variable that does not exist in this context. So you are probably getting an error there.
It looks like you're trying to do something like:
$scope.movie = {}; // add this
$scope.addMovie = addMovie; // modify to this
...
factory.addMovie = function(movie){ // add parameter movie
movies.push(movie);
};
...
give that a shot.
First, I have this table:
Where you can see, different colours in the column estado. There are 4 different cases. And i Want to count this different cases. For example in this case there are: Active(green): 1, Vodafone(green+logo): 1, Desactive(Red): 1, Pending(orange):1. But it can change depend of the case.
<div class="input-group">
<div> <h>Instalaciones: {{filteredsites.length}}</h> <h>Active: {{}}</h> <h>Vodafone: {{}}</h> <h>Desactive: {{}}</h> <h>Pending: {{}}</h></div>
</div>
<div class="panel-body">
<div class="row">
<div class="col-lg-3">
<div >
<table class="table table-bordered table-hover table-responsive table-striped dataTable no-footer" data-sort-name="name" data-sort-order="desc">
<tr role = "row" class="info text-center">
<th ng-click="order('msisdn')">Número Teléfono</th>
<th ng-click="order('icc')">ICC</th>
<!--th>IMEI</th-->
<th ng-click="order('ActivationStatus')">Estado</th>
<th ng-click="order('sitename')">Instalación</th>
<th ng-click="order('siteaddress')">Dirección</th>
<th ng-click="order('sitecity')">Ciudad</th>
<th ng-click="order('sitezip')">Código Postal</th>
<th ng-click="order('phonedesc')">Modelo Teléfono</th>
</tr>
<tr class=" text-center" ng-repeat-start="object in filteredsites = (objects | filter:searchText | filter:{parentgroupid:selectedgroup||undefined}) | filter:tableFilter| orderBy:predicate:reverse" ng-click="showDetails = ! showDetails" >
<td>{{object.msisdn}}</td>
<td>{{object.icc}}</td>
<!--td>{{object.ActivationStatus}}</td-->
<td><span ng-init="getStatusCount(object.ActivationStatus)" ng-show="object.ActivationStatus=='AC' && object.ContractingMode=='0'" class="fa fa-square fa-3x"style="color:lime"></span><span ng-show="object.ContractingMode=='2' && object.ActivationStatus=='AC' " ><img src="../img/Vodafone_logo.png" width="40" height="40" style="background-color: lime"></span><span ng-show="object.ActivationStatus=='PA'" class="fa fa-square fa-3x"style="color:yellow"></span><span ng-show="object.ActivationStatus=='DE'" class="fa fa-square fa-3x"style="color:red"></span></td>
<td>{{object.sitename}}</td>
<td>{{object.siteaddress}}</td>
<td>{{object.sitecity}}</td>
<td>{{object.sitezip}}</td>
<td><span ng-show="object.phonedesc==''"></span><span ng-show="object.phonedesc=='Desconocido'">Desconocido</span><span></span>{{getPhoneModel(object.phonedesc)}}</td>
</tr>
</table>
</div>
<!-- /.table-responsive -->
</div>
<!-- /.col-lg-4 (nested) -->
<!-- /.col-lg-8 (nested) -->
</div>
And the controller:
var app = angular.module('dashboard', ['ui.bootstrap']);
app.controller('dashboardController', function ($scope, $http, $modal) {
$scope.objects = [];
$scope.grupos = [];
$scope.longitud = [];
$scope.eventos = [];
var URL = "/api/auth/logout";
var URLOperation = "/api/sites";
var URLModel = "http://localhost:81/api/phonelist/";
$scope.getStatusCount= function (status){
// console.log(status);
var active = 0;
active++;
console.log(active);
angular.forEach(status ,function(obj) {
if (obj.status == status) {
console.log(obj.status);
console.log(status);
console.log(active);
active++;
console.log(active);
} });
}
//Funci?n que devuelve las instalaciones de un usuario
$http.get(URLOperation, $scope)
.success(function (data) {
var groups = data;
angular.forEach(groups, function (group) {
var group2 = group;
angular.forEach(group2.sites, function (group3) {
$scope.longitud.push(group3);
$scope.objects.push(group3);
$scope.predicate = 'msisdn';
$scope.reverse = true;
$scope.order = function (predicate) {
$scope.reverse = ($scope.predicate === predicate) ? !$scope.reverse : false;
$scope.predicate = predicate;
};
})
});
})
.error(function (data) {
window.alert('Something Wrong...');
});
});
If someone can help me the count the different ActivationStatus cases i will appreciated.
You pretty much had it correct? I worked on your example in plunker and it worked right off the bet?
ng-show="object.ActivationStatus=='AC' && object.ContractingMode=='0'"
Seemed to be working for me.