AngularJS/Bootstrap - Select row and open details in modal with button - angularjs

I'm using AngularJS, Bootstrap, and data-toggle to open a modal. I want to click on a row in a table, get the index number and store it, and click a button to open a modal that displays more details for that row using the stored index.
My code right now can get the index of the clicked row and my button opens a modal, but they're not connected so that the button grabs the row index and shows those details in the modal. My modal shows all row data instead of the details for the one clicked row. How can I connect the clicked row to the button and how do I get my modal to show details for one app instead of all apps? Any help would be much appreciated!
Here is my JS Fiddle.
Here is the code snippet for the click functions:
$scope.selectedRow = null;
$scope.clickRow = function(index) {
$scope.selectedRow = index;
console.log(index);
};
$scope.getDetails = function(index) {
$scope.selectedRow = index;
console.log(index);
};
And here is the code for my table and modal that call the click functions:
<div id="tableDiv">
<table id="myTable" class="table display">
<thead>
<tr>
<th ng-repeat="(i, th) in head" value="{{th.id}}" class="{{th.class}}"><span>{{th.name}}</span></th>
</tr>
</thead>
<tbody>
<tr ng-repeat="app in apps | filter:search" ng-click="clickRow($index)" ng-class="{selected: $index === selectedRow}">
<td>{{app.appName}}</td>
<td>{{app.dateCreated}}</td>
<td>{{app.dateUpdated}}</td>
<td>{{app.payload}}</td>
<td>{{app.status.name}}</td>
<td>{{app.errorCode.name}}</td>
<td>{{app.errorDesc}}</td>
</tr>
</tbody>
<tfoot>
<tr>
<th ng-repeat="(i, th) in head" value="{{th.id}}"><span>{{th.name}}</span></th>
</tr>
</tfoot>
</table>
</div>
<div id="details">
<button class="btn btn-default" data-toggle="modal" data-target="#myModal" ng-click="getDetails($index)">Launch</button>
<div class="modal fade" id="myModal" tabindex="-1" role="dialog"
aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal"
aria-hidden="true">×</button>
<h4 class="modal-title" id="myModalLabel">Details</h4>
</div>
<div class="modal-body">
<table class="table display">
<thead>
<tr>
<th ng-repeat="(i, th) in details" value="{{th.id}}"
class="{{th.class}}"><span>{{th.name}}</span></th>
</tr>
</thead>
<tbody>
<tr ng-repeat="app in apps">
<td>{{app.appName}}</td>
<td>{{app.errorDesc}}</td>
<td>{{app.recordCount}}</td>
<td>{{app.recordFail}}</td>
</tr>
</tbody>
</table>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
</div>
</div>
</div>
</div>
</div>

The first thing I'll point out is that you're not actually using angular-ui-bootstrap, you're using the jQuery version without angular directives, and by doing so making life harder for yourself. If you're going to do much more with this or making more modals I recommend switching.
You can still make this work though.
Instead of passing the $index in clickRow($index), pass the app itself clickRow(app) and assign that to your scope property.
It's a variable created in your ng-repeat loop that can be accessed by other expressions in the loop.
$scope.clickRow = function(app) {
$scope.selectedApp = app
};
Then, in your modal's html, you can bind to the properties of selectedApp. It should only show you the data for that one app.

Related

How to switch from one tab to another in angularjs?

How do i switch from one tab to another tab in angular js? I am using multiple divs for creating tabs. I want to switch from one tab to another by click on button.
This is part of my code -
<div ng-controller="MyController">
<div class="tabgroup" ng-init="tab=1">
<div class="tab" ng-class="{selected: tab==1}" ng-click="tab = 1">Home</div>
<div class="tab" ng-class="{selected: tab==2}" ng-click="tab = 2">Display Records</div>
<div class="tab" ng-class="{selected: tab==3}" ng-click="tab = 3">Add Records</div>
<div class="tab" ng-class="{selected: tab==4}" ng-click="tab = 4">Remove Records</div>
</div>
<div class="otherContainer">
<div class="tabcontents">
<div ng-show="tab == 1">
This application shows employee details registered for this site. You can add your records by clicking on add button. Also you can update and delete records.
</div>
<div ng-show="tab == 2">
<table border=1>
<thead>
<th>Id</th>
<th>Name</th>
<th>Birthdate</th>
<th>Address</th>
<th>Contact</th>
<th>Email</th>
</thead>
<tr data-ng-repeat="Emp in EmpList">
<td ng-bind="Emp.Id"></td>
<td ng-bind="Emp.Name"></td>
<td ng-bind="Emp.Birthdate"></td>
<td ng-bind="Emp.Address"></td>
<td ng-bind="Emp.Contact"></td>
<td ng-bind="Emp.Email"></td>
<th><input type="button" ng-click="removeItem()" value="Remove" /></th>
<th><input type="button" ng-click="editItem(i)" value="Edit" /></th>
</tr>
</table>
</div>
You can refer the following sample
//in your controller
// code to switch you views based on tabs
$scope.onep = true; // sets bydefault true on div
$scope.one = function() {
$scope.onep = true;
$scope.twop = false;
$scope.threep = false;
}
//follow as above for funcions two() and three()
//your tabs
<div ng-click=one()>
//div content
</div>
<div ng-click=two()>
//div content
</div>
<div ng-click=three()>
//div content
</div>
<p ng-show=onep></p>
<p ng-show=twop></p>
<p ng-show=threep></p>
Using JavaScript for this problem will easily solve the problem.
<div class="tab" data-target="#tab1" ng-class="{selected: tab==1}" ng-click="goToTab(1)">Home</div>
In your controller
$scope.goToTab = function(tabIndex) {
$scope.tab = tabIndex;
angular.element('[data-target="#tab'+tabIndex+'"]').tab('show');
}

