angular add property to model - angularjs

I have an angular service that returns a list of items from the database.
I display those items through an ng-repeat. I'd like to hide/show each one of them using the ng-show.
Is it a good practice to add a "display" property directly on my items to show or hide them in the UI?
Edit: If someone could point me to an article explaining that orientation (can't seem to find any).

Yes. This is the right choice. It enables your model to control how items are viewed according to a separately controlled logic. This makes your application scalabale too.
A filter is a better choice in further modeling your logic.

As suggested by other answers, filter is the better choice for your case. Add a property display and then filter based on that property.
<div ng-repeat="item in dataFromServer | filter:{ display: true }">
{{item.name}}
</div>
I have used underscore to create a new property for each object
https://jsfiddle.net/k8u3c8t7/

Related

Angular 1.x bind to variable property

Is there a way to bind via html to a variable property in angular 1.x?
I have a data object that I need to update based on certain conditions, which would change the property it should bind to:
<div ng-repeat="option in options">
<custom-component selected="$ctrl.data[option.dataProperty]"></custom-component>
</div>
I can't seem to get it to bind into the customComponent with one or two way bindings. Would appreciate any other suggestions.
Update:
Thanks for the comments, writing the plunker illuminated the problem for me :) you can find it here for posterity's sake. Thanks!

List of objects that need different logic

I want to display a list of events of very different types that should have different UI logic. Yes, they have common properties (like name, date/time, location etc) but also sets of custom properties that can be simple text, typeahead items, drop down lists etc. Depending on the specific event type (there will be tens of them) I need to handle user input in different ways. For example, on select a typeahead item I want to clear two other fields etc.
I'm gonna display those events using ng-repeat and dynamically load template views depending on the specific event type. These views will have proper controllers that are specific to the business object. I still haven't make it work but please advice me.
Is loading type-related views with controllers inside is a good idea
for this task?
Would directives instead of controllers be better?
Is there a way to dynamically set controller/directive name in the HTML attribute?
Any other advices?
yes
yes, use directives. If you have a base event definition, it is probably best to define an element directive for that and use attribute directives to extend/customize the functionality for different event types.
not exactly, but you can use ng-switch on your list item element.
example:
<li ng-repeat="event in events" ng-switch on="event.type">
<my-event event="event" first-type ng-switch-when="type1"></my-event>
<my-event event="event" second-type ng-switch-when="type2"></my-event>
<my-event event="event" third-type ng-switch-when="type3"></my-event>
<my-event event="event" ng-switch-default></my-event>
</li>
Use require: 'myEvent' in your extending directives to gain access to the base myEvent controller.
Demo

Simple One way binding for ng-repeat?

I have read some articles that said ng-repeat would led to poor performance if there is over 2000 items, because there are too many two way binding to watch. I am new to angularjs and have trouble understanding the relationship between ng-repeat and two-way binding:
Does ng-repeat (like outputting a list of json objects) necessarily create two way binding?
Is there a simple way to do ng-repeat using only one way binding? (preferably do not need external module)
Like user1843640 mentioned, if you are on Angular 1.3, you can use one-time-binding, but, just for clarity, you need to put the :: on all the bindings, not just the repeater. The docs say do this:
<div ng-repeat="item in ::items">{{item.name}}</div>
But, if I count the watchers, this only removed one. To really drop the number of two-way-bindings, place the :: on the bindings within the repeater, like this:
<div ng-repeat="item in ::items">{{::item.name}}</div>
Here are two plunkers that will display the number of watchers:
All Bindings
Repeater Only
Thanks goes out to Miraage for provinding the function to count the watchers https://stackoverflow.com/a/23470578/2200446
For anyone using or upgrading to Angular 1.3 you can now use "one-time binding". For ng-repeat it would look like this:
<div ng-repeat="item in ::items">{{item.name}}</div>
Notice the ::items syntax.
For more information check the Angular documentation for expressions.
This blog post presents some interesting solutions. The end result was:
Upgrade to AngularJS 1.1.5 and use limitTo together with Infinite scrolling. AngularJS ng-repeat offers from version 1.1.4 the limitTo option. I slightly adapted the Infinite Scroll directive to make scrolling within a container possible that does not have height 100% of window.
Basically you limit the number of objects you initially render, then use the Infinite scrolling directive to render more as needed. Since you don't want an external module, just mimic the infinite scroll functionality as needed with your own script.
Note: This should solve your performance problem but it won't remove two-way binding.
what ever is generated by ng-model will be having a watcher on data(model) which reduces the page performance if it crosses 200 watchers.
Refer this for ONE WAY BINDING http://blog.scalyr.com/2013/10/31/angularjs-1200ms-to-35ms/ but make sure you use it properly
Hope it helps!!!

AngularJS Bootstrap UI btn-checkbox in ng-repeat

I have having some trouble utilizing the angular bootstrap-ui btn-checkbox directive and its interaction with a ng-repeat directive. The way the directive appears to be setup is that you have to manually name each individual model for a multi checkbox scenario, which is either not possible within an ng-repeat or I haven't found how to accomplish this.
I found an answer somewhat similar to this issue:
Setting and getting bootstrap radio button inside angular repeat loop
and forked the plunker to better explain exactly what I am seeing as a problem.
The plunker can be viewed:
http://plnkr.co/edit/ddiH78pzqE3fsSoq8gAr?p=preview
The answer you linked is the same solution for this problem. Each button within the repeat needs it's own unique property of the model. If they are all set to the same model, as in the plunk $scope.checkboxModel = {id: 0}, when one button is checked, they will all be checked.
So to give each button uniqueness, you could set another property onto the objects within the ng-repeat. This property would hold a boolean value that changes on check. So your model would look like:
$scope.companies = [{"id":2,"name":"A", truthy:false}] // and so on
You would not need to explicitly set this in the controller - just declare the new property right in the button element's model:
<companies ng-repeat="company in companies">
<button type="button" class="btn" ng-model="company.truthy"
btn-checkbox>{{company.name}}</button>
</companies>
Here's the plunk

Simple Example using Backbone.js and Rivets.js

I am looking for a very simple example where e.g. there is a two way binding between span text and an input element using Backbone.js and Rivets.js. Perhaps there is one in the Rivets.js docs, but I can't find it. Any help please?
Assuming that you mean a two-way binding (model-to-view and view-to-model) on an input element and a one-way binding (model-to-view) on a span element, then the following view will do what you describe.
<div id="user-view">
<span>{ user:name }</span>
<input rv-value="user:name">
</div>
Here is a fiddle that demonstrates things in action. It includes a Backbone adapter on the : interface and shows how to bind a model to the view (this is just a more trivial example of what is already shown on the homepage).
I recommend that you use:
https://github.com/theironcook/Backbone.ModelBinder
It can satisfy the two-way binding between the demand of all the view and model。
This is what I do nested view binding example:
http://files.cnblogs.com/justinw/Nested_Model_bi_Binding.zip

Resources