Properly toggle a hidden table to visible with angular-datatables? - angularjs

I have 2 tables, one displayed, the other one hidden:
<div ng-show="displayed('active')" ng-controller="DataTablesCtrlA as datatables">
<table datatable="" dt-columns="datatables.dtColumns" dt-options="datatables.dtOptions" class="display"></table>
</div>
<div ng-show="displayed('retired')" ng-controller="DataTablesCtrlB as datatables">
<table datatable="" dt-columns="datatables.dtColumns" dt-options="datatables.dtOptions" class="display"></table>
</div>
I have a toggle which controls the visibility of the tables, when button A is clicked, then table A is displayed and table B get hidden and vice-versa.
The issue I am facing is that when table B get displayed, the table header is not properly expanded. This is known and well explained on DataTables documention here.
Below a screenshot of the issue:
So I am using columns.adjust() like so:
In the View template:
<div class="btn-group">
<button ng-click="setDisplayed('active')"
ng-class="{active: displayed('active')}" class="btn btn-default">Active</button>
<button id="btn-retired" ng-click="setDisplayed('retired')"
ng-class="{active: displayed('retired')}" class="btn btn-default">Retired</button>
</div>
In the View controller:
//...
this.setDisplayed = function(toDisplay){
this.displayed = toDisplay;
$.fn.dataTable.tables( {visible: true, api: true} ).columns.adjust().draw();
};
//...
The issue I am facing is that table B is still hidden when setDisplayed get called and the header stay "unexpanded".
Is there a clean way to solve this problem ?
One solution I have in mind would be to listen for changes on the table display style attribute and call colums.adjust() in the event handler. But this would require to change the directive link property.

Related

Show/Hide all with show/hide sections inside angularjs

I need to have an overall Show/Hide click to show or hide all the detail divs of a list of "panels" of data. Also within each panel, there is a Show/Hide click to individually show or hide that div of data.
I think that if the overall show/hide is clicked that the individual click values should be set equal to overall value when clicked. That way if the individual ones are changed, they are all set to show or hide when the main one is clicked.
This is how I tried to do that:
<div>- Hide All Details / + Show All</div>
<div class="tender-list" ng-repeat="row in tenders" ng-include="'tender/tender_panel.html'"></div>
Where the hide/show part of tender_panel.html is here:
<div>- Hide Details</div>
<div class="tender-details" ng-hide="hideDetails">
<table width="100%" id="tender-bottom-table">
<tbody>
...
</tbody>
</table>
</div>
There is another table above the tender-bottom-table. Plus a another table after.
What is happening is that it works fine when initially loaded. The Hide All/Show All works. Then I click on the individual show/hides and they work. But then the All Show/All Hide no longer works and I don't see how clicking the individual links breaks things.
This app is Symfony2 with Angular and Bootstrap.
Any help would be greatly appreciated.
one thing you could try is to have a property flag in each tenders item that sets if it's shown/hidden and show the individual item based on if hideAllDetails + their flag is true:
<div>- <a href='#' ng-click="hideAllDetails = ! hideAllDetails;">Hide All
Details / + Show All</a></div>
<div class="tender-list" ng-repeat="row in tenders" ng-
include="'tender/tender_panel.html'"></div>
tender_panel.html:
<div>- <a href='#' ng-click="row.hideDetails = ! row.hideDetails">Hide
Details</a></div>
<div class="tender-details" ng-hide="hideDetails || hideAllDetails">
<table width="100%" id="tender-bottom-table">
<tbody>
...
</tbody>
</table>
</div>

How to use ng-repeat in multiple div's?