Not update dataTable info

I have a class list. As you can see in the first picture, there are different numbers of students in each class.
1st class -> 3
2nd class -> 0
3rd class -> 1
When I click on '(3)', I use the variable "sinif" as $scope.sinif for use in modal. I list $scope.sinif.ogrenciler in modal with ng-repeat. When I click (3), the list is correct. But when I turn off modal and click (0), the info is not updated. Likewise when I click (1). How can we solve this.
This is my first list. After clicking on the following modal opens.
Modal
This problem here. Look info
This is My modal.
<!-- Modal -->
<div class="modal fade in" id="SinifOgrenci" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog modal-lg">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">×</button>
<h4 class="modal-title" id="myModalLabel"> {{this.sinif.sinifAdi}} - Öğrencileri </h4>
</div>
<div class="modal-body">
<table datatable-setups ng-if="sinif.ogrenciler" class="table table-bordered table-striped js-dataTable-full-pagination">
<thead>
<tr>
<th class="hidden-xs" style="width: 5%;"></th>
<th class="text-center">Öğrenci Adı Soyadı</th>
<th class="text-center">Yaş</th>
<th class="text-center">Boy</th>
<th class="text-center">Cinsiyet</th>
<!--<th class="text-center">Aktif / Pasif</th>-->
</tr>
</thead>
<tbody>
<tr ng-repeat="ogrenci in sinif.ogrenciler">
<td class="hidden-xs">{{this.ogrenci.id}}</td>
<td class="text-center">{{this.ogrenci.adSoyad}}</td>
<td class="text-center">{{this.ogrenci.yas}}</td>
<td class="text-center">{{this.ogrenci.boy}}</td>
<td class="text-center">{{this.ogrenci.cinsiyet}}</td>
</tr>
</tbody>
</table>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal"> Kapat </button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
My datatable directive
angular.module("app")
.directive('datatableSetups', ['$timeout', '$rootScope',
function ($timeout, $rootScope) {
return {
restrict: 'A',
link: function (scope, element) {
$timeout(function () {
element.dataTable({
pagingType: "full_numbers",
columnDefs: [],
pageLength: 10,
lengthMenu: [[5, 10, 15, 20], [5, 10, 15, 20]]
});
});
}
};
}
]);

How to disable button click until item selected/activated?

Trying to disable button in table. and enable it only when item selected/clicked/activated
button code
<td><a class="btn btn-info" ng-disabled="isDisabled">Edit</a></td>
disabled bool
$scope.isDisabled = false;
trying to enable button only when selected is true
$scope.selectedRow = false; // initialize our variable to null
$scope.setClickedRow = function(index) { //function that sets the value of selectedRow to current index
$scope.selectedRow = index;
$scope.isDisabled = true;
}
any help please?
http://plnkr.co/edit/llmcbXCA93kuTVTzpQlm?p=catalogue
the full table
<thead>
<tr>
<th class="hidden-xs">ID</th>
<th>Name</th>
<th>Date</th>
<th>Grade</th>
<th>Subject</th>
<th></th>
</tr>
</thead>
<tbody>
<tr ng-repeat="trainee in trainees | filter: search" ng-class="{'selected':$index == selectedRow}" ng-click="setClickedRow($index)">
<td class="hidden-xs">{{$index+1}}</td>
<td>{{trainee.name}}</td>
<td>{{trainee.date | date:'d/M/yyyy'}}</td>
<td>{{trainee.grade}}</td>
<td>{{trainee.subject}}</td>
<td><a class="btn btn-info">Edit</a></td>
</tr>
</tbody>
</table>
First make the plunk work!
You were referencing a file that didn't exist in the plunk, so had to change:
<script src="main.js"></script> to <script src="script.js"></script>.
Amend your ng-disabled directive:
Also had to add ng-disabled="selectedRow !== $index" on your link button:
<td><a class="btn btn-info" ng-disabled="selectedRow !== $index">Edit</a></td>
I don't think you need the $scope.disabled variable as the $scope.selectedRow along with $index takes care of enabling/disabling each edit button.
Prevent click events from bubbling up the DOM tree:
The ng-click on your tr tag will be triggered by any ng-click that you place on your edit link button, to fix that you have to add $event.stopPropagation(); after any function that you put there:
<a class="btn btn-info"
ng-disabled="selectedRow === $index"
ng-click="onEditButtonClicked(); $event.stopPropagation();">
Edit
</a>
Fix Invalid HTML Markup:
Moved the following up and out of the table:
<div class="form-inline">
<input class="form-control" type="text" placeholder="Search" ng-model="search">
<a type="button" href="#add-form" class="btn btn-info" ng-click="addForm()">Add new trainee</a>
<button class="btn btn-danger" ng-click="removeTrainee(trainee)">Remove</button>
</div>
Styles.css 404 not Found:
Last but not least styles.css doesn't exist and gets a 404 not found, and so the following can be removed: <link rel="stylesheet" href="styles.css">
Working Plunk

How to pass or reference item from ng-repeat to another element?

I want to pass a single item/object ('ca') from a repeater to another element (in this case a modal) within the same controller context:
<div data-ng-controller="ContactActionCtrl" data-ng-app="myApp" runat="server">
<div class="row">
<div class="col-sm-12">
<h2>Tasks</h2>
<table class="table">
<thead>
<tr>
<th>Created</th>
<th>Due</th>
<th>Completed</th>
<th>Created By</th>
<th>Assigned</th>
<th>Description</th>
</tr>
</thead>
<tbody data-ng-repeat="ca in contactactions | filter:{ObjectType:'Task'}">
<tr data-actionid="{{ca.Id}}" data-toggle="modal" data-target="#actionDetail">
<td>{{ca.CreationDate | date:"MM/dd/yyyy"}}</td>
<td>{{ca.ActionDate | date:"MM/dd/yyyy 'at' h:mma"}}</td>
<td>{{ca.CompletionDate | date:"MM/dd/yyyy"}}</td>
<td>{{ca.CreatedByUsername}}</td>
<td>{{ca.UserIDUsername}}</td>
<td><label data-ng-if="ca.ActionType">{{ca.ActionType}} - </label><label>{{ca.ActionDescription}}</label><br>{{ca.CreationNotes | limitTo:270}}</td>
</tr>
</tbody>
</table>
</div>
</div>
<div id="actionDetail" class="modal" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">×</button>
<h4 class="modal-title">{{ca.ActionDescription}}</h4>
</div>
<div class="modal-body">
//more details from ca here
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
</div>
</div>
</div>
</div>
Everything is working, including popping up the bootstrap modal div from a row click, except for actually populating it from outside of the repeater. Since the full object is still in memory, I was hoping to avoid fetching a singular item from the db again (with a different service call) in order to fill the modal. Even though I'm showing a modal, I think this question might apply to any element / set of elements that lie outside the repeater.
I think the most straight forward way for you would be to have the modal display a different single variable e.g. 'ca.selectedItem' then when you click on an item populate selectedItem with that object. I'll see if I can whip up an example.
Controller:
$scope.contactActions = [{name:"Action 1"},{name:"Action 2"},{name:"Action 3"}]
$scope.selectedAction = {name:""};
$scope.rowClick = function(event, selected) {
$scope.selectedAction = selected;
};
Markup:
<tr data-actionid="{{ca.Id}}" ng-click="ca.rowClick($event, i)" data-toggle="modal" data-target="#actionDetail">
Here's a plunk.
P.S. You can use bootstrap with Angular but it uses non-angular javascript (i.e. jquery) which bypasses Angular to do things like DOM manipulation. This often results in Angular not updating it's bindings properly, so you end up doing stuff like $scope.apply() to manually tell Angular to update all it's bindings. One alternative to this would be to use UI Bootstrap which uses the same css but the javascript has been re-implemented in Angular.

Angular JS ng-repeat and modal dialog

I am iterating over a list of students and each row has the student name and college and a button. On clicking the button you see a modal dialog which shows student details. For some reason I am unable to get the correct student information. The dialog just shows the 1'st student information only. Here is the pluker
http://plnkr.co/edit/kXB7OZuyOz57qyVMIu8T?p=preview
<div class="table-responsive">
<table class="table table-striped">
<tr ng-repeat = "student in students">
<td>{{student.name}}</td>
<td>{{student.college}}</td>
<td>
<div class="modal-header">
<button type="button" class="btn btn-primary"
data-toggle="modal" data-target="#dialogTestDialog">Options</button>
</div>
<div class="modal fade" id="dialogTestDialog" tabindex="-1" role="dialog" aria-labelledby="executionOptionLabel"
aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
Student : {{student.name}} <br/> Detail on Student
<div class="modal-body">
<p>{{student.age}}</p>
<p>{{student.address}}</p>
<p>{{student.race}}</p>
</div>
</div>
</div>
</div>
</td>
</tr>
</table>
</div>
The problem is that all your modals have the same id value, so this is not valid html. You need different id values so you can reference the correct one on click. eg: ng-click="showModal($index)"
I would check this out:
How to set the id attribute of a HTML element dynamically with angular js?
Also if you really want to play with bootstrap js and angular, you should use a version specific to angular: http://angular-ui.github.io/bootstrap
Check this version in Plunker: Working Version
To get the ng-repeat index value , you have to use {{ $index }} ng-repeat documentation
and to data-toggle should be the values specified in bootstrap Here

Resources