I read about ngClass in angularjs docs looked at different issues, but i still dont understand how to solve my simple problem with angular...
I have a simple button in html
<div class="form-group">
<button ng-click="displayMessage();">Change color</button>
</div>
By click on this button, function displayMessage analyze input-field (i didnt show it here) and returns one message from three, it depends from condition.
$scope.message = firstMessage;
$scope.message = secondMessage;
$scope.message = thirdMessage;
This message is expression. And validates with "if" in my app.js
<div class="form-group message">
{{message}}
</div>
And my problem is to change style of my message depending what message now is showing.
For example if it validates with firstMessage - this message should be green.
If it secondMessage - yellow...
And so on.
As i understand i need to manipulate with ng-class, but i could imagine how it works without good example
Store message and class associated with it in an object and use it in your html
$scope.message = {
"message" : "firstMessage",
"class" : "red"
}
in HTML
<div ng-class="message.class" class="form-group message">
{{message.message}}
</div>
in CSS
.red {
//whatever styling you want
}
Please have a look at plunker
Related
I would like to understand how to do the following, they asked me to try and create a function in the controller instead of writing the code in the view.
The code is:
<div class="row">
<div class="col-xs-12 max300"
uib-dropdown is-open="vm.descriptionDropdownOpen">
<textarea name="description" class="form-control"
ng-model="vm.presence.description"
ng-click="vm.toggleDescriptionDropdown()"
autofocus>
</textarea>
<ul id="descriptionDropdown" uib-dropdown-menu>
<li ng-repeat="descr in vm.loadedDescriptions"
ng-click="vm.presence.description = descr.text;
vm.descriptionDropdownOpen = false;">
{{descr.text}}
</li>
</ul>
</div>
</div>
so basically this creates a text box, and when you click on it, a dropdown menu will appear, and if you click on a string of the dropdown menu, that string will be put in the text box.
What I need to do is to create a function that will be put in the controller, so we can just call that function in the view and keep the code nicer.
This function just needs to do the last part of the code I posted above, take the string I click on from the dropdown menu and put it in the text box!
It's really simple but as I'm learning I'm not that sure on how I should write it
setDescription(text: string) {
// code should go here.
}
Sorry for this stupid question, just wanna be sure to understand correctly what I am doing! thank you
html
ng-click="vm.submitString(descr.text)"
controller
vm.submitString = function(text){
return vm.presence.description = text;
}
resolved like this:
setDescription(text: string) {
return this.presence.description = text;
}
I am getting this error when i click the button without entering anything in input field. I am seeing this is because of the naming convention as "lunchCtrl.iform.inputText". when i use this as "lunchCtrl.inputText" or just "inputText" in controller and html its going good without error for empty value onbutton click.
if i enter any text and click the button its going good.
can anyone help me whats going wrong here.
i have attached the code in the following jsfiddle [here][1]. please help me to find the reason.
https://jsfiddle.net/29bmy95j/
code for here:
index.html
Lunch Checker
<div class="form-group">
<input id="lunch-menu" type="text"
placeholder="list comma separated dishes you usually have for lunch"
class="form-control" ng-model="lunchCtrl.iform.inputText">
</div>
<div class="form-group">
<button class="btn btn-default" ng-click="checkTooMuch()">Check If Too Much</button>
</div>
<div class="form-group message">
<!-- Your message can go here. -->
</div>
Entered values::{{lunchCtrl.iform.inputText}}
<p ng-bind="errorMsg" style="color:red"></p>
App.js:
var app=angular.module('LunchCheck', []);
app.controller('LunchCheckController', ["$scope",function($scope){
//function for checkTooMuch() ng-click event
$scope.checkTooMuch=function(){
var inputfieldVal=$scope.lunchCtrl.iform.inputText;
$scope.inputfieldValScope=inputfieldVal;
var array=inputfieldVal.split(',');
//$scope.array=array;
var arrLen=array.length;
if(arrLen > 3){$scope.errorMsg="Too much!";}
else{$scope.errorMsg="Enjoy!";}
}
}]);
error Image
Because $scope.lunchCtrl.iform is not defined, thus initially when you don't type anything in the textfield $scope.lunchCtrl.iform.inputText will trigger an error.
$scope.checkTooMuch=function(){
var inputfieldVal=$scope.lunchCtrl.iform.inputText;//error
So the fix would be to
OPTION 1
write a check and avoid:
$scope.checkTooMuch=function(){
if (!$scope.lunchCtrl.iform.inputText){
return;
}
...your code
OPTION 2
Define your variable like below in the controller
app.controller('LunchCheckController', ["$scope",function($scope){
//var v=$scope.inputText='';
this.iform = {inputText:""};
...
working code here
I've been tinkering around a bit with AngularJS and the Ionic framework. Now I would like to display 12 buttons inside a popup. I have this all working, but I would like the buttons to switch appearance when they got pressed.
html
<label>
<p>Fill in catergory name</p>
<input type="text" placeholder="Rent">
</label>
<br />
<br />
<div class="row">
<div class="col col-25"><button class="button button-outline" id="button12in" ng-class="button12 ? 'button12in' : 'button12inpress'" ng-click="button12 = !button12">
</div>
</div>
As you can see I've been trying with button 12.
app.js
$scope.button12 = false;
css
#button12in {background-color: #51FF00;}
#button12inpress{border-style: solid; border-color: black; border-width: 4px;background-color: #51FF00;}
So the idea is that clicking on the button will change the state of $scope.button12. The result of this would be that via the ng-class the button will change style! but for some reason, this is not possible. It picks up the changed state of button12 but the ng-class isn't working in all kinds of syntax I've tried
I think it should be
ng-class="{'class': trueOrFalse}"
To apply different classes when different expressions evaluate to true:
<div ng-class="{class1 : expression1, class2 : expression2}">
Hello World!
</div>
To apply multiple classes when an expression holds true:
<!-- notice expression1 used twice -->
<div ng-class="{class1 : expression1, class2 : expression1}">
Hello World!
</div>
or quite simply:
<div ng-class="{'class1 class2' : expression1}">
Hello World!
</div>
Notice the single quotes surrounding css classes.
or check this Adding multiple class using ng-class
Don't use your flag directly on $scope , but rather try setting the flag on an object on $scope
Example
Use $scope.flagContainer.button12 instead of $scope.button12
$scope.flagContainer = {
button12 : false
}
Now change it view accordingly
I am working on a website that displays numerous articles. Each article has a comment section. I have effectively been able to recursively write the comments to the DOM with recursion inside an ng-repeat. However, I need to be able to click on a respond button on any of the comments (they display in a nested fashion) and for a div to be inserted beneath the clicked button. This div would contain a text area for the comment they want to submit and a button. When this second button is clicked, the controller will save the comment to the database. I initially wanted to do this by directly manipulating the DOM from the controller. However, after further research, that would be in direct violation of the MVC/MVW pattern. I believe the correct answer is to create a custom directive. Please give me some insight on how to correctly do this. Any and all information would be very helpful. Thanks in advance.
If you want to add response div dinamically:
<div ng-repeat="article in articles" id="article-{{$index}}">
<p>{{article.content}}</p>
<button ng-click="addAnswer($index)">Add Answer</button>
</div>
js:
myApp.controller("articlesController", function($compile){
$scope.addAnswer = function (index) {
var div = $("<div></div>");
var input = $("<input type='text' ng-model='article.response'></input>");
div.append(input);
var button = $("<button>Send</button>");
button.attr("ng-click", "sendResponse(article)");
$compile(div)($scope);
$("#article-" + index).append(div);
};
});
You don't really need to make a directive to achieve this.
html:
<div ng-repeat="article in articles">
<p>{{article.content}}</p>
<input type="text" ng-model="article.response"></input>
<button ng-click="sendResponse(article)">Send</button>
</div>
js:
myApp.controller("articlesController", function($http){
$scope.sendResponse = function (article) {
console.log(article.response);
$http.post(url, article);
};
});
Of course, you can do it better by hidding input and send button, and show it after user clicks over an answer button.
I'm trying to add some text to the last cursor place after clicking a button.
In the controller:
$scope.addEmoji = function(name){
var element = $("#chat-msg-input-field");
element.focus(); //ie
var selection = element.getSelection();
var textBefore = $scope.chatMsg.substr(0, selection.start);
var textAfter = $scope.chatMsg.substr(selection.end);
$scope.chatMsg = textBefore + name + textAfter;
}
$scope.updateChatMsg = function(chatMsg){
$scope.chatMsg = chatMsg;
}
$scope.sendChatMsg = function(){
var backend = $scope.convs[$scope.active.conv].backend.name;
$scope.view.addChatMsg($scope.active.conv, $scope.active.user, $scope.chatMsg,new Date().getTime() / 1000, backend);
Chat[backend].on.sendChatMsg($scope.active.conv, $scope.chatMsg);
$scope.chatMsg = '';
};
And then some HTML:
<div class="chat-msg-button" >
<button ng-click="view.toggle('emojiContainer')" ><img src="/apps/chat/img/emoji/smile.png"></button>
</div>
<form id="chat-msg-form" ng-submit="sendChatMsg()">
<div class="chat-msg-button" >
<button type="submit"><div class="icon-play"> </div></button>
</div>
<div id="chat-msg-input">
<textarea id="chat-msg-input-field" autocomplete="off" type="text" ng-model="chatMsg" ng-change="updateChatMsg(chatMsg)" placeholder="Chat message"></textarea>
<div>{{ chatMsg }}</div>
</div>
</form>
What I'm trying to achieve: a user types some text in the textarea => $scope.chatMsg gets the value of the textarea. Now the user press one of the button's => the name of the button is added to the latest cursor position. (it's no problem to find the latest cursor position)
The problem
There is a difference between the value of $scope.chatMsg, {{ chatMsg }} inside the div and the text in the textarea.
The contents of the textarea and the div stays always the same. But when pressing the button the name is added to $scope.chatMsg but the contents of the textarea isn't changed...
How can I solve this?
TIA
First of all, you're mixing jQuery with AngularJS, it doesn't look like you need jQuery here that much.
Also, your chat message is updated in 3 different functions, so you need some debugging to see which are fired.
In general:
To solve your issue, try some more debugging, do a
$scope.$watch($scope.chatMsg, function(){
console.log($scope.chatMsg);
});
this will watch all changes to chatMsg. Add console.log() to each of your functions and you can watch which is fired.
Also, rather than using {{ }} inside your div just use ng-bind since that text is the only item in your div, it's cleaner if your app crashes somewhere.
// change from
<div>{{ chatMsg }}</div>
// to
<div ng-bind="chatMsg "></div>
Update: after seeing your plunker, I modified it and came up with this: http://plnkr.co/edit/oNKGxRrcweiJafKCm9A5?p=preview
Your ng-repeat needs to be tracked by $index so that duplicates are displayed rather than crashing when someone creates the same message
I solved all problems. The plunkr form above works. So after investigating all scopes with the Angular chrome extension I saw that chatMsg was defined in another scope. Thus not in the scope I was trying to acces it from.
Via this question angularJS ng-model input type number to rootScope not updating I found a solution.
I added chatMsg to the fields object.