I am working with angularJS ng-repeat. So, I want to use my ng-repeat value in another div. I am doing the following. But it doesn't loop through and give me the exact value.
Code in ng-repeat
<div uib-slide index="$index" class="uibSlider" ng-repeat='id in code' ng-click="$parent.ContentId = id.ContentId" ng-class="{'selected' : ContentId.Id === ContentId}">
<paragraph tag>{{id.ContentId}}</paragraph tag>
</div>
Code in Another Div
<div>
<label>{{(code| filter: {Id: ContentId}: true)[1].ContentId}}</label>
</div>
So, the problem is I have bunch of data and in the another div if I make the array value from 0 to 1. i'm getting null value. But automatically the value isn't changing based on what I contentID select. It always gives me the same value. I'm not sure where I'm going wrong.
Any Help would be appreciated.
You can use ng-repeat-start | ng-repeat-end
<div uib-slide ng-repeat-start='id in code'>
<paragraph tag>{{id.ContentId}}</paragraph tag>
</div>
<div ng-repeat-end>
<label>{{(id.ContentId}}</label>
</div>
If you are trying to show the same data in a modal, depending where the user clicks:
<div ng-repeat="id in code">
<!-- when the user clicks here, the modal will open. The ID will be the same as the one clicking -->
<a ng-click="openModal(id)">Open modal for id: {{id}}</a>
</div>
Then in your controller you will have a function called openModal which takes a parameter (id) that will open the modal and pass along the data.

wj-popup in ng-repeat, Wijmo5 and AngularJS

I'm trying to make use of wj-popup inside an ng-repeat in an AngularJS application, but am having difficulty.
Basically, I've used the demo example for wj-popup and wrapped it in an ng-repeat as follows. I have an array of posts, each has a property that is its indexValue (post.indexValue).
Each button needs to have a different ID, so I expect that using post.indexValue should work, and it does set the button ID on each repetition correctly, but the calling function doesn't work and the popup doesn't appear, and I'm not sure what I'm doing wrong.
<div ng-repeat="post in posts">
Click to open, move focus away to close:
<button id="{{post.indexValue}}" type="button" class="btn">
Click
</button>
<wj-popup class="popover" owner="#{{post.indexValue}}" show-trigger="Click" hide-trigger="Blur">
<ng-include src="'includes/popup.htm'"></ng-include>
</wj-popup>
</div>
Issue is with id. Pop up is not working even if there is no ng-repeat and owner id starts with any number. Changing button id to "btn{{post.indexValue}}" worked for me. Try this fiddle.
<div ng-repeat="post in posts">
Click to open, move focus away to close:
<button id="btn{{post.indexValue}}" type="button" class="btn">
Click
</button>
<wj-popup class="popover" owner="#btn{{post.indexValue}}" show-trigger="Click" hide-trigger="Blur">
<ng-include src="'includes/popup.htm'"></ng-include>
</wj-popup>
</div>

Override ng-hide on ng-click

On the process of trying to learn angularjs, I am creating a set of divs using ng-repeat. I have five divs in all. I am only displaying the first div using $firstdirective component.
<div class="container" ng-app="demoApp" ng-controller="demoController">
<div class="row" ng-repeat="job in jobs" ng-hide="!$first">
<div class="col-md-4">
{{job}}
</div>
<div class="col-md-4">
<button class="btn-primary btn-xs add" ng-click="showNext($event)" ng-hide="$last">Add</button>
<button class="btn-primary btn-xs delete" style="display: none;">Delete</button>
</div>
</div>
</div>
That works.
Now, each div has two buttons, Add and Delete. When I click add I want to hide the add button and delete button of the current row and open the next row. So I wrote,
$scope.showNext = function(evt) {
var elm = evt.target;
$(elm).hide();
$(elm).next().hide();
$(elm).closest("div.row").next().slideDown();
};
This is not working as ng-hide is overriding my slideDown. What is the angularjs way of doing it?
Also I would like the delete button only on the $last visible row && !first. How to find last visible row in ng-repeat?
Fiddle: https://jsfiddle.net/codeandcloud/u4penpxw/
You shouldn't manipulate the DOM with things like $(elm).hide();, you should use ng-class= to let Angular add classes that hide or show the elements. If you switch your ng-repeat to ng-repeat="job in jobs track by $index", you could write something like that in your showNext()-function:
$scope.showNext = function(index) {
$scope.currentJob = $scope.jobs[index]
}
and call it like ng-click="showNext($index) - of course you'd need to do some refactoring as well. But then you could write something like ng-class="{hidden: (job == currentJob}" to hide all buttons except in the current row.
There's a lot of good thoughts in this q&a: "Thinking in AngularJS" if I have a jQuery background?

AngularJS with ui-router ng-hide not working after initially working

I've been struggling with a ng-hide issue in combination with using ui-router. Simple app. Index.html shows some data via the "notes" route, you click on "detail" and you go to the sub route "notes.note" to view the detail just below the other records. The "detail" html has a "Save" & "Cancel" button.
Now there is an "Add New" button when you are not viewing the detail with the attribute ng-hide="HideAddNew". "HideAddNew" is a $scope variable in the controller. When I click "detail" on a row I have this ng-click="toggleAddNew()" on the link which in turn calls this
$scope.toggleAddNew= function()
{
$scope.HideAddNew=($scope.HideAddNew ? false : true);
}
That works perfectly, my detail shows and my "Add New" button has disappeared. Now on the detail when I click "Cancel" it fire off the ng-click="hideData()" which calls the function:
$scope.hideData=function()
{
$scope.toggleAddNew();
$state.go('notes');
}
And now my "Add New" has disappeared even though the variable is set to false, i.e. Don't hide. I've tried $timeout in that "hideData" function and in the "toggleAddNew" function. I've tried putting "$scope.toggleAddNew();" after the "$state.go('notes');" too. I don't want to resort to manually adding and removing classes. AngularJS ver: v1.3.15 , ui-router ver: v0.2.13 Thanx all :)
EDIT
Would the below work Tony?
<button ng-if="HideAddNew" ng-click="SelectRoute('notenew')" class="btn btn-primary">
<span class="glyphicon glyphicon-plus -glyphicon-align-left"></span>Add New</button>
Perhaps you could simplify and use ng-switch instead.
Something like this:
<ul ng-switch="expression">
<li ng-switch-when="firstThing">my first thing</li>
<li ng-switch-when="secondThing">my second thing</li>
<li ng-switch-default>default</li>
</ul>
Alternatively, maybe you could use ng-if or ng-show instead of ng-hide, eg:
<p ng-if="HideAddNew">it's here!</p>
<p ng-if="!HideAddNew">it's not here.</p>
Edit
If I understand what you're trying to achieve exactly, I would use ng-show with an ng-click:
Controller:
$scope.addNew = false;
View:
<button ng-show="!addNew" ng-click="addNew = true">Add New</button>
<button ng-show="addNew" ng-click="save()">Save</button>
<button ng-show="addNew" ng-click="addNew = false">Cancel</button>
Example

Resources