angular.js ng-hide not working - angularjs

I am having an issue with using ng-hide. With all of the code below, I am able to get everything working the way I want it to until I add the ng-hide attribute, at which point it refuses to show ANY of the images. If I leave it out, the images all show up like I expect, leaving me to believe my controller is working correctly and I have hooked into it correctly. What am I not understanding? Also, you will see I put an alert in the function to make sure it is being called, but I cannot for the life of me get an alert box to work using angular.
app.js
(function () {
var app = angular.module("mainApp", []);
app.controller("StoriesListController", ["$http", StoriesListController]);
function StoriesListController($http) {
var vm = this;
vm.title = "Tutorial List";
vm.imageIndex = 0;
activate();
function activate() {
vm.stories = [];
$http.get("api/Story").then(function (response) {
vm.stories = response.data;
});
}
vm.setCurrentImage = function (index) {
vm.imageIndex = index;
};
vm.isCurrentImage = function (index) {
alert(index);
return vm.imageIndex === index;
};
}
}());
index.html
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml" ng-app="mainApp">
<head>
<title>TEST</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
<script src="/Scripts/bootstrap.min.js"></script>
<script src="Scripts/angular.min.js"></script>
<script type="text/javascript" src="Scripts/App.js"></script>
<link href="/Content/bootstrap.min.css" type="text/css" rel="stylesheet" />
</head>
<body>
<h1>TEST</h1>
<div ng-controller="StoriesListController as vm">
<h1>{{vm.title}}</h1>
<div class="container slider">
<div ng-repeat="story in vm.stories">
<img ng-src="{{story.PreviewImageURL}}" ng-hide="!isCurrentImage($index)" class="slide" />
</div>
</div>
</div>
</body>
</html>
StoryController.cs (the API I am calling to fill stories)
namespace AngularWebApi.Controllers
{
public class StoryController : ApiController
{
private static readonly List<Story> apps = new List<Story>
{
new Story
{
ID = 1,
Name = "Test 1",
Descript = "Test 1 Desc",
PreviewImageURL = "/Images/Test1.png",
Views = 1,
Ranking = 1
},
new Story
{
ID = 2,
Name = "Test 2",
Descript = "Test 2 Desc",
PreviewImageURL = "/Images/Test2.png",
Views = 1,
Ranking = 2
},
new Story
{
ID = 3,
Name = "Test 3",
Descript = "Test 3 Desc",
PreviewImageURL = "/Images/Test3.png",
Views = 1,
Ranking = 3
},
};
public IHttpActionResult Get()
{
return Ok(apps);
}
}
}

I think you just miss vm. Try ng-hide="!vm.isCurrentImage($index)".

Related

Angular.js remove item from collections using filter

I need some help with this code, i'm storing "activities" and removing it.
For now it's storing but not removing. (I just need a simple solution to this code).
Angular.js
angular
.module("TodoList",["LocalStorageModule"])
.factory("TodoService", function(localStorageService){
var todoService = {};
todoService.key = "angular-todolist";
if(localStorageService.get(todoService.key)){
todoService.activities = localStorageService.get(todoService.key);
} else {
todoService.activities = [];
}
todoService.add = function(newActv){
todoService.activities.push(newActv);
todoService.updaLocalStorage();
};
todoService.updaLocalStorage = function(){
localStorageService.set(todoService.key, todoService.activities);
};
todoService.clean = function(){
todoService.activities = [];
todoService.updaLocalStorage();
};
todoService.getAll = function(){
return todoService.activities;
};
toDoService.removeItem = function (item) { **Creating function for remove**
toDoService.activities = toDoService.activities.filter(function (activity) {
return activity !== item;
});
toDoService.updateLocalStorage();
return toDoService.getAll();
};
return toDoService;
})
.controller("TodoListCtrl", function($scope, todoService){
$scope.todo = todoService.getAll();
$scope.newActv = {};
$scope.addActv = function(){
todoService.add($scope.newActv);
$scope.newActv = {};
}
$scope.removeActv = function (item) { **Scope for remove**
$scope.todo = ToDoService.removeItem(item);
}
$scope.clean = function(){
todoService.clean();
}
});
Html
<!DOCTYPE html>
<html ng-app = "TodoList">
<head>
<meta charset="utf-8">
<title></title>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.6.2/angular.min.js"></script>
<script src = "todoctrl.js"></script>
<script src = "angular-local-storage.min.js"></script>
</head>
<body ng-controller = "TodoListCtrl">
<ul>
<li ng-repeat = "actividad in todo">
{{actividad.descripcion}} -
{{actividad.fecha | date: 'short'}} -
x **Where is removing**
</li>
</ul>
<form ng-submit = "addActv()">
<input type="text" ng-model = "newActv.descripcion">
<input type="datetime-local" ng-model = "newActv.fecha">
<input type="submit" value = "Guardar">
</form>
<button ng-click = "clean()">Limpiar</button>
</body>
</html>
update your ToDoService.removeItem(item);function. if you want to remove an item from activity you use array.splice(item) to remove an item from an array. you want to remove an item ToDoService.removeItem(item); function but your function is not doing this. it is returning a value that is either true or false. change your function body.

Angular UI Grid not displaying data

I am learning Angular and using the UI grid where I populate the grid from a simple loop method in the ShopplingList controller. The grid is displayed with the column headings but the data is not and I have no errors in chrome when I hit F12. Any help on where I am going wrong!!
My HTML and Javascript
var app = angular.module('app', ['ui.grid']);
app.controller('MainCtrl', ['$scope', '$http',
function($scope, $http) {
$scope.gridOptions1 = {};
$scope.gridOptions1.columnDefs = [{
name: 'ID'
}, {
name: 'Shopping Item'
}];
$http.get("/ShoppingList/getShoppingItems/")
.success(function(data) {
$scope.gridOptions1.data = data;
}).error(function(error) {
console.log(error);
});
}
]);
body {} .grid {
width: 1500px;
height: 450px;
}
<!DOCTYPE html>
<html ng-app="app">
<head>
<meta name="viewport" content="width=device-width" charset="UTF-8" />
<title>ShoppingList</title>
</head>
<script src="~/Scripts/angular.min.js"></script>
<script src="~/Scripts/ui-grid.min.js"></script>
<script src="~/Scripts/Irlca/ShoppingList.js"></script>
<link href="~/Content/ui-grid.css" rel="stylesheet" type="text/css" />
<link href="~/Content/main.css" rel="stylesheet" type="text/css" />
<body>
<div ng-controller="MainCtrl">
<div id="grid1" ui-grid="gridOptions1" class="grid"></div>
</div>
</body>
</html>
My Model
public class ShoppingListModel
{
public int id { get; set; }
public string shoppingItem { get; set; }
}
My Controller
public class ShoppingListController : Controller
{
//
// GET: /ShoppingList/
public ActionResult ShoppingList()
{
return View("ShoppingList");
}
public ActionResult getShoppingItems()
{
List<ShoppingListModel> lstRes = new List<ShoppingListModel>();
for (int i = 0; i < 10; i++)
{
ShoppingListModel tsk = new ShoppingListModel();
tsk.id = i * 10;
tsk.shoppingItem = "Milk" + i.ToString();
lstRes.Add(tsk);
}
return Json(lstRes, JsonRequestBehavior.AllowGet);
}
}
Assuming your get method receives the requested entities, there is one thing missing in your ui-grid configuration: the entity's field. This is set in columnDefs property and is in charge of connecting the name property (which will be the column header) to the actual entity field.
Try this:
$scope.gridOptions1.columnDefs = [{
name: 'ID',
field: 'id'
}, {
name: 'Shopping Item',
field: 'shoppingItem'
}];

Foreach with firebase

var myApp = angular.module("myApp", ["firebase"]);
var nick = prompt("Anna nimesi");
myApp.controller("MyController", ["$scope", "$firebaseArray",
function($scope, $firebaseArray) {
var msgref = new Firebase("https://(myapp).firebaseio.com/messages");
var usrref = new Firebase("https://(myapp).firebaseio.com/users");
$scope.messages = $firebaseArray(msgref);
$scope.users = $firebaseArray(usrref);
console.log($scope.users);
console.log($scope.messages);
var taken = false;
angular.forEach($scope.users, function(value, key) {
console.log(value, key);
if (value.username == nick) {
taken = true;
}
// put your code here
});
if (taken == false) {
$scope.users.$add({
username: nick
});
};
$scope.addMessage = function(e) {
if (e.keyCode == 13 && $scope.msg) {
var name = nick || "anynomous";
$scope.messages.$add({
from: name,
body: $scope.msg
});
$scope.msg = "";
}
}
}
])
<!DOCTYPE html>
<html ng-app="myApp">
<head>
<link rel="stylesheet" type="text/css" href="style.css">
<meta charset="utf-8" />
<title>title</title>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular.min.js"></script>
<script src="https://cdn.firebase.com/js/client/2.2.4/firebase.js"></script>
<script src="https://cdn.firebase.com/libs/angularfire/1.1.1/angularfire.min.js"></script>
</head>
<body ng-controller="MyController">
<div class="example-chat l-demo-container">
<ul id="example-messages" class="example-chat-messages">
<li ng-repeat="msg in messages">
<strong class="example-chat-username">{{msg.from}}</strong>
{{msg.body}}
</li>
</ul>
</div>
<input class="input" autofocus="true" ng-model="msg" ng-keydown="addMessage($event)" type="text" id="messageInput" placeholder="kirjota">
<script src="script.js"></script>
</body>
</html>
Im doing a chat, and i want to check if there is already a user with same name, so that there could not be two users with same nick. This does not work, and i can add many same nicks.
var usrref = new Firebase("https://(myapp).firebaseio.com/users");
$scope.users = $firebaseArray(usrref);
var taken = false;
for (var usr in $scope.users) {
if(usr.username == nick){
taken = true;
};};
if(taken == false){
$scope.users.$add({username:nick});
};
My messages is showing perfectly with ng-repeat in html, but i cant get this work. Its obviously something simple, but i have struggled too long with this.
Since you're using Angular, I'd suggest using Angular's forEach method. Here's an example of what you could do:
angular.forEach($scope.users, function(value, key) {
// put your code here
});
Edited
This should work for you. It checks your data after it has been loaded from Firebase. If the username is present, then it doesn't add the name. If it is not present, then it's added. You could check out the AngularFire API for $loaded().
var addNameToArray = true;
$scope.users.$loaded().then(function(data) {
angular.forEach(data, function(value, key) {
if(value.username === "John") {
addNameToArray = false;
}
});
if(addNameToArray) {
$scope.users.$add({username: "John"});
}
});
A for (var ... in ...) iterates over object keys. So if $scope.users is an array you'll get indexes: 0, 1, 2, ... in the usr variable. To iterate over an array you can use for example following construct:
$scope.users.forEach(function(user) {
});
But maybe instead of using an array it would be better to use an object indexed by username. Then you'll get immediate information if given user exists (users[nick] !== undefined) and you'll also avoid some other trouble. See Best Practices: Arrays in Firebase.

How does service variable change update to controllers

I have a small problem and I don't understand this thing:
When I add an item to TestiFactorys arr - array it does update to both controllers
On the other hand why does not TestiFactorys arr_len update to both controllers. And in TestiController why do I have to "manually" update TestControllers list1_length to make it update to view but I don't have to update TestiContollers list1 to make it update to view
I am assuming that my poor Javascript or Javascript variable scope understanding is causing this but i just don't see it.
I am using AngularJS version 1.2.16
<!DOCTYPE html>
<html ng-app="TestiApp">
<head>
<title></title>
</head>
<body>
<div ng-controller="TestController">
List items from controller: {{list1}}<br>
List item count:{{list1_length}}
<input type="text" ng-model="param"><br>
<button ng-click="list1_add(param)">asd</button>
</div>
<br><br>
<div ng-controller="TestController2">
List items from controller2{{list2}} <br>
List items count in from controller2: {{list2_length}}
</div>
<script src="scripts/angular.min.js"></script>
<script src="scripts/app.js"></script>
</body>
</html>
And this is my app.js:
var TestiApp = angular.module('TestiApp', [])
TestiApp.factory('TestiFactory',function() {
var arr = ['abx','cbs'];
var arr_len = arr.length;
return {
list : function() {
return arr;
},
add_to_arr : function(n) {
arr.push(n);
},
arr_len : function() {
arr_len = arr.length;
return arr_len;
}
}
}
);
TestiApp.controller('TestController', function($scope, TestiFactory) {
$scope.list1 = TestiFactory.list();
$scope.list1_length = TestiFactory.arr_len();
$scope.list1_add = function (d) {
TestiFactory.add_to_arr(d);
$scope.param = '';
$scope.list1_length = TestiFactory.arr_len();
}
});
TestiApp.controller('TestController2', function($scope, TestiFactory) {
$scope.list2 = TestiFactory.list();
$scope.list2_length = TestiFactory.arr_len();
});
EDIT WITH SOLUTION
Here is working solution. Based to comments I decided to do more studying on Javascripts basics which
is of course the thing I should have done before trying to use this complex framework which uses Javascript. So now I have some basic understanding how to use references in Javascript and what primitive data types are. And based on that here is working version:
<!DOCTYPE html>
<html ng-app="TestiApp">
<head>
<title></title>
</head>
<body>
<div ng-controller="TestController">
List items from controller: {{list1()}}<br>
List item count:{{list1_len()}}
<input type="text" ng-model="param"><br>
<button ng-click="list1_add(param)">asd</button>
</div>
<br><br>
<div ng-controller="TestController2">
List items from controller2{{list2()}} <br>
List items count in from controller2: {{list2_length()}}
</div>
<script src="scripts/angular.min.js"></script>
<script src="scripts/app.js"></script>
</body>
</html>
And app.js:
var TestiApp = angular.module('TestiApp', [])
TestiApp.factory('TestiFactory',function() {
var arr = ['abx','cbs'];
return {
list : function() {
return arr;
},
add_to_arr : function(n) {
arr.push(n);
},
arr_len : function() {
return arr.length;
}
}
}
);
TestiApp.controller('TestController', function($scope, TestiFactory) {
$scope.list1 = TestiFactory.list;
$scope.list1_add = TestiFactory.add_to_arr;
$scope.list1_len = TestiFactory.arr_len;
});
TestiApp.controller('TestController2', function($scope, TestiFactory) {
$scope.list2 = TestiFactory.list;
$scope.list2_length = TestiFactory.arr_len;
});
I've ran into this many times. Factories and services in angular are not like scopes...they work using references. The reason the array updates in your controllers is because the original reference was updated. The length is not updating because the number type is primitive.
This should work:
TestiApp.controller('TestController', function($scope, TestiFactory) {
$scope.list1 = TestiFactory.list();
$scope.$watch('list1', function(list1) {
$scope.list1_length = list1.length;
});
$scope.list1_add = function (d) {
TestiFactory.add_to_arr(d);
$scope.param = '';
};
});
TestiApp.controller('TestController2', function($scope, TestiFactory) {
$scope.list2 = TestiFactory.list();
$scope.$watch('list2', function(list2) {
$scope.list2_length = list2.length;
});
});

Editing model property inside ngRepeat, error undefined

I'm quite inexperienced with AngularJS.
I've read some answers that might be related but they were not clear enough for me.
My code- Plunker
I've created a table using ngRepeat and I want to change the websites name inside this table
only after clicking save button.
But I get error undefined.
My Code:
var webApp = angular.module('webApp', []);
//controllers
webApp.controller ('websitesCtrl', function ($scope, Websites) {
//$scope.x = new Website('1','3343','32434','name','privKey','pubKey','userID');
$scope.websites = Websites.get();
//This function displayes site details
$scope.expandWeb = function(website) {
console.log('expand');
$scope.websiteNew = angular.copy(website);
$scope.showName = true;
};
$scope.saveWeb = function(websiteNew) {
$scope.website.name = websiteNew.name;
$scope.showName = false;
};
});
//services
webApp.factory('Websites', function(){
var websites = {};
websites.get = function() {
return [{
id: '1',
created: '223112',
updated: '222212',
name: 'google.com',
secretKey: 'dhsd#22%$',
publicKey: '234233###',
userIdentification:'COOKIES'
},
{
id: '2',
created: '1111112',
updated: '444412',
name: 'walla.com',
secretKey: 'dhsd#22%$',
publicKey: '234233###',
userIdentification:'NONE-COOKIES'
},
{
id: '3',
created: '1111112',
updated: '444412',
name: 'Umms.com',
secretKey: 'dhsd#22%$',
publicKey: '234233###',
userIdentification:'NONE-COOKIES'
}
]
};
return websites;
});
My HTML:
<html ng-app="webApp">
<head>
<script data-require="angular.js#1.0.7" data-semver="1.0.7" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.0.7/angular.js"></script>
<link rel="stylesheet" href="style.css" />
<script src="app.js"></script>
</head>
<body ng-controller='websitesCtrl'>
<table >
<tr ng-repeat="website in websites">
<td>
{{website.name}}
<button ng-click='expandWeb(website)'>edit name</button>
</td>
</tr>
</table>
<div ng-show="showName">
<input ng-model="websiteNew.name"/>
<button ng-click='saveWeb(websiteNew)'>save</button>
</div>
</body>
</html>
$scope.webSite is undefined in saveWeb method. You should probably set it in expandWeb method.
$scope.expandWeb = function(website) {
console.log('expand');
$scope.website = website;
$scope.websiteNew = angular.copy(website);
$scope.showName = true;
};
http://plnkr.co/edit/beExyHMpXigVlCgJyfkF?p=preview

Resources