My toggle works fine but when I click the button again it will not reset all. The tab which is open will stay open or close (if it's close). It is behaving like it doesn't want to reset to its original form. Can someone suggest me what I am doing wrong, please
<md-card>
<md-card-content>
<button ng-click="Custom()">Cick Here</button>
<div>
<div ng-repeat="search in vm.searchResults">
<md-card ng-click="callaction=!callaction">
<md-card-content>
<br />
<div ng-repeat="sponsor in search.scp">
<div ng-repeat="cin in sponsor.ci">
<div ng-repeat="po in cin.po" >
<p></p>
<span> {{sponsor.Name }}</span>
<span ng-repeat="prod in po.prods">
<img ng-src="{{img/cc2.ico}}">
</span>
<md-list>
<md-list-item ng-hide="callaction">
<div class="outside">
<div ng-repeat="delivery in po.deliveryAddresses" class='extra divInner'>
{{delivery.PracticeName}} <br /> <span ng-show="delivery.LineTwo">{{ delivery.LineTwo}}
</div>
</div>
</md-list-item>
</md-list>
</div>
</div>
</div>
</md-card-content>
</md-card>
</div>
</div>
</md-card-content>
</md-card>
Javascript
$scope.callaction = true;
$scope.Custom = function () {
$scope.callaction = !$scope.callaction;
};
As you can see running the code snippet,
angular works fine...
function TestCtrl($scope, cards) {
var vm = $scope;
vm.cards = cards;
vm.collapseCard = function(card) {
card.callaction = false;
};
vm.expandCard = function(card) {
card.callaction = true;
};
vm.Custom = function(event, card) {
card.callaction
? vm.collapseCard(card)
: vm.expandCard(card)
;
};
vm.collapseAll = function(event) {
vm.cards.forEach(vm.collapseCard);
};
vm.expandAll = function(event) {
vm.cards.forEach(vm.expandCard);
};
vm.toggleAll = function(event) {
vm.cards.forEach(function(card) {
vm.Custom(event, card);
});
};
vm.checkboxStyleBehaviour = function(event) {
var someCollapsed = vm.cards.some(
function(card) { return card.callaction === false; }
);
if(/* there are */ someCollapsed /* cards left */) {
return vm.expandAll();
}
return vm.collapseAll();
};
}
angular
.module('test', [])
.controller('TestCtrl', TestCtrl)
.constant('cards', Array.from({length: 20},
(_, i) => ({id: ++i, callaction: true})
))
;
.toggle-disabled {
visibility: hidden;
}
button {
margin-right: 5px;
}
.cbox {
background: lightcoral;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<section ng-app="test">
<div ng-controller="TestCtrl">
<button ng-click="expandAll($event)">Expand All Cards</button>
<button ng-click="collapseAll($event)">Collapse All Cards</button>
<button ng-click="toggleAll($event)">Toggle All Cards</button>
<button ng-click="checkboxStyleBehaviour($event)" class="cbox">Checkbox Style?</button>
<hr />
<hr />
<div ng-repeat="card in cards track by $index">
<button ng-click="Custom($event, card)">Toggle</button> <strong ng-class="{false: 'toggle-disabled'}[card.callaction]">
{{card.id}} - I Am Active
</strong>
<hr />
</div>
</div>
</section>
Related
I recently started to study JS and wanted to do a clickable tab showing different text with forEach method, but unfortunately i'm struggling!
const buttons = document.querySelectorAll('.button');
const texts = document.querySelectorAll('.text');
buttons.forEach(button => {
button.addEventListener('click', (event) => {
//make buttons active
buttons.forEach((button) => {
button.classList.remove('active')
})
event.target.classList.add('active')
//show text
texts.forEach(text => {
text.classList.remove('text');
})
});
})
<button class="button">Tab1</button>
<button class="button">Tab2</button>
<button class="button">Tab3</button>
<div class="text-tabs">
<div class="text">
<h4>Text from tab1</h4>
</div>
<div class="text">
<h4>Text from tab2</h4>
</div>
<div class="text">
<h4>Text from tab3</h4>
</div>
The CSS already has the display: none and then block
a way to do it is to add a data attribute to your different tab (for sample an id or an index) <button class="button" data-tab="1">Tab1</button>
and recover this value when you click on element
event.target.dataset.tab
const buttons = document.querySelectorAll('.button');
const texts = document.querySelectorAll('.text');
buttons.forEach(button => {
button.addEventListener('click', (event) => {
//make buttons active
buttons.forEach((button) => {
button.classList.remove('active')
})
event.target.classList.add('active')
texts.forEach(text => text.classList.add('hidden'));
const tabToShow = document.querySelector(`.text:nth-child(${event.target.dataset.tab})`);
if (tabToShow) {
tabToShow.classList.remove('hidden');
}
});
})
.hidden {
display: none;
}
button.active {
background: red;
}
<button class="button" data-tab="1">Tab1</button>
<button class="button" data-tab="2">Tab2</button>
<button class="button" data-tab="3">Tab3</button>
<div class="text-tabs">
<div class="text hidden">
<h4>Text from tab1</h4>
</div>
<div class="text hidden">
<h4>Text from tab2</h4>
</div>
<div class="text hidden">
<h4>Text from tab3</h4>
</div>
</div>
I have set of four button and I want to make them toggle and active on click of the button. Currently my buttons are get toggled on double click.
The solution what I am expecting is, when I click on the button current btn should get highlighted and data should be displayed and when I click on the next button, previous content should get hidden and current content should be visible.
Code:
(function() {
var app = angular.module('myapp', []);
app.controller('toggle', function($scope) {
$scope.Ishide_bank = true;
$scope.bank = function() {
$scope.Ishide_bank = $scope.Ishide_bank ? false : true;
};
$scope.Ishide_asset = true;
$scope.assets = function() {
$scope.Ishide_asset = $scope.Ishide_asset ? false : true;
};
$scope.Ishide_address = true;
$scope.address = function() {
$scope.Ishide_address = $scope.Ishide_address ? false : true;
};
$scope.Ishide_personal = true;
$scope.personal = function() {
$scope.Ishide_personal = $scope.Ishide_personal ? false : true;
};
});
})();
<!DOCTYPE html>
<html ng-app="myapp">
<head>
<link rel="stylesheet" href="style.css">
<script src="script.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.6.4/angular.min.js"></script>
</head>
<body ng-controller="toggle">
<div>
<button class="bttn" ng-click="address()">Address</button>
<button class="bttn" ng-click="personal()">Personal-details</button>
<button class="bttn" ng-click="bank()">Bank-Account</button>
<button class="bttn" ng-click="assets()">Asset</button>
</div>
<div ng-hide="Ishide_address">
<h1>Btn 1</h1>
</div>
<div ng-hide="Ishide_bank">
<h1>Btn 2</h1>
</div>
<div ng-hide="Ishide_asset">
<h1>Btn 3</h1>
</div>
<div ng-hide="Ishide_personal">
<h1>Btn 4</h1>
</div>
</body>
</html>
Plunker : https://plnkr.co/edit/8hr9zXXkgBkBZRqUjpks?p=preview
Please let me know where I am going wrong.
first of your script order is wrong!
angular lib should be first then custom script.js
also below is the simplest way to do what you trying to do.
(function() {
var app = angular.module('myapp', []);
app.controller('toggle', function($scope) {
$scope.view = 'default';
$scope.toggle_view = function(view) {
$scope.view = $scope.view === view ? 'default' : view;
};
});
})();
.bttn {
background: #eee;
border: 1px solid #aaa;
}
.bttn.active {
background: yellow;
}
.bttn:focus {
outline: none;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="myapp">
<div ng-controller="toggle">
<div>
<button class="bttn" ng-class="{'active': view === 'address'}" ng-click="toggle_view('address')">Address</button>
<button class="bttn" ng-class="{'active': view === 'personal'}" ng-click="toggle_view('personal')">Personal-details</button>
<button class="bttn" ng-class="{'active': view === 'bank'}" ng-click="toggle_view('bank')">Bank-Account</button>
<button class="bttn" ng-class="{'active': view === 'asset'}" ng-click="toggle_view('asset')">Asset</button>
</div>
<div ng-show="view === 'address'">
<h1>Address View</h1>
</div>
<div ng-show="view === 'bank'">
<h1>Bank View</h1>
</div>
<div ng-show="view === 'asset'">
<h1>Asset View</h1>
</div>
<div ng-show="view === 'personal'">
<h1>Personal View</h1>
</div>
</div>
</div>
I created one TODO List in AngularJS but I didn't finish the update function. I have some difficulty.
How do I create the update function?
Link: https://plnkr.co/edit/XfWoGVrEBqSl6as0JatS?p=preview
<ul class="list-todo">
<li ng-repeat="t in tasks track by $index">
<div class="row">
<div class="six columns">
<p>{{ t }}</p>
</div>
<div class="three columns">
<button class="button" ng-click="update()">update</button>
</div>
<div class="three columns">
<button class="button" ng-click="delete()">x</button>
</div>
</div>
</li>
</ul>
Angular Code:
angular.module('todoTest', [])
.controller('todoController', function($scope) {
$scope.tasks = [];
$scope.add = function() {
$scope.tasks.push($scope.dotask);
}
$scope.update = function(){
$apply.tasks.push($scope.dotask);
}
$scope.delete = function() {
$scope.tasks.splice(this.$index, 1);
}
})
If you want to update the value you have to pass as parameter the position of the task inside the tasks array ($index is the position):
<button class="button" ng-click="update($index)">update</button>
And then the update function would be:
$scope.update = function(index){
$scope.tasks[index] = $scope.dotask;
}
Is that what you needed?
Button for updating. Visible only while updating.
<div class="row">
<button type="submit" class="u-full-width button button-primary">Criar Tarefa</button>
<button ng-show="updateMode" ng-click="update()" type="button" class="u-full-width button button-primary">Update</button>
</div>
New update function.
$scope.update = function(index) {
if ($scope.updateMode) {
$scope.tasks[$scope.updateIndex] = $scope.dotask;
$scope.updateMode = false;
} else {
$scope.dotask = $scope.tasks[index];
$scope.updateMode = true;
$scope.updateIndex = index;
}
If you click update on the task it will make the big update button visible and bring the old todo to the input. After hitting the big update button the todo task will update.
Plunker
Ive tried to use this with the current view scope and also by adding its own controller. No success in clearing all fields on cancel button click. All I need is to clear the fields.
Here is my in my controller modal :
var myApp = angular.module('starter.controllers');
function TalkSearchPageCtrl($scope, TalkSearch, $ionicModal) {
var nextPageNum = 1;
$scope.noMoreItemsAvailable = false;
var nextPageNum = 1;
$scope.loadMore = function() {
TalkSearch.getList(nextPageNum, {
}, $scope.idsToExclude, $scope.backResult).success(function(items) {
if (typeof(items.idsToExclude) !== undefined) {
$scope.idsToExclude = items.idsToExclude;
$scope.backResult = true;
} else {
$scope.idsToExclude = undefined;
$scope.backResult = undefined;
}
// error check when it's not loading
if (items.talks.length != 0) {
i = 0;
while (i != items.talks.length - 1) {
$scope.talks.push(items.talks[i]);
i++;
}
nextPageNum++;
} else {
$scope.noMoreItemsAvailable = true;
}
$scope.$broadcast('scroll.infiniteScrollComplete');
});
};
$scope.talks = [];
$scope.categories = [
];
$scope.checkedCategories = [];
$scope.toggleCheck = function(category) {
if ($scope.checkedCategories.indexOf(category) === -1) {
$scope.checkedCategories.push(category);
} else {
$scope.checkedCategories.splice($scope.checkedCategories.indexOf(category), 1);
}
};
$scope.getValues = function(filter) {
console.log(filter);
if (filter.length || filter !== undefined) {
$scope.userFilter = {};
$scope.userFilter.categories = [];
$scope.userFilter.filters = {};
$scope.userFilter.filters = angular.copy(filter);
var categories = $scope.checkedCategories;
$scope.userFilter.categories = categories;
getFiltersService.filter = angular.copy(filter);
console.log($scope.userFilter);
// console.log(getFiltersService.filter);
}
};
$scope.reset = function() {
console.log($scope.userFilter);
// $scope.modal.hide();
// $scope.userFilter.filters = null;
// $scope.userFilter.categories = null;
// $scope.userFilter = {};
console.log($scope.userFilter);
};
$ionicModal.fromTemplateUrl('my-modal.html', {
scope: $scope,
animation: 'slide-in-up'
}).then(function(modal) {
$scope.modal = modal;
});
}
myApp.controller('TalkSearchPageCtrl', ['$scope', 'TalkSearch', '$ionicModal', TalkSearchPageCtrl]);
$ionicModal.fromTemplateUrl('my-modal.html', {
scope: $scope,
animation: 'slide-in-up'
}).then(function(modal) {
$scope.modal = modal;
});
Here is my html script template :
<script id="my-modal.html" type="text/ng-template">
<ion-modal-view>
<ion-header-bar class="bar bar-header schoolinkscolor headerSection" ng-controller="TalkFilterPageCtrl">
<div class="row padding0">
<div class="col">
<div class="button button-white closeModal" side="right" ng-click="reset(talkfilter);hideButton=false;showDetails=false;"><span>Cancel</span></div>
</div>
<div class="col">
<div class="light headerTitle"><span class="light">Schoo</span><span class="color-black">Links</span></div>
</div>
<div class="col">
<div class="button button-white searchButton" side="left"><span>Search</span></div>
</div>
</div>
</ion-header-bar>
<ion-content class="has-header">
<div class="talkFilterContainer">
<section>
<div class="col padding0">
<div class="list list-inset">
<label class="item item-input">
<i class="icon ion-search placeholder-icon"></i>
<input type="text" placeholder="Search" ng-model="talkfilter.searchTalk" ng-change="getValues(talkfilter)" ng-model-options="{ debounce: 1000 }">
</label>
</div>
</div>
</section>
<div class="row padding clearboth"></div>
<section>
<div class="list padding">
<label class="item item-input item-select">
<div class="input-label">
Language:
</div>
<select ng-options="author for author in ['Mandarin','Spanish','Portuguese']" ng-model="talkfilter.selectLanguage" ng-init="author = 'Select Preferred Language'" ng-change="getValues(talkfilter)">
<option value="">Select Preferred Language</option>
</select>
</label>
</div>
</section>
<div class="row padding clearboth"></div>
<section>
<div class="list padding">
<label class="item item-input item-select">
<div class="input-label">
Author Type:
</div>
<select ng-options="author for author in ['Consultant','School','Student']" ng-model="talkfilter.authorType" ng-init="author = 'Select By Author Type'" ng-change="getValues(talkfilter)">
<option value="">Select By Author Type</option>
</select>
</label>
</div>
</section>
<div class="row padding clearboth"></div>
<section class="padding">
<ion-list>
<ion-item ng-repeat="category in categories track by $index" ng-class="{ 'hidden': ! showDetails && $index > 2}">
<ion-checkbox value="{{category}}" ng-model="$index" ng-click="toggleCheck(category); getValues(talkfilter)">{{category}}</ion-checkbox>
</ion-item>
</ion-list>
<div class="row">
<button class="button button-full button-clear" ng-click="showDetails = ! showDetails;hideButton=true" ng-show="!hideButton">See All Categories</button>
</div>
</section>
</div>
</ion-content>
</ion-modal-view>
Here is my reset function:
var Talk = this;
Talk.reset = function(filter) {
console.log(filter);
filter = null;
};
Also tried with $scope :
$scope.reset = function(filter) {
console.log(filter);
filter = null;
};
***Update:
$scope.reset = function(filter) {
$scope.userFilter = null; //does not work. none of these variations work.
$scope.userFilter = '';
};
Both of these methods return undefined. But if i put the button in the body it clears the fields. I need the button in the header.
Also tried inlining the reset with:
<button ng-click="talkfilter=null"></button>
The problem is that you are not passing anything in the filter function with the ng-click, because your $scope.userfilter is not defined throughout the controller.
Adding $scope.userFilter = {} like you have done inside of getValues, outside of that function should give you the desired result if you do your reset function like so....
function TalkSearchPageCtrl($scope, TalkSearch, $ionicModal) {
$scope.userFilter = {};
...
$scope.reset = function(filter) {
console.log(filter); \\Make sure this is the object
$scope.userFilter = null; \\Set it to null or {}
}`
I am trying to work how to add a class with ngClick. I have uploaded up my code onto plunker Click here. Looking at the angular documentation i can't figure out the exact way it should be done. Below is a snippet of my code. Can someone guide me in the right direction
<div ng-show="isVisible" ng-class="{'selected': $index==selectedIndex}" class="block"></div>
Controller
var app = angular.module("MyApp", []);
app.controller("subNavController", function ($scope){
$scope.toggle = function (){
$scope.isVisible = ! $scope.isVisible;
};
$scope.isVisible = false;
});
I want to add or remove "active" class in my code dynamically on ng-click, here what I have done.
<ul ng-init="selectedTab = 'users'">
<li ng-class="{'active':selectedTab === 'users'}" ng-click="selectedTab = 'users'"><a href="#users" >Users</a></li>
<li ng-class="{'active':selectedTab === 'items'}" ng-click="selectedTab = 'items'"><a href="#items" >Items</a></li>
</ul>
You just need to bind a variable into the directive "ng-class" and change it from the controller. Here is an example of how to do this:
var app = angular.module("ap",[]);
app.controller("con",function($scope){
$scope.class = "red";
$scope.changeClass = function(){
if ($scope.class === "red")
$scope.class = "blue";
else
$scope.class = "red";
};
});
.red{
color:red;
}
.blue{
color:blue;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<body ng-app="ap" ng-controller="con">
<div ng-class="class">{{class}}</div>
<button ng-click="changeClass()">Change Class</button>
</body>
Here is the example working on jsFiddle
There is a simple and clean way of doing this with only directives.
<div ng-class="{'class-name': clicked}" ng-click="clicked = !clicked"></div>
you can also do that in a directive, if you want to remove the previous class and add a new class
.directive('toggleClass', function() {
return {
restrict: 'A',
link: function(scope, element, attrs) {
element.bind('click', function() {
if(element.attr("class") == "glyphicon glyphicon-pencil") {
element.removeClass("glyphicon glyphicon-pencil");
element.addClass(attrs.toggleClass);
} else {
element.removeClass("glyphicon glyphicon-ok");
element.addClass("glyphicon glyphicon-pencil");
}
});
}
};
});
and in your template:
<i class="glyphicon glyphicon-pencil" toggle-class="glyphicon glyphicon-ok"></i>
You have it exactly right, all you have to do is set selectedIndex in your ng-click.
ng-click="selectedIndex = 1"
Here is how I implemented a set of buttons that change the ng-view, and highlights the button of the currently selected view.
<div id="sidebar" ng-init="partial = 'main'">
<div class="routeBtn" ng-class="{selected:partial=='main'}" ng-click="router('main')"><span>Main</span></div>
<div class="routeBtn" ng-class="{selected:partial=='view1'}" ng-click="router('view1')"><span>Resume</span></div>
<div class="routeBtn" ng-class="{selected:partial=='view2'}" ng-click="router('view2')"><span>Code</span></div>
<div class="routeBtn" ng-class="{selected:partial=='view3'}" ng-click="router('view3')"><span>Game</span></div>
</div>
and this in my controller.
$scope.router = function(endpoint) {
$location.path("/" + ($scope.partial = endpoint));
};
var app = angular.module("MyApp", []);
app.controller("subNavController", function ($scope){
$scope.toggle = function (){
$scope.isVisible = ! $scope.isVisible;
};
$scope.isVisible = false;
});
<div ng-show="isVisible" ng-class="{'active':isVisible}" class="block"></div>
I used Zack Argyle's suggestion above to get this, which I find very elegant:
CSS:
.active {
background-position: 0 -46px !important;
}
HTML:
<button ng-click="satisfaction = 'VeryHappy'" ng-class="{active:satisfaction == 'VeryHappy'}">
<img src="images/VeryHappy.png" style="height:24px;" />
</button>
<button ng-click="satisfaction = 'Happy'" ng-class="{active:satisfaction == 'Happy'}">
<img src="images/Happy.png" style="height:24px;" />
</button>
<button ng-click="satisfaction = 'Indifferent'" ng-class="{active:satisfaction == 'Indifferent'}">
<img src="images/Indifferent.png" style="height:24px;" />
</button>
<button ng-click="satisfaction = 'Unhappy'" ng-class="{active:satisfaction == 'Unhappy'}">
<img src="images/Unhappy.png" style="height:24px;" />
</button>
<button ng-click="satisfaction = 'VeryUnhappy'" ng-class="{active:satisfaction == 'VeryUnhappy'}">
<img src="images/VeryUnhappy.png" style="height:24px;" />
</button>
If you prefer separation of concerns such that logic for adding and removing classes happens on the controller, you can do this
controller
(function() {
angular.module('MyApp', []).controller('MyController', MyController);
function MyController() {
var vm = this;
vm.tab = 0;
vm.setTab = function(val) {
vm.tab = val;
};
vm.toggleClass = function(val) {
return val === vm.tab;
};
}
})();
HTML
<div ng-app="MyApp">
<ul class="" ng-controller="MyController as myCtrl">
<li ng-click="myCtrl.setTab(0)" ng-class="{'highlighted':myCtrl.toggleClass(0)}">One</li>
<li ng-click="myCtrl.setTab(1)" ng-class="{'highlighted':myCtrl.toggleClass(1)}">Two</li>
<li ng-click="myCtrl.setTab(2)" ng-class="{'highlighted':myCtrl.toggleClass(2)}">Three</li>
<li ng-click="myCtrl.setTab(3)" ng-class="{'highlighted':myCtrl.toggleClass(3)}">Four</li>
</ul>
CSS
.highlighted {
background-color: green;
color: white;
}
I can't believe how complex everyone is making this. This is actually very simple. Just paste this into your html (no directive./controller changes required - "bg-info" is a bootstrap class):
<div class="form-group col-md-12">
<div ng-class="{'bg-info': (!transport_type)}" ng-click="transport_type=false">CARS</div>
<div ng-class="{'bg-info': transport_type=='TRAINS'}" ng-click="transport_type='TRAINS'">TRAINS</div>
<div ng-class="{'bg-info': transport_type=='PLANES'}" ng-click="transport_type='PLANES'">PLANES</div>
</div>
for Reactive forms -
HTML file
<div class="col-sm-2">
<button type="button" [class]= "btn_class" id="b1" (click)="changeMe()">{{ btn_label }}</button>
</div>
TS file
changeMe() {
switch (this.btn_label) {
case 'Yes ': this.btn_label = 'Custom' ;
this.btn_class = 'btn btn-danger btn-lg btn-block';
break;
case 'Custom': this.btn_label = ' No ' ;
this.btn_class = 'btn btn-success btn-lg btn-block';
break;
case ' No ': this.btn_label = 'Yes ';
this.btn_class = 'btn btn-primary btn-lg btn-block';
break;
}