← Back to team overview

dhis2-devs team mailing list archive

[Branch ~dhis2-devs-core/dhis2/trunk] Rev 16116: tracker capture - custom form in data entry; more organization of data in tei based report

 

------------------------------------------------------------
revno: 16116
committer: Abyot Asalefew Gizaw abyota@xxxxxxxxx
branch nick: dhis2
timestamp: Sun 2014-07-13 15:08:50 +0200
message:
  tracker capture - custom form in data entry; more organization of data in tei based report
removed:
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/eventDetails.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/teiReport.html
added:
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/custom-form.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/default-form.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/event-details.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/program-details.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/tei-report.html
modified:
  dhis-2/dhis-web/dhis-web-event-capture/src/main/webapp/dhis-web-event-capture/scripts/controllers.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dashboard/dashboard-controller.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry-controller.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/enrollment/enrollment.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/notes/notes-controller.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile-controller.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/relationship/relationship-controller.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report-controller.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report.html
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/i18n/en.json
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/directives.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/services.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/tracker-capture.js
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/styles/style.css
  dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/views/home.html


--
lp:dhis2
https://code.launchpad.net/~dhis2-devs-core/dhis2/trunk

Your team DHIS 2 developers is subscribed to branch lp:dhis2.
To unsubscribe from this branch go to https://code.launchpad.net/~dhis2-devs-core/dhis2/trunk/+edit-subscription
=== modified file 'dhis-2/dhis-web/dhis-web-event-capture/src/main/webapp/dhis-web-event-capture/scripts/controllers.js'
--- dhis-2/dhis-web/dhis-web-event-capture/src/main/webapp/dhis-web-event-capture/scripts/controllers.js	2014-07-06 12:46:18 +0000
+++ dhis-2/dhis-web/dhis-web-event-capture/src/main/webapp/dhis-web-event-capture/scripts/controllers.js	2014-07-13 13:08:50 +0000
@@ -479,7 +479,7 @@
             updatedEvent.notes = [{value: $scope.note.value}];
             
             if($scope.currentEvent.notes){
-                $scope.currentEvent.notes.splice(0,0,{value: $scope.note.value, storedDate: today, storedBy: ''});
+                $scope.currentEvent.notes.splice(0,0,{value: $scope.note.value, storedDate: today, storedBy: storedBy});
             }
             else{
                 $scope.currentEvent.notes = [{value: $scope.note.value, storedDate: today, storedBy: storedBy}];

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dashboard/dashboard-controller.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dashboard/dashboard-controller.js	2014-07-07 15:04:56 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dashboard/dashboard-controller.js	2014-07-13 13:08:50 +0000
@@ -20,7 +20,7 @@
     $rootScope.smallerDashboardWidgets = [];
     $rootScope.enrollmentWidget = {title: 'enrollment', view: "components/enrollment/enrollment.html", show: true, expand: true};
     $rootScope.dataentryWidget = {title: 'dataentry', view: "components/dataentry/dataentry.html", show: true, expand: true};
-    $rootScope.reportWidget = {title: 'report', view: "components/report/teiReport.html", show: true, expand: true};
+    $rootScope.reportWidget = {title: 'report', view: "components/report/tei-report.html", show: true, expand: true};
     $rootScope.selectedWidget = {title: 'current_selections', view: "components/selected/selected.html", show: false, expand: true};
     $rootScope.profileWidget = {title: 'profile', view: "components/profile/profile.html", show: true, expand: true};
     $rootScope.relationshipWidget = {title: 'relationships', view: "components/relationship/relationship.html", show: true, expand: true};

=== added file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/custom-form.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/custom-form.html	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/custom-form.html	2014-07-13 13:08:50 +0000
@@ -0,0 +1,1 @@
+<d2-custom-form custom-form-type="PROGRAM_STAGE" custom-form-object="currentStage"></d2-custom-form>
\ No newline at end of file

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry-controller.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry-controller.js	2014-07-07 15:04:56 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry-controller.js	2014-07-13 13:08:50 +0000
@@ -14,6 +14,16 @@
 
     TranslationService.translate();
     
+    //Data entry form
+    $scope.dataEntryOuterForm = {};
+    $scope.displayCustomForm = false;
+    $scope.currentElement = {};
+    
+    var loginDetails = storage.get('LOGIN_DETAILS');
+    var storedBy = '';
+    if(loginDetails){
+        storedBy = loginDetails.userCredentials.username;
+    }
     var today = moment();
     today = Date.parse(today);
     today = $filter('date')(today, 'yyyy-MM-dd');
@@ -229,54 +239,65 @@
         }
     }; 
     
-    $scope.getDataEntryForm = function(){        
-        
-        DHIS2EventFactory.get($scope.currentEvent.event).then(function(data){
-            $scope.currentEvent = data;
-            $scope.currentEvent.providedElsewhere = [];
-            
-            $scope.currentEvent.dueDate = DateUtils.format($scope.currentEvent.dueDate);
-            $scope.currentEvent.eventDate = DateUtils.format($scope.currentEvent.eventDate);
-            
-            if(!angular.isUndefined( $scope.currentEvent.notes)){
-                $scope.currentEvent.notes = orderByFilter($scope.currentEvent.notes, '-storedDate');            
-                angular.forEach($scope.currentEvent.notes, function(note){
-                    note.storedDate = moment(note.storedDate).format('DD.MM.YYYY @ hh:mm A');
-                });
-            }
-            
-            ProgramStageFactory.get($scope.currentEvent.programStage).then(function(stage){
-                $scope.currentStage = stage;
-
-                $scope.allowProvidedElsewhereExists = false;
-                angular.forEach($scope.currentStage.programStageDataElements, function(prStDe){
-                    $scope.currentStage.programStageDataElements[prStDe.dataElement.id] = prStDe.dataElement;
-                    if(prStDe.allowProvidedElsewhere){
-                        $scope.allowProvidedElsewhereExists = true;
-                        $scope.currentEvent.providedElsewhere[prStDe.dataElement.id] = '';   
-                    }                
-                });
-                angular.forEach($scope.currentEvent.dataValues, function(dataValue){
-                    var val = dataValue.value;
-                    if(val){
-                        var de = $scope.currentStage.programStageDataElements[dataValue.dataElement];
-                        if( de && de.type === 'int' && val){
-                            val = parseInt(val);
-                            dataValue.value = val;
-                        }
-                        $scope.currentEvent[dataValue.dataElement] = val;
-                    }                    
-                });
-
-                $scope.currentEvent.dataValues = [];
-                $scope.currentEventOriginal = angular.copy($scope.currentEvent);
-            });            
-        });            
-        
+    $scope.switchDataEntryForm = function(){
+        $scope.displayCustomForm = !$scope.displayCustomForm;
+    };
+    
+    $scope.getDataEntryForm = function(){ 
+        
+        $scope.currentEvent.providedElsewhere = [];
+
+        $scope.currentEvent.dueDate = DateUtils.format($scope.currentEvent.dueDate);
+        $scope.currentEvent.eventDate = DateUtils.format($scope.currentEvent.eventDate);
+
+        if(!angular.isUndefined( $scope.currentEvent.notes)){
+            $scope.currentEvent.notes = orderByFilter($scope.currentEvent.notes, '-storedDate');            
+            angular.forEach($scope.currentEvent.notes, function(note){
+                note.storedDate = moment(note.storedDate).format('DD.MM.YYYY @ hh:mm A');
+            });
+        }
+
+        ProgramStageFactory.get($scope.currentEvent.programStage).then(function(stage){
+            $scope.currentStage = stage;
+
+            $scope.programStageDataElements = [];                  
+            angular.forEach($scope.currentStage.programStageDataElements, function(prStDe){
+                $scope.programStageDataElements[prStDe.dataElement.id] = prStDe; 
+            }); 
+
+            $scope.customForm = $scope.currentStage.dataEntryForm ? $scope.currentStage.dataEntryForm.htmlCode : null; 
+            $scope.displayCustomForm = $scope.customForm ? true:false;
+
+            $scope.allowProvidedElsewhereExists = false;
+            angular.forEach($scope.currentStage.programStageDataElements, function(prStDe){
+                $scope.currentStage.programStageDataElements[prStDe.dataElement.id] = prStDe.dataElement;
+                if(prStDe.allowProvidedElsewhere){
+                    $scope.allowProvidedElsewhereExists = true;
+                    $scope.currentEvent.providedElsewhere[prStDe.dataElement.id] = '';   
+                }                
+            });
+
+            angular.forEach($scope.currentEvent.dataValues, function(dataValue){
+                var val = dataValue.value;
+                if(val){
+                    var de = $scope.currentStage.programStageDataElements[dataValue.dataElement];
+                    if( de && de.type === 'int' && val){
+                        val = parseInt(val);
+                        dataValue.value = val;
+                    }
+                    $scope.currentEvent[dataValue.dataElement] = val;
+                }                    
+            });
+
+            $scope.currentEvent.dataValues = [];
+            $scope.currentEventOriginal = angular.copy($scope.currentEvent);
+        });
     };
     
     $scope.saveDatavalue = function(prStDe){
         
+        $scope.currentElement = {};
+        
         //check for input validity
         $scope.dataEntryOuterForm.submitted = true;        
         if( $scope.dataEntryOuterForm.$invalid ){
@@ -321,8 +342,7 @@
         $scope.updateSuccess = false;
         
         if(!angular.isUndefined($scope.currentEvent.providedElsewhere[prStDe.dataElement.id])){
-            
-            console.log('the event is:  ',$scope.currentEvent.providedElsewhere[prStDe.dataElement.id]);
+
             //currentEvent.providedElsewhere[prStDe.dataElement.id];
             var value = $scope.currentEvent[prStDe.dataElement.id];
             var ev = {  event: $scope.currentEvent.event,
@@ -387,10 +407,10 @@
             var newNote = {value: $scope.note};
 
             if(angular.isUndefined( $scope.currentEvent.notes) ){
-                $scope.currentEvent.notes = [newNote];
+                $scope.currentEvent.notes = [{value: $scope.note, storedDate: today, storedBy: storedBy}];
             }
             else{
-                $scope.currentEvent.notes.splice(0,0,newNote);
+                $scope.currentEvent.notes.splice(0,0,{value: $scope.note, storedDate: today, storedBy: storedBy});
             }
 
             var e = {event: $scope.currentEvent.event,
@@ -401,24 +421,32 @@
                      notes: [newNote]
                     };
 
-            console.log('the notes before update are:  ', $scope.currentEvent);
             DHIS2EventFactory.updateForNote(e).then(function(data){
                 $scope.note = '';                
             });
         }        
     };    
     
-    $scope.getClass = function(id){
-        if($scope.currentElement){
+    $scope.getInputNotifcationClass = function(id, custom){
+        if($scope.currentElement.id){
             if($scope.currentElement.saved && ($scope.currentElement.id === id)){
+                if(custom){
+                    return 'input-success';
+                }
                 return 'form-control input-success';
             }            
             if(!$scope.currentElement.saved && ($scope.currentElement.id === id)){
+                if(custom){
+                    return 'input-error';
+                }
                 return 'form-control input-error';
             }            
-        }        
-        return 'form-control';      
-    };
+        }  
+        if(custom){
+            return '';
+        }
+        return 'form-control';
+    };  
     
     $scope.closeEventCreation = function(){
         $scope.currentDummyEvent = null;

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry.html	2014-07-08 08:30:39 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/dataentry.html	2014-07-13 13:08:50 +0000
@@ -86,84 +86,18 @@
                     <input type="text" name="dueDate" class="form-control" ng-date ng-model="currentEvent.dueDate" ng-disabled="true"/>
                 </div>                        
             </div>
-            <hr>
-            <form name="dataEntryOuterForm" novalidate>                
-                <table class="table-borderless table-striped" ng-if='currentEvent'>
-                    <thead>
-                        <tr class="col-md-12">
-                            <th class="col-md-5">
-                                {{'data_element'| translate}}
-                            </th>
-                            <th class="col-md-5 align-center">
-                                {{'value'| translate}}
-                            </th>
-                            <th class="col-md-2 align-center" ng-if="allowProvidedElsewhereExists">
-                                {{'provided_elsewhere'| translate}}
-                            </th>
-                        </tr>
-                    </thead>
-                    <tr class="col-md-12" ng-repeat="prStDe in currentStage.programStageDataElements">
-                        <td class="col-md-5">
-                            {{prStDe.dataElement.formName ? prStDe.dataElement.formName : prStDe.dataElement.name}}
-                        </td>
-                        <td class="col-md-5">
-                            <ng-form name="dataEntryInnerForm">
-                                <div ng-switch="prStDe.dataElement.type">
-                                    <div ng-switch-when="int">
-                                        <input type="number"
-                                               ng-class='getClass(prStDe.dataElement.id)'
-                                               ng-model="currentEvent[prStDe.dataElement.id]" 
-                                               ng-required={{prStDe.compulsory}}
-                                               ng-blur="saveDatavalue(prStDe)" 
-                                               name="foo"/>
-                                        <span ng-show="dataEntryOuterForm.submitted && dataEntryInnerForm.foo.$invalid" class="error">{{'number_required'| translate}}</span>
-                                    </div>
-                                    <div ng-switch-when="string">    
-                                        <input type="text"
-                                               ng-class='getClass(prStDe.dataElement.id)'
-                                               ng-model="currentEvent[prStDe.dataElement.id]" 
-                                               ng-required={{prStDe.compulsory}} 
-                                               typeahead="option for option in prStDe.dataElement.optionSet.options | filter:$viewValue | limitTo:20" 
-                                               typeahead-open-on-focus    
-                                               ng-blur="saveDatavalue(prStDe)" 
-                                               name="foo"/>
-                                    </div>
-                                    <div ng-switch-when="bool">
-                                        <select ng-class='getClass(prStDe.dataElement.id)'
-                                                ng-model="currentEvent[prStDe.dataElement.id]" 
-                                                ng-required={{prStDe.compulsory}} 
-                                                ng-change="saveDatavalue(prStDe)" 
-                                                name="foo">
-                                            <option value="">{{'please_select'| translate}}</option>                        
-                                            <option value="0">{{'no'| translate}}</option>
-                                            <option value="1">{{'yes'| translate}}</option>
-                                        </select>
-
-                                    </div>
-                                    <div ng-switch-when="date">
-                                        <input type="text" 
-                                               placeholder="yyyy-mm-dd" 
-                                               ng-date 
-                                               ng-class='getClass(prStDe.dataElement.id)'
-                                               ng-model="currentEvent[prStDe.dataElement.id]"
-                                               ng-required={{prStDe.compulsory}}  
-                                               blur-or-change="saveDatavalue(dhis2Event, eventGridColumn.id)"
-                                               name="foo"/>
-                                    </div>
-                                </div>
-                            </ng-form>                            
-                        </td>
-                        <td class="col-md-2" ng-if="allowProvidedElsewhereExists">                    
-                            <div class="align-center" ng-show="prStDe.allowProvidedElsewhere">
-                                <input type="checkbox" 
-                                       ng-model="currentEvent.providedElsewhere[prStDe.dataElement.id]"
-                                       ng-change="saveDatavalueLocation(prStDe)"/>
-                            </div>
-                        </td>
-                    </tr>
-                </table>
-            </form>
-            <hr>
+            <div class='row'><hr></div>
+            <div class='col-md-12' ng-if="customForm">
+                <a href ng-click="switchDataEntryForm()" title="{{displayCustomForm ? 'default_form' : 'custom_form'| translate}}"><span class="primary pull-right"><i class="fa fa-file-text fa-2x"></i></span></a>                
+                <!--<button type="button" class="btn btn-default pull-right" ng-click="switchDataEntryForm()">
+                    {{displayCustomForm ? 'default_form' : 'custom_form'| translate}}
+                </button>--> 
+            </div>
+
+            <div class="vertical-spacing" ng-if="displayCustomForm" ng-include="'components/dataentry/custom-form.html'"></div>  
+            <div class="vertical-spacing" ng-if="!displayCustomForm" ng-include="'components/dataentry/default-form.html'"></div>
+
+            <div class='row'><hr></div>
             <div class="row">
                 <div class="col-md-10">
                     <textarea class="form-control" rows="3" ng-model="note" placeholder="{{'add_your_note_here'| translate}}"></textarea>
@@ -176,23 +110,23 @@
                     </button>
                 </div>
 
-                <table class="table table-with-fixed-layout">
+                <table class="table table-striped dhis2-table-hover">
                     <tr ng-repeat="note in currentEvent.notes">
                         <td class="over-flow-hidden">
-                    <d2-pop-over content="note" template="note.html" details="{{'details'| translate}}">
-                        <div>{{note.value}}</div>
-                    </d2-pop-over>
-                    <script type="text/ng-template" id="note.html">
-                        <p>{{content.value}}</p>
-                        <hr>
-                        <p><strong>{{'created_by' | translate}}: </strong>{{content.storedBy}}</p>
-                        <p><strong>{{'date' | translate}}: </strong>{{content.storedDate}}</p>                           
-                    </script>
-                    </td> 
+                            <d2-pop-over content="note" template="note.html" details="{{'details'| translate}}">
+                                <div>{{note.value}}</div>
+                            </d2-pop-over>
+                            <script type="text/ng-template" id="note.html">
+                                <p>{{content.value}}</p>
+                                <hr>
+                                <p><strong>{{'created_by' | translate}}: </strong>{{content.storedBy}}</p>
+                                <p><strong>{{'date' | translate}}: </strong>{{content.storedDate}}</p>                           
+                            </script>
+                        </td> 
                     </tr>
                 </table>
             </div>
-            <hr>
+            <div class='row'><hr></div>
             <div class="form-group">
                 <div class="btn-group btn-group-justified">
                     <a href ng-click="completeEvent()" class="btn btn-info" ng-disabled="currentEvent.status !== 'ACTIVE'">{{'complete'| translate}}</a>

=== added file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/default-form.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/default-form.html	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/dataentry/default-form.html	2014-07-13 13:08:50 +0000
@@ -0,0 +1,85 @@
+<form name="dataEntryOuterForm" novalidate>                
+    <table class="table-borderless table-striped" ng-if='currentEvent'>
+        <thead>
+            <tr class="col-md-12">
+                <th class="col-md-5">
+                    {{'data_element'| translate}}
+                </th>
+                <th class="col-md-5 align-center">
+                    {{'value'| translate}}
+                </th>
+                <th class="col-md-2 align-center" ng-if="allowProvidedElsewhereExists">
+                    {{'provided_elsewhere'| translate}}
+                </th>
+            </tr>
+        </thead>
+        <tr class="col-md-12" ng-repeat="prStDe in currentStage.programStageDataElements">
+            <td class="col-md-5">
+                {{prStDe.dataElement.formName ? prStDe.dataElement.formName : prStDe.dataElement.name}}
+            </td>
+            <td class="col-md-5">
+                <ng-form name="dataEntryInnerForm">
+                    <div ng-switch="prStDe.dataElement.type">
+                        <div ng-switch-when="int">
+                            <input type="number"
+                                   ng-class='getInputNotifcationClass(prStDe.dataElement.id,false)'
+                                   ng-model="currentEvent[prStDe.dataElement.id]" 
+                                   ng-required={{prStDe.compulsory}}
+                                   ng-blur="saveDatavalue(prStDe)" 
+                                   name="foo"/>
+                            <span ng-show="dataEntryOuterForm.submitted && dataEntryInnerForm.foo.$invalid" class="error">{{'number_required'| translate}}</span>
+                        </div>
+                        <div ng-switch-when="string">    
+                            <input type="text"
+                                   ng-class='getInputNotifcationClass(prStDe.dataElement.id,false)'
+                                   ng-model="currentEvent[prStDe.dataElement.id]" 
+                                   ng-required={{prStDe.compulsory}} 
+                                   typeahead="option for option in prStDe.dataElement.optionSet.options | filter:$viewValue | limitTo:20" 
+                                   typeahead-open-on-focus    
+                                   ng-blur="saveDatavalue(prStDe)" 
+                                   name="foo"/>
+                        </div>
+                        <div ng-switch-when="bool">
+                            <select ng-class='getInputNotifcationClass(prStDe.dataElement.id,false)'
+                                    ng-model="currentEvent[prStDe.dataElement.id]" 
+                                    ng-required={{prStDe.compulsory}} 
+                                    ng-change="saveDatavalue(prStDe)" 
+                                    name="foo">
+                                <option value="">{{'please_select'| translate}}</option>                        
+                                <option value="0">{{'no'| translate}}</option>
+                                <option value="1">{{'yes'| translate}}</option>
+                            </select>
+
+                        </div>
+                        <div ng-switch-when="date">
+                            <input type="text" 
+                                   placeholder="yyyy-mm-dd" 
+                                   ng-date 
+                                   ng-class='getInputNotifcationClass(prStDe.dataElement.id,false)'
+                                   ng-model="currentEvent[prStDe.dataElement.id]"
+                                   ng-required={{prStDe.compulsory}}  
+                                   blur-or-change="saveDatavalue(prStDe)"
+                                   name="foo"/>
+                        </div>
+                        <div ng-switch-when="trueOnly">
+                            <input type="checkbox"                         
+                                   ng-class='getInputNotifcationClass(prStDe.dataElement.id,false)'
+                                   ng-model="currentEvent[prStDe.dataElement.id]"                                                               
+                                   ng-required={{prStDe.compulsory}}
+                                   ng-change="saveDatavalue(prStDe)" 
+                                   name="foo"/>
+                            <span ng-show="outerForm.submitted && innerForm.foo.$invalid" class="required">{{'required'| translate}}</span>
+                        </div>
+                    </div>
+                </ng-form>                            
+            </td>
+            <td class="col-md-2" ng-if="allowProvidedElsewhereExists">                    
+                <div class="align-center" ng-show="prStDe.allowProvidedElsewhere">
+                    <input type="checkbox" 
+                           ng-model="currentEvent.providedElsewhere[prStDe.dataElement.id]"
+                           ng-change="saveDatavalueLocation(prStDe)"/>
+                </div>
+            </td>
+        </tr>
+    </table>
+</form>

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/enrollment/enrollment.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/enrollment/enrollment.html	2014-07-02 20:53:29 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/enrollment/enrollment.html	2014-07-13 13:08:50 +0000
@@ -21,7 +21,7 @@
                     </td>
                 </tr>
             </table>
-            <hr>
+            <div class='row'><hr></div>
             <table class="table-borderless table-striped">
                 <thead>
                     <tr class="col-md-12">
@@ -42,7 +42,6 @@
                     </td>
                 </tr>
             </table>
-
             <div class="vertical-spacing small-horizonal-spacing">
                 <button type="button" 
                         class="btn btn-primary"
@@ -86,7 +85,7 @@
                         </td>
                     </tr>
                 </table>
-                <hr>
+                <hr ng-if='attributesForEnrollment'>
                 <table class="table-borderless table-striped">
                     <tr class="col-md-12" ng-repeat="attribute in attributesForEnrollment">
                         <td class="col-md-6">
@@ -135,7 +134,7 @@
                     </tr>                        
                 </table>
 
-                <div class="vertical-spacing small-horizonal-spacing">            
+                <div class="vertical-spacing col-md-12">            
                     <button type="button" 
                             class="btn btn-primary"
                             ng-click="enroll()">

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/notes/notes-controller.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/notes/notes-controller.js	2014-07-09 12:49:49 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/notes/notes-controller.js	2014-07-13 13:08:50 +0000
@@ -1,6 +1,8 @@
 trackerCapture.controller('NotesController',
         function($scope,
                 $rootScope,
+                $filter,
+                storage,
                 EnrollmentService,
                 CurrentSelection,
                 orderByFilter,
@@ -8,6 +10,16 @@
 
     TranslationService.translate();
     
+    var loginDetails = storage.get('LOGIN_DETAILS');
+    var storedBy = '';
+    if(loginDetails){
+        storedBy = loginDetails.userCredentials.username;
+    }
+    
+    var today = moment();
+    today = Date.parse(today);
+    today = $filter('date')(today, 'yyyy-MM-dd');
+    
     $scope.$on('notesController', function(event, args) {
         $scope.selectedEnrollment = null;
         var selections = CurrentSelection.get();
@@ -38,10 +50,11 @@
             var newNote = {value: $scope.note};
 
             if(angular.isUndefined( $scope.selectedEnrollment.notes) ){
-                $scope.selectedEnrollment.notes = [newNote];
+                $scope.selectedEnrollment.notes = [{value: $scope.note, storedDate: today, storedBy: storedBy}];
+                
             }
             else{
-                $scope.selectedEnrollment.notes.splice(0,0,newNote);
+                $scope.selectedEnrollment.notes.splice(0,0,{value: $scope.note, storedDate: today, storedBy: storedBy});
             }
 
             var e = $scope.selectedEnrollment;

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile-controller.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile-controller.js	2014-07-04 10:10:13 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile-controller.js	2014-07-13 13:08:50 +0000
@@ -26,69 +26,15 @@
         $scope.selectedTei = angular.copy(selections.tei);
         $scope.trackedEntity = selections.te;
         $scope.selectedProgram = selections.pr;   
-        $scope.selectedEnrollment = selections.enrollment;   
+        $scope.selectedEnrollment = selections.enrollment;  
         
-        $scope.processTeiAttributes();
+        //display only those attributes that belong the selected program
+        //if no program, display attributesInNoProgram
+        TEIService.processAttributes($scope.selectedTei, $scope.selectedProgram, $scope.selectedEnrollment).then(function(tei){
+            $scope.selectedTei = tei;            
+        });
     });
     
-    //display only those attributes that belong the selected program
-    //if no program, display attributesInNoProgram
-    $scope.processTeiAttributes = function(){        
- 
-        if($scope.selectedTei.attributes){
-            if($scope.selectedProgram && $scope.selectedEnrollment){
-                //show attribute for selected program and enrollment
-                AttributesFactory.getByProgram($scope.selectedProgram).then(function(atts){    
-                    $scope.selectedTei.attributes = $scope.showRequiredAttributes(atts,$scope.selectedTei.attributes, true);
-                }); 
-            }
-            if($scope.selectedProgram && !$scope.selectedEnrollment){
-                //show attributes for selected program            
-                AttributesFactory.getByProgram($scope.selectedProgram).then(function(atts){    
-                    $scope.selectedTei.attributes = $scope.showRequiredAttributes(atts,$scope.selectedTei.attributes, false);
-                }); 
-            }
-            if(!$scope.selectedProgram && !$scope.selectedEnrollment){
-                //show attributes in no program            
-                AttributesFactory.getWithoutProgram().then(function(atts){                
-                    $scope.selectedTei.attributes = $scope.showRequiredAttributes(atts,$scope.selectedTei.attributes, false);                
-                });
-            }
-        }              
-    };
-    
-    $scope.showRequiredAttributes = function(requiredAttributes, teiAttributes, fromEnrollment){        
-       
-        //first reset teiAttributes
-        for(var j=0; j<teiAttributes.length; j++){
-            teiAttributes[j].show = false;
-            if(teiAttributes[j].type === 'number' && !isNaN(parseInt(teiAttributes[j].value))){
-                teiAttributes[j].value = parseInt(teiAttributes[j].value);
-            }
-        }
-        
-        //identify which ones to show
-        for(var i=0; i<requiredAttributes.length; i++){
-            var processed = false;
-            for(var j=0; j<teiAttributes.length && !processed; j++){
-                if(requiredAttributes[i].id === teiAttributes[j].attribute){                    
-                    processed = true;
-                    teiAttributes[j].show = true;
-                    teiAttributes[j].order = i;
-                }
-            }
-
-            if(!processed && fromEnrollment){//attribute was empty, so a chance to put some value
-                teiAttributes.push({show: true, order: i, attribute: requiredAttributes[i].id, displayName: requiredAttributes[i].name, type: requiredAttributes[i].valueType, value: ''});
-            }                   
-        }
-        
-        teiAttributes = orderByFilter(teiAttributes, '-order');
-        teiAttributes.reverse();
-        
-        return teiAttributes;
-    };
-    
     $scope.enableEdit = function(){
         $scope.entityAttributes = angular.copy($scope.selectedTei.attributes);
         $scope.editProfile = !$scope.editProfile; 

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile.html	2014-07-09 09:33:55 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/profile/profile.html	2014-07-13 13:08:50 +0000
@@ -1,6 +1,6 @@
 <div class="panel panel-default" ng-controller="ProfileController">
     <div class="panel-heading handle bold">
-        {{trackedEntity.name || 'entity' | translate}} {{profileWidget.title| translate}}
+        {{profileWidget.title| translate}}
         <span class="nav-pills" ng-show="selectedTei.attributes.length">
             | <a href ng-click="enableEdit()" title="{{'edit_profile'| translate}}"><span class="bold">{{'edit'| translate}}</span></a>
         </span>

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/relationship/relationship-controller.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/relationship/relationship-controller.js	2014-07-07 11:46:45 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/relationship/relationship-controller.js	2014-07-13 13:08:50 +0000
@@ -30,7 +30,7 @@
         var modalInstance = $modal.open({
             templateUrl: 'components/relationship/add-relationship.html',
             controller: 'AddRelationshipController',
-            windowClass: 'relationship-modal-window',
+            windowClass: 'modal-full-window',
             resolve: {
                 relationshipTypes: function () {
                     return $scope.relationshipTypes;

=== added file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/event-details.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/event-details.html	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/event-details.html	2014-07-13 13:08:50 +0000
@@ -0,0 +1,74 @@
+<div class="modal-header">
+    <h2>{{'details'| translate}}</h2>
+</div>
+<div class="modal-body">
+    <div class='row' ng-if="reportMode === 'PROGRAM'">
+        <span class="bold">
+            {{entityName}}
+        </span>
+        <table class="table-borderless table-striped">
+            <tr class="col-md-12" ng-repeat="gridColumn in gridColumns">
+                <td class="col-md-6">
+                    {{gridColumn.name}}
+                </td>
+                <td class="col-md-6">
+                    <input type="text" ng-model="selectedTei[gridColumn.id]" ng-disabled='true'/>                       
+                </td>                
+            </tr>
+        </table>
+    </div>
+    <div class='row' ng-if='currentEvent'>      
+        <hr ng-if="reportMode === 'PROGRAM'">
+        <span class="bold">
+            <span ng-if="reportMode === 'TEI'">{{currentEvent.programName}}  |  </span>{{currentEvent.name}}  |  {{currentEvent.orgUnitName}}  |  {{currentEvent.eventDate}}
+        </span>
+        <table class="table-borderless table-striped">
+            <thead>
+                <tr class="col-md-12">
+                    <th class="col-md-5">
+                        {{'data_element'| translate}}
+                    </th>
+                    <th class="col-md-5">
+                        {{'value'| translate}}
+                    </th>
+                    <th class="col-md-2" ng-if="allowProvidedElsewhereExists">
+                        {{'provided_elsewhere'| translate}}
+                    </th>
+                </tr>
+            </thead>
+            <tr class="col-md-12" ng-repeat="prStDe in currentStage.programStageDataElements">
+                <td class="col-md-5">
+                    {{prStDe.dataElement.formName ? prStDe.dataElement.formName : prStDe.dataElement.name}}
+                </td>
+                <td class="col-md-5">
+                    <input type="text" ng-model="currentEvent[prStDe.dataElement.id]" ng-disabled='true'/>                       
+                </td>
+                <td class="col-md-2" ng-if="allowProvidedElsewhereExists">                    
+                    <div class="align-center" ng-show="prStDe.allowProvidedElsewhere">
+                        <input type="checkbox" ng-model="currentEvent.providedElsewhere[prStDe.dataElement.id]" ng-disabled='true'/>
+                    </div>
+                </td>
+            </tr>
+        </table>
+    </div>
+    <div class="row" ng-if='currentEvent.notes'>
+        <hr>
+        <table class="table-borderless table-striped">  
+            <tr>
+                <th>
+                    {{'notes' | translate}}
+                </th>
+            </tr>
+            <tr class="col-md-12" ng-repeat="note in currentEvent.notes">
+                <td class="col-md-12 over-flow-hidden" style="width:100%;">
+                    <p>{{note.value}}</p>
+                    <p><strong>{{'created_by' | translate}}: </strong>{{note.storedBy}}</p>
+                    <p><strong>{{'date' | translate}}: </strong>{{note.storedDate}}</p>                    
+                </td>                    
+            </tr>
+        </table>
+    </div>
+</div>
+<div class="modal-footer">
+    <button class="btn btn-default" data-ng-click="close()">{{'close'| translate}}</button>
+</div>
\ No newline at end of file

=== removed file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/eventDetails.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/eventDetails.html	2014-07-09 12:49:49 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/eventDetails.html	1970-01-01 00:00:00 +0000
@@ -1,83 +0,0 @@
-<div class="modal-header">
-    <h2>{{'details'| translate}}</h2>
-</div>
-<div class="modal-body">
-    <div class='row' ng-if="reportMode === 'PROGRAM'">
-        <table class="table-borderless table-striped">
-            <tr>
-                <th colspan="2">
-                    {{entityName}}
-                </th>
-            </tr>
-            <tr class="col-md-12" ng-repeat="gridColumn in gridColumns">
-                <td class="col-md-6">
-                    {{gridColumn.name}}
-                </td>
-                <td class="col-md-6">
-                    <input type="text" ng-model="selectedTei[gridColumn.id]" ng-disabled='true'/>                       
-                </td>                
-            </tr>
-        </table>
-    </div>
-    <div class='row' ng-if='currentEvent'>      
-        <hr ng-if="reportMode === 'PROGRAM'">
-        <span class="bold">
-            <span ng-if="reportMode === 'TEI'">{{currentEvent.programName}}  |  </span>{{currentEvent.name}}  |  {{currentEvent.orgUnitName}}  |  {{currentEvent.eventDate}}
-        </span>
-        <table class="table-borderless table-striped">
-            <thead>
-                <tr class="col-md-12">
-                    <th class="col-md-5">
-                        {{'data_element'| translate}}
-                    </th>
-                    <th class="col-md-5">
-                        {{'value'| translate}}
-                    </th>
-                    <th class="col-md-2" ng-if="allowProvidedElsewhereExists">
-                        {{'provided_elsewhere'| translate}}
-                    </th>
-                </tr>
-            </thead>
-            <tr class="col-md-12" ng-repeat="prStDe in currentStage.programStageDataElements">
-                <td class="col-md-5">
-                    {{prStDe.dataElement.formName ? prStDe.dataElement.formName : prStDe.dataElement.name}}
-                </td>
-                <td class="col-md-5">
-                    <input type="text" ng-model="currentEvent[prStDe.dataElement.id]" ng-disabled='true'/>                       
-                </td>
-                <td class="col-md-2" ng-if="allowProvidedElsewhereExists">                    
-                    <div class="align-center" ng-show="prStDe.allowProvidedElsewhere">
-                        <input type="checkbox" ng-model="currentEvent.providedElsewhere[prStDe.dataElement.id]" ng-disabled='true'/>
-                    </div>
-                </td>
-            </tr>
-        </table>
-    </div>
-    <div class="row" ng-if='currentEvent.notes'>
-            <hr>
-            <table class="table-borderless table-striped dhis2-table-hover">  
-                <tr>
-                    <th>
-                        {{'notes' | translate}}
-                    </th>
-                </tr>
-                <tr class="col-md-12" ng-repeat="note in currentEvent.notes">
-                    <td class="over-flow-hidden">
-                        <d2-pop-over content="note" template="note.html" details="{{'details'| translate}}">
-                            <div class='col-md-12'>{{note.value}}</div>
-                        </d2-pop-over>
-                        <script type="text/ng-template" id="note.html">
-                            <p>{{content.value}}</p>
-                            <hr>
-                            <p><strong>{{'created_by' | translate}}: </strong>{{content.storedBy}}</p>
-                            <p><strong>{{'date' | translate}}: </strong>{{content.storedDate}}</p>                           
-                        </script>
-                    </td> 
-                </tr>
-            </table>
-        <!--</div>  -->      
-    </div>
-</div>
-<div class="modal-footer">
-    <button class="btn btn-default" data-ng-click="close()">{{'close'| translate}}</button>
-</div>
\ No newline at end of file

=== added file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/program-details.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/program-details.html	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/program-details.html	2014-07-13 13:08:50 +0000
@@ -0,0 +1,114 @@
+<div class="modal-header">
+    <h1>{{selectedProgram.name}} {{'report'| translate}}</h1>
+    <span class="pull-right bold">
+        {{'date'| translate}}: {{today}}
+    </span>
+</div>
+<div class="modal-body">
+    <div class='row'>
+        <div class="col-md-6">
+            <h2>{{selectedProgram.trackedEntity.name}} {{'_details'| translate}}</h2>
+            <table class="table table-bordered table-compact">
+                <tr ng-repeat="attribute in selectedTei.attributes" ng-show="attribute.show">
+                    <td class="bold">
+                        {{attribute.displayName}}
+                    </td>
+                    <td>
+                        {{attribute.value}}<!--<input type="text" class="form-control" ng-model="attribute.value" ng-disabled='true'/>                       -->
+                    </td>                
+                </tr>
+            </table>
+        </div>
+    </div>
+    <div class="row" ng-repeat="enrollment in enrollments">
+        <h2 class='col-sm-12'>{{'enrollment'| translate}} {{'_details'| translate}}</h2>
+        <div class="col-sm-4">
+            <span class="bold">{{selectedProgram.dateOfEnrollmentDescription}}:</span>  {{enrollment.dateOfEnrollment}}            
+        </div>
+        <div class="col-sm-4">
+            <span class="bold">{{selectedProgram.dateOfIncidentDescription}}:</span>    {{enrollment.dateOfIncident}}            
+        </div>
+        <div class="col-sm-4">
+            <span class="bold">{{'status'| translate}}:</span>  {{enrollment.status}}           
+        </div>
+        <div class='row vertical-spacing'></div>
+        <div ng-if="enrollment.notes">
+            <h3 class='col-sm-12'>{{'notes'| translate}}</h3>
+            <table class="table-borderless table-striped">
+                <tr class="col-sm-12" ng-repeat="note in enrollment.notes">
+                    <td class="col-sm-12 over-flow-hidden">
+                        <p>
+                            {{note.value}}<br>
+                            ({{note.storedBy}}, {{note.storedDate}})
+                        </p>                                  
+                    </td>                    
+                </tr>
+            </table>
+        </div>
+
+        <div class='vertical-spacing' ng-repeat='dhis2Event in report.enrollments[enrollment.enrollment]'>
+            <h3 class='col-sm-12'>{{'visits'| translate}}</h3>
+            <div class="col-sm-2">
+                <span class="bold">{{'name'| translate}}:</span>    {{dhis2Event.name}}                
+            </div>
+            <div class="col-sm-2">
+                <span class="bold">{{'org_unit'| translate}}:</span> {{dhis2Event.orgUnitName}}                
+            </div>
+            <div class="col-sm-2">
+                <span class="bold">{{'due_date'| translate}}:</span>    {{dhis2Event.dueDate}}
+            </div>
+            <div class="col-sm-2">
+                <span class="bold">{{'visit'| translate}} {{'_date'| translate}}:</span>    {{dhis2Event.eventDate}}
+            </div>
+            <div class="col-sm-2">
+                <span class="bold">{{'status'| translate}}:</span>  {{dhis2Event.status}}
+            </div>
+            <div class='row vertical-spacing'></div>
+            <div class='col-sm-6'>
+                <table class="table table-bordered table-compact">
+                    <tr class="col-sm-12">
+                        <th class="col-md-5">
+                            {{'data_element'| translate}}
+                        </th>
+                        <th class="col-sm-5">
+                            {{'value'| translate}}
+                        </th>
+                        <th class="col-sm-2" ng-if="allowProvidedElsewhereExists[dhis2Event.programStage]">
+                            {{'provided_elsewhere'| translate}}
+                        </th>
+                    </tr>
+                    <tr class="col-sm-12" ng-repeat="prStDe in programStages[dhis2Event.programStage].programStageDataElements">
+                        <td>
+                            {{prStDe.dataElement.formName ? prStDe.dataElement.formName : prStDe.dataElement.name}}
+                        </td>
+                        <td>
+                            {{dhis2Event[prStDe.dataElement.id].value}}          
+                        </td>
+                        <td ng-if="allowProvidedElsewhereExists[dhis2Event.programStage]">
+                            {{dhis2Event[prStDe.dataElement.id].providedElsewhere ? 'provided_elsewhere' : '' | translate}}
+                        </td>
+                    </tr>
+                </table>  
+            </div>
+            <div class='row vertical-spacing'></div>
+            <div ng-if="dhis2Event.notes">
+                <h3 class='col-sm-12'>{{'notes'| translate}}</h3>
+                <table class="table-borderless table-striped">
+                    <tr class="col-sm-12" ng-repeat="note in dhis2Event.notes">
+                        <td class="col-sm-12 over-flow-hidden">
+                            <p>
+                                {{note.value}}<br>
+                                ({{note.storedBy}}, {{note.storedDate}})
+                            </p>                                  
+                        </td>                    
+                    </tr>
+                </table>
+            </div>
+            
+        </div>
+
+    </div>
+</div>
+<div class="modal-footer">
+    <button class="btn btn-default" data-ng-click="close()">{{'close'| translate}}</button>
+</div>
\ No newline at end of file

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report-controller.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report-controller.js	2014-07-10 13:17:04 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report-controller.js	2014-07-13 13:08:50 +0000
@@ -76,7 +76,7 @@
     $scope.showEventDetails = function(dhis2Event, selectedTei){
         
         var modalInstance = $modal.open({
-            templateUrl: 'components/report/eventDetails.html',
+            templateUrl: 'components/report/event-details.html',
             controller: 'EventDetailsController',
             resolve: {
                 dhis2Event: function () {
@@ -158,6 +158,7 @@
     };
 })
 
+
 //conroller for tei report
 .controller('TeiReportController',
         function($scope,
@@ -175,17 +176,17 @@
     $scope.programs = [];  
     $scope.programNames = [];  
     $scope.programStageNames = [];
-    ProgramFactory.getAll().then(function(programs){
-        
-        angular.forEach(programs, function(pr){
-            $scope.programs.push({id: pr.id, name: pr.name});
+    ProgramFactory.getAll().then(function(programs){     
+        $scope.programs = programs;
+        angular.forEach($scope.programs, function(pr){
+            delete pr.organisationUnits;
             $scope.programNames[pr.id] = {id: pr.id, name: pr.name};
-            angular.forEach(pr.programStages, function(stage){
-                $scope.programStageNames[stage.id] = stage;
+            angular.forEach(pr.programStages, function(stage){                
+                $scope.programStageNames[stage.id] = {id: stage.id, name: stage.name};
             });
         });
     });
-    
+        
     $scope.$on('dashboard', function(event, args) {
         var selections = CurrentSelection.get();
         $scope.selectedOrgUnit = storage.get('SELECTED_OU');
@@ -193,7 +194,7 @@
         $scope.selectedEntity = selections.te;
         $scope.selectedProgram = selections.pr;        
         $scope.selectedEnrollment = selections.enrollment; 
-        
+    
         if($scope.selectedTei){            
             $scope.getEvents();
         }       
@@ -211,7 +212,7 @@
         
         $scope.report = [];
         angular.forEach($scope.programs, function(pr){
-            $scope.report[pr.id] = {events: []};
+            $scope.report[pr.id] = {};
         });
         
         DHIS2EventFactory.getEventsByProgram($scope.selectedTei.trackedEntityInstance, orgUnitId, programId).then(function(eventList){
@@ -220,12 +221,25 @@
                 if(ev.program){                    
                     ev.name = $scope.programStageNames[ev.programStage].name;
                     ev.programName = $scope.programNames[ev.program].name;
+                    if(angular.isUndefined($scope.report[ev.program].enrollments)){
+                        $scope.report[ev.program] = {enrollments: {}};
+                    }
                     ev.statusColor = EventUtils.getEventStatusColor(ev); 
                     ev.eventDate = DateUtils.format(ev.eventDate);                    
-                    $scope.report[ev.program].events.push(ev);
+                    ev.dueDate = DateUtils.format(ev.dueDate);                    
+
+                    if(ev.enrollment){
+                        if($scope.report[ev.program].enrollments[ev.enrollment]){
+                            $scope.report[ev.program].enrollments[ev.enrollment].push(ev);
+                        }
+                        else{
+                            $scope.report[ev.program].enrollments[ev.enrollment]= [ev];
+                        }
+                    }
                     ev = EventUtils.setEventOrgUnitName(ev);
                 }                
             });
+
             if(eventList){
                 $scope.dataExists = true;
             }
@@ -233,17 +247,20 @@
         });
     };
     
-    $scope.showEventDetails = function(dhis2Event){
+       
+    
+    $scope.showProgramReportDetails = function(pr){
         
         var modalInstance = $modal.open({
-            templateUrl: 'components/report/eventDetails.html',
-            controller: 'EventDetailsController',
+            templateUrl: 'components/report/program-details.html',
+            controller: 'ProgramDetailsController',
+            windowClass: 'modal-full-window',
             resolve: {
-                dhis2Event: function () {
-                    return dhis2Event;
+                program: function () {
+                    return pr;
                 },
-                gridColumns: function(){
-                    return $scope.gridColumns;
+                report: function(){
+                    return $scope.report[pr.id];
                 },
                 selectedTei: function(){
                     return $scope.selectedTei;
@@ -259,9 +276,89 @@
 
         modalInstance.result.then({
         });
+    };
+})
+
+//Controller for program details
+.controller('ProgramDetailsController', 
+    function($scope, 
+            $modalInstance,
+            $filter,
+            ProgramStageFactory,
+            TEIService,
+            EnrollmentService,
+            DateUtils,
+            program,
+            report,
+            selectedTei,
+            entityName,
+            reportMode){
+    
+    $scope.selectedTei = selectedTei;
+    $scope.entityName = entityName;
+    $scope.reportMode = reportMode;
+    $scope.selectedProgram = program;
+    $scope.report = report;
+    
+    //today as report date
+    $scope.today = moment();
+    $scope.today = Date.parse($scope.today);
+    $scope.today = $filter('date')($scope.today, 'yyyy-MM-dd');
+
+    //process tei attributes, this is to have consistent display that the tei 
+    //contains program attributes whether is has value or not
+    TEIService.processAttributes($scope.selectedTei, $scope.selectedProgram, null).then(function(tei){
+        $scope.selectedTei = tei;  
+    });
+    
+    //get program stage for the selected program
+    //they are needed assign data element names for event data values
+    $scope.programStages = [];  
+    $scope.allowProvidedElsewhereExists = [];
+    angular.forEach($scope.selectedProgram.programStages, function(st){
+        ProgramStageFactory.get(st.id).then(function(stage){
+            $scope.programStages[stage.id] = stage;
+            var providedElsewhereExists = false;
+            for(var i=0; i<stage.programStageDataElements.length && !providedElsewhereExists; i++){                
+                if(stage.programStageDataElements[i].allowProvidedElsewhere){
+                    providedElsewhereExists = true;
+                    $scope.allowProvidedElsewhereExists[st.id] = true;
+                }                
+            }            
+        });
+    });
+    
+    //program reports come grouped in enrollment
+    //process for each enrollment
+    $scope.enrollments = [];        
+    angular.forEach(Object.keys($scope.report.enrollments), function(enr){        
+        //format report data values
+        angular.forEach($scope.report.enrollments[enr], function(ev){
+            angular.forEach(ev.notes, function(note){
+                note.storedDate = moment(note.storedDate).format('DD.MM.YYYY @ hh:mm A');
+            }); 
+            if(ev.dataValues){
+                angular.forEach(ev.dataValues, function(dv){
+                    if(dv.dataElement){
+                        ev[dv.dataElement] = dv;
+                    }                    
+                });
+            }
+        });
+        
+        //get enrollment details
+        EnrollmentService.get(enr).then(function(enrollment){
+            enrollment.dateOfEnrollment = DateUtils.format(enrollment.dateOfEnrollment);
+            enrollment.dateOfIncident = DateUtils.format(enrollment.dateOfIncident);            
+            angular.forEach(enrollment.notes, function(note){
+                note.storedDate = moment(note.storedDate).format('DD.MM.YYYY @ hh:mm A');
+            });            
+            $scope.enrollments.push(enrollment);               
+        });
+    });
+    
+    $scope.close = function () {
+        $modalInstance.close();        
     };   
-    
-    $scope.showProgramReportDetails = function(prId){
-        console.log('I need to display details for:  ', prId, '-',$scope.report[prId].events);
-    };
+
 });
\ No newline at end of file

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report.html	2014-07-10 13:17:04 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/report.html	2014-07-13 13:08:50 +0000
@@ -61,7 +61,7 @@
                         <thead>
                             <tr>
                                 <th>{{selectedProgram.trackedEntity.name}}</th>
-                                <th>{{selectedProgram.name}} {{'record' | translate}}</th>
+                                <th>{{selectedProgram.name}} {{'visit' | translate}}</th>
                             </tr>
                         </thead>
                         <tr ng-repeat="tei in teiList.rows">
@@ -70,27 +70,28 @@
                                     <span class="bold">{{gridColumn.name}}:</span> {{tei[gridColumn.id]}}<br>
                                 </span>
                             </td>
-                            <td>    
-                                <div class='bold inline-block vertical-center' ng-if='!dhis2Events[tei.id]'>{{'no_visit_made' | translate}}</div>
-                                <div class="inline-block vertical-center" ng-repeat="ev in dhis2Events[tei.id] | orderBy: 'eventDate'">                                    
+                            <td class='vertical-center'>    
+                                <div class='bold inline-block' ng-if='!dhis2Events[tei.id]'>{{'no_visit_made' | translate}}</div>
+                                <div class="inline-block" ng-repeat="ev in dhis2Events[tei.id] | orderBy: 'eventDate'">                                    
                                     <div class="block align-center">{{ev.orgUnitName}}</div>                   
                                     <div class="empty-stage-container" 
-                                         title="{{ev.dataValues ? 'details' : 'no_data_registerd' | translate}}"
+                                         title="{{'no_data' | translate}}"
                                          ng-class="{'{{ev.statusColor}}': true}"
                                          ng-if='!ev.dataValues'>
                                         {{ev.name}}<br/>
-                                        {{ev.eventDate}}         
+                                        {{ev.eventDate}}<br>
+                                        {{'no_data' | translate}}
                                     </div>
                                     <div class="stage-container" 
-                                         title="{{ev.dataValues ? 'details' : 'no_data_registerd' | translate}}"
+                                         title="{{'details' | translate}}"
                                          ng-class="{'{{ev.statusColor}}': true}"
                                          ng-if='ev.dataValues'
                                          ng-click="showEventDetails(ev, tei)">
                                         {{ev.name}}<br/>
-                                        {{ev.eventDate}}         
-                                    </div>
-                                    
-                                    <i class="fa fa-arrow-right" ng-show="$index < dhis2Events[tei.id].length - 1"></i>
+                                        {{ev.eventDate}}<br>  
+                                        {{'data_exists' | translate}}
+                                    </div>                                    
+                                    <span><i class="fa fa-arrow-right" ng-show="$index < dhis2Events[tei.id].length - 1"></i></span>
                                 </div>                                         
                             </td>
                         </tr>

=== added file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/tei-report.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/tei-report.html	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/tei-report.html	2014-07-13 13:08:50 +0000
@@ -0,0 +1,24 @@
+<div class="panel panel-default" ng-controller="TeiReportController">
+    <div class="panel-heading handle bold">
+        {{reportWidget.title| translate}}        
+        <span class="pull-right">
+            <a class="small-horizonal-spacing" href ng-click="expandCollapse(reportWidget)">
+                <span ng-show="reportWidget.expand"><i class="fa fa-chevron-up" title="{{'collapse'| translate}}"></i></span>
+                <span ng-show="!reportWidget.expand"><i class="fa fa-chevron-down" title="{{'expand'| translate}}"></i></span>
+            </a>
+            <a class="small-horizonal-spacing" href ng-click="removeWidget(reportWidget)" title="{{'remove'| translate}}"><i class="fa fa-times-circle"></i></a>            
+        </span>        
+    </div>
+    <div ng-show="reportWidget.expand" class="panel-body dashboard-widget-container">        
+        <div ng-if="!dataExists" class="alert alert-warning">{{'no_data_report'| translate}}</div>
+        <div ng-if="dataExists" class="remove-default-padding">
+            <table class="table table-striped dhis2-table-hover">
+                <tr ng-click="showProgramReportDetails(pr)" ng-repeat="pr in programs" ng-if="report[pr.id].enrollments" title="{{'details'| translate}}">                   
+                    <td>
+                        {{pr.name}}                        
+                    </td>
+                </tr>
+            </table>
+        </div>
+    </div>
+</div>
\ No newline at end of file

=== removed file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/teiReport.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/teiReport.html	2014-07-10 13:17:04 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/components/report/teiReport.html	1970-01-01 00:00:00 +0000
@@ -1,44 +0,0 @@
-<div class="panel panel-default" ng-controller="TeiReportController">
-    <div class="panel-heading handle bold">
-        {{reportWidget.title| translate}}        
-        <span class="pull-right">
-            <a class="small-horizonal-spacing" href ng-click="expandCollapse(reportWidget)">
-                <span ng-show="reportWidget.expand"><i class="fa fa-chevron-up" title="{{'collapse'| translate}}"></i></span>
-                <span ng-show="!reportWidget.expand"><i class="fa fa-chevron-down" title="{{'expand'| translate}}"></i></span>
-            </a>
-            <a class="small-horizonal-spacing" href ng-click="removeWidget(reportWidget)" title="{{'remove'| translate}}"><i class="fa fa-times-circle"></i></a>            
-        </span>        
-    </div>
-    <div ng-show="reportWidget.expand" class="panel-body dashboard-widget-container">        
-        <div ng-if="!dataExists" class="alert alert-warning">{{'no_data_report'| translate}}</div>
-        <div ng-if="dataExists" class="remove-default-padding">
-            <table class="table table-striped dhis2-table-hover">
-                <tr ng-click="showProgramReportDetails(pr.id)" ng-repeat="pr in programs" ng-if="report[pr.id].events" title="{{'program_details'| translate}}">                   
-                    <td>
-                        {{pr.name}}
-                        <!--<div class="row col-md-12 bold vertical-spacing">{{pr.name}}</div>
-                        <div class='bold vertical-center' ng-if='report[pr.id].events.length < 1'>{{'no_visit_made'| translate}}</div>
-                        <div class="inline-block vertical-center" ng-repeat="ev in report[pr.id].events | orderBy: 'eventDate'">                                    
-                            <div class="empty-stage-container" 
-                                 title="{{ev.dataValues ? 'details' : 'no_data_registerd'| translate}}"
-                                 ng-class="{'{{ev.statusColor}}': true}"
-                                 ng-if='!ev.dataValues'>
-                                <div class="row">{{ev.name}}</div>
-                                <div class="row">{{ev.eventDate}}</div>        
-                            </div>
-                            <div class="stage-container" 
-                                 title="{{ev.dataValues ? 'details' : 'no_data_registerd'| translate}}"
-                                 ng-class="{'{{ev.statusColor}}': true}"
-                                 ng-if='ev.dataValues'
-                                 ng-click="showEventDetails(ev)">
-                                <div class="row">{{ev.name}}</div>
-                                <div class="row">{{ev.eventDate}}</div>            
-                            </div>
-                            <i class="fa fa-arrow-right vertical-center" ng-show="$index < report[pr.id].events.length - 1"></i>
-                        </div>  -->                                       
-                    </td>
-                </tr>
-            </table>
-        </div>
-    </div>
-</div>
\ No newline at end of file

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/i18n/en.json'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/i18n/en.json	2014-07-10 13:17:04 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/i18n/en.json	2014-07-13 13:08:50 +0000
@@ -27,6 +27,7 @@
     "number_required": "Number required",
     "date_required": "Date required (yyyy-mm-dd)",
     "search": "Search",
+    "_search": "search",  
     "advanced_search": "Advanced search",
     "search_for": "Search for",
     "type_here_for_simple_search": "Type your criteria here for simple search",
@@ -60,10 +61,12 @@
     "complete": "Complete",
     "incomplete": "Incomplete",
     "validate": "Validate",
+    "status": "Status",
     "details": "Details",
-    "program_details": "Program details",
+    "_details": "details",
     "created_by": "Registerd by",
     "date": "Date",
+    "_date": "date",
     "add_new": "Add new",
     "add_filter": "Add filter",
     "remove_filter": "Remove filter",
@@ -90,11 +93,20 @@
     "please_select_source": "Please select source",
     "register_new": "Register new",
     "search_from_existing": "Search from existing",
+    "name": "Name",
     "dataentry": "Data Entry",
+    "custom_form": "Custom form",
+    "default_form": "Default form",
     "report": "Report",
+    "_report": "report", 
     "registered_data": "Registered data",
-    "no_data_registerd": "No data registered",
+    "no_data": "No data",
+    "data_exists": "Data exists",
+    "data_registerd": "No data registered",
     "no_visit_made": "No visit made",
+    "_visit": "visit",
+    "visit": "Visit",
+    "visits": "Visits",
     "current_selections": "Current selections",
     "org_unit": "Organisation unit",
     "SELECTED": "Selected",
@@ -140,6 +152,7 @@
     "no": "No",
     "records": "Records",
     "record": "Record",
+    "_record": "record",
     "found": "Found",
     "move_to_selected": "Move to selected",
     "move_all_to_selected": "Move all to selected",
@@ -148,6 +161,7 @@
     "registration": "Registration",
     "registration_date": "Registration date",
     "register": "Register",
+    "_register": "register",
     "registration_error": "Error in registration",
     "update_error": "Error in update",
     "event_creation_error": "Error in event creation",

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/directives.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/directives.js	2014-07-02 20:53:29 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/directives.js	2014-07-13 13:08:50 +0000
@@ -78,6 +78,23 @@
     };
 })
 
+.directive('d2CustomForm', function($compile, $parse, CustomFormService) {
+    return{ 
+        restrict: 'E',
+        link: function(scope, elm, attrs){   
+            
+            var customFormType = attrs.customFormType;
+            var customFormObject = $parse(attrs.customFormObject)(scope);
+            
+            if(customFormType === 'PROGRAM_STAGE'){                
+                var customForm = CustomFormService.getForProgramStage(customFormObject);  
+                elm.html(customForm ? customForm : '');
+                $compile(elm.contents())(scope);     
+            }
+        }
+    };
+})
+
 .directive('d2PopOver', function($compile, $templateCache){
     return {        
         restrict: 'EA',

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/services.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/services.js	2014-07-08 19:07:43 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/services.js	2014-07-13 13:08:50 +0000
@@ -272,13 +272,12 @@
 })
 
 /* Service for getting tracked entity instances */
-.factory('TEIService', function($http, DateUtils) {
-    
-    var promise;
+.factory('TEIService', function($http, $q, AttributesFactory, DateUtils) {
+
     return {
         
         get: function(entityUid) {
-            promise = $http.get(  '../api/trackedEntityInstances/' +  entityUid ).then(function(response){     
+            var promise = $http.get(  '../api/trackedEntityInstances/' +  entityUid ).then(function(response){     
                 var tei = response.data;
                 
                 angular.forEach(tei.attributes, function(attribute){                   
@@ -291,13 +290,12 @@
                 return tei;
             });            
             return promise;
-        },
-        
+        },        
         getByOrgUnitAndProgram: function(orgUnitUid, programUid) {
 
             var url = '../api/trackedEntityInstances.json?ou=' + orgUnitUid + '&program=' + programUid;
             
-            promise = $http.get( url ).then(function(response){               
+            var promise = $http.get( url ).then(function(response){               
                 //return EntityService.formatter(response.data);
                 return response.data;
             });            
@@ -307,7 +305,7 @@
             
             var url =  '../api/trackedEntityInstances.json?ou=' + orgUnitUid;
             
-            promise = $http.get( url ).then(function(response){                                
+            var promise = $http.get( url ).then(function(response){                                
                 //return EntityService.formatter(response.data);
                 return response.data;
             });            
@@ -336,7 +334,7 @@
                 url = url + '&paging=false';
             }
             
-            promise = $http.get( url ).then(function(response){                                
+            var promise = $http.get( url ).then(function(response){                                
                 return response.data;
             });            
             return promise;
@@ -357,12 +355,39 @@
                 return response.data;
             });
             return promise;
+        },
+        processAttributes: function(selectedTei, selectedProgram, selectedEnrollment){
+            var def = $q.defer();            
+            if(selectedTei.attributes){
+                if(selectedProgram && selectedEnrollment){
+                    //show attribute for selected program and enrollment
+                    AttributesFactory.getByProgram(selectedProgram).then(function(atts){    
+                        selectedTei.attributes = AttributesFactory.showRequiredAttributes(atts,selectedTei.attributes, true);
+                        def.resolve(selectedTei);
+                    }); 
+                }
+                if(selectedProgram && !selectedEnrollment){
+                    //show attributes for selected program            
+                    AttributesFactory.getByProgram(selectedProgram).then(function(atts){    
+                        selectedTei.attributes = AttributesFactory.showRequiredAttributes(atts,selectedTei.attributes, false);
+                        def.resolve(selectedTei);
+                    }); 
+                }
+                if(!selectedProgram && !selectedEnrollment){
+                    //show attributes in no program            
+                    AttributesFactory.getWithoutProgram().then(function(atts){                
+                        selectedTei.attributes = AttributesFactory.showRequiredAttributes(atts,selectedTei.attributes, false);     
+                        def.resolve(selectedTei);
+                    });
+                }
+            }       
+            return def.promise;
         }
     };
 })
 
 /* Factory for getting tracked entity attributes */
-.factory('AttributesFactory', function($q, $rootScope, StorageService) {      
+.factory('AttributesFactory', function($q, $rootScope, StorageService, orderByFilter) {      
 
     return {
         getAll: function(){
@@ -443,8 +468,38 @@
                 def.resolve(missingAttributes);
             });            
             return def.promise();            
+        },
+        showRequiredAttributes: function(requiredAttributes, teiAttributes, fromEnrollment){        
+
+            //first reset teiAttributes
+            for(var j=0; j<teiAttributes.length; j++){
+                teiAttributes[j].show = false;
+                if(teiAttributes[j].type === 'number' && !isNaN(parseInt(teiAttributes[j].value))){
+                    teiAttributes[j].value = parseInt(teiAttributes[j].value);
+                }
+            }
+
+            //identify which ones to show
+            for(var i=0; i<requiredAttributes.length; i++){
+                var processed = false;
+                for(var j=0; j<teiAttributes.length && !processed; j++){
+                    if(requiredAttributes[i].id === teiAttributes[j].attribute){                    
+                        processed = true;
+                        teiAttributes[j].show = true;
+                        teiAttributes[j].order = i;
+                    }
+                }
+
+                if(!processed && fromEnrollment){//attribute was empty, so a chance to put some value
+                    teiAttributes.push({show: true, order: i, attribute: requiredAttributes[i].id, displayName: requiredAttributes[i].name, type: requiredAttributes[i].valueType, value: ''});
+                }                   
+            }
+
+            teiAttributes = orderByFilter(teiAttributes, '-order');
+            teiAttributes.reverse();
+
+            return teiAttributes;
         }
-
     };
 })
 
@@ -633,57 +688,175 @@
     };    
 })
 
+/* service for dealing with custom form */
+.service('CustomFormService', function(){
+    
+    return {
+        getForProgramStage: function(programStage){
+            
+            if(!programStage){
+                return null;
+            }
+            
+            var htmlCode = programStage.dataEntryForm ? programStage.dataEntryForm.htmlCode : null;  
+            
+            if(htmlCode){                
+            
+                var programStageDataElements = [];
+
+                angular.forEach(programStage.programStageDataElements, function(prStDe){
+                    programStageDataElements[prStDe.dataElement.id] = prStDe;
+                });
+
+                var inputRegex = /<input.*?\/>/g,
+                    match,
+                    inputFields = [];                
+
+                while (match = inputRegex.exec(htmlCode)) {                
+                    inputFields.push(match[0]);
+                }
+                
+                for(var i=0; i<inputFields.length; i++){                    
+                    var inputField = inputFields[i];                    
+                    var inputElement = $.parseHTML( inputField );
+                    var attributes = {};
+                                       
+                    $(inputElement[0].attributes).each(function() {
+                        attributes[this.nodeName] = this.nodeValue;                       
+                    });
+                    
+                    var deId = '', newInputField;     
+                    if(attributes.hasOwnProperty('id')){
+                        deId = attributes['id'].substring(4, attributes['id'].length-1).split("-")[1]; 
+                     
+                        //name needs to be unique so that it can be used for validation in angularjs
+                        if(attributes.hasOwnProperty('name')){
+                            attributes['name'] = deId;
+                        }
+                        
+                        //check data element type and generate corresponding angular input field
+                        if(programStageDataElements[deId].dataElement.type == "int"){
+                            newInputField = '<input type="number" ' +
+                                            this.getAttributesAsString(attributes) +
+                                            ' ng-model="currentEvent.' + deId + '"' +
+                                            ' ng-class="getInputNotifcationClass(' + deId + ',true)"' +
+                                            ' ng-blur="saveDatavalue(programStageDataElements.'+ deId + ')"' + 
+                                            ' ng-required="programStageDataElements.' + deId + '.compulsory">';
+                        }
+                        if(programStageDataElements[deId].dataElement.type == "string"){
+                            newInputField = '<input type="text" ' +
+                                            this.getAttributesAsString(attributes) +
+                                            ' ng-model="currentEvent.' + deId + '" ' +
+                                            ' ng-class="getInputNotifcationClass(' + deId + ',true)"' +
+                                            ' ng-required="programStageDataElements.' + deId + '.compulsory"' +
+                                            ' ng-blur="saveDatavalue(programStageDataElements.'+ deId + ')"' + 
+                                            ' typeahead="option for option in programStageDataElements.'+deId+'.dataElement.optionSet.options | filter:$viewValue | limitTo:20"' +
+                                            ' typeahead-open-on-focus ng-required="programStageDataElements.'+deId+'.compulsory">';
+                        }
+                        if(programStageDataElements[deId].dataElement.type == "bool"){
+                            newInputField = '<select ' +
+                                            this.getAttributesAsString(attributes) +
+                                            ' ng-model="currentEvent.' + deId + '" ' +
+                                            ' ng-class="getInputNotifcationClass(' + deId + ',true)"' +
+                                            ' ng-change="saveDatavalue(programStageDataElements.'+ deId + ')"' + 
+                                            ' ng-required="programStageDataElements.' + deId + '.compulsory">' + 
+                                            '<option value="">{{\'please_select\'| translate}}</option>' +
+                                            '<option value="0">{{\'no\'| translate}}</option>' + 
+                                            '<option value="1">{{\'yes\'| translate}}</option>';
+                        }
+                        if(programStageDataElements[deId].dataElement.type == "date"){
+                            newInputField = '<input type="text" ' +
+                                            this.getAttributesAsString(attributes) +
+                                            ' ng-model="currentEvent.' + deId + '"' +
+                                            ' ng-class="getInputNotifcationClass(' + deId + ',true)"' +
+                                            ' ng-date' +
+                                            ' blur-or-change="saveDatavalue(programStageDataElements.'+ deId + ')"' + 
+                                            ' ng-required="programStageDataElements.' + deId + '.compulsory">';
+                        }
+                        if(programStageDataElements[deId].dataElement.type == "trueOnly"){
+                            newInputField = '<input type="checkbox" ' +
+                                            this.getAttributesAsString(attributes) +
+                                            ' ng-model="currentEvent.' + deId + '"' +
+                                            ' ng-class="getInputNotifcationClass(' + deId + ',true)"' +
+                                            ' ng-change="saveDatavalue(programStageDataElements.'+ deId + ')"' + 
+                                            ' ng-required="programStageDataElements.' + deId + '.compulsory">';
+                        }
+                        htmlCode = htmlCode.replace(inputField, newInputField);
+                    }
+                }
+                
+                return htmlCode;
+                
+            }
+            
+            return null;
+        },
+        getAttributesAsString: function(attributes){
+            if(attributes){
+                var attributesAsString = '';                
+                for(var prop in attributes){
+                    if(prop != 'value'){
+                        attributesAsString += prop + '="' + attributes[prop] + '" ';
+                    }
+                }
+                return attributesAsString;
+            }
+            return null;
+        }
+    };            
+})
+
 /* Modal service for user interaction */
 .service('ModalService', ['$modal', function($modal) {
 
-        var modalDefaults = {
-            backdrop: true,
-            keyboard: true,
-            modalFade: true,
-            templateUrl: 'views/modal.html'
-        };
-
-        var modalOptions = {
-            closeButtonText: 'Close',
-            actionButtonText: 'OK',
-            headerText: 'Proceed?',
-            bodyText: 'Perform this action?'
-        };
-
-        this.showModal = function(customModalDefaults, customModalOptions) {
-            if (!customModalDefaults)
-                customModalDefaults = {};
-            customModalDefaults.backdrop = 'static';
-            return this.show(customModalDefaults, customModalOptions);
-        };
-
-        this.show = function(customModalDefaults, customModalOptions) {
-            //Create temp objects to work with since we're in a singleton service
-            var tempModalDefaults = {};
-            var tempModalOptions = {};
-
-            //Map angular-ui modal custom defaults to modal defaults defined in service
-            angular.extend(tempModalDefaults, modalDefaults, customModalDefaults);
-
-            //Map modal.html $scope custom properties to defaults defined in service
-            angular.extend(tempModalOptions, modalOptions, customModalOptions);
-
-            if (!tempModalDefaults.controller) {
-                tempModalDefaults.controller = function($scope, $modalInstance) {
-                    $scope.modalOptions = tempModalOptions;
-                    $scope.modalOptions.ok = function(result) {
-                        $modalInstance.close(result);
-                    };
-                    $scope.modalOptions.close = function(result) {
-                        $modalInstance.dismiss('cancel');
-                    };
-                };
-            }
-
-            return $modal.open(tempModalDefaults).result;
-        };
-
-    }])
+    var modalDefaults = {
+        backdrop: true,
+        keyboard: true,
+        modalFade: true,
+        templateUrl: 'views/modal.html'
+    };
+
+    var modalOptions = {
+        closeButtonText: 'Close',
+        actionButtonText: 'OK',
+        headerText: 'Proceed?',
+        bodyText: 'Perform this action?'
+    };
+
+    this.showModal = function(customModalDefaults, customModalOptions) {
+        if (!customModalDefaults)
+            customModalDefaults = {};
+        customModalDefaults.backdrop = 'static';
+        return this.show(customModalDefaults, customModalOptions);
+    };
+
+    this.show = function(customModalDefaults, customModalOptions) {
+        //Create temp objects to work with since we're in a singleton service
+        var tempModalDefaults = {};
+        var tempModalOptions = {};
+
+        //Map angular-ui modal custom defaults to modal defaults defined in service
+        angular.extend(tempModalDefaults, modalDefaults, customModalDefaults);
+
+        //Map modal.html $scope custom properties to defaults defined in service
+        angular.extend(tempModalOptions, modalOptions, customModalOptions);
+
+        if (!tempModalDefaults.controller) {
+            tempModalDefaults.controller = function($scope, $modalInstance) {
+                $scope.modalOptions = tempModalOptions;
+                $scope.modalOptions.ok = function(result) {
+                    $modalInstance.close(result);
+                };
+                $scope.modalOptions.close = function(result) {
+                    $modalInstance.dismiss('cancel');
+                };
+            };
+        }
+
+        return $modal.open(tempModalDefaults).result;
+    };
+
+}])
 
 /* Dialog service for user interaction */
 .service('DialogService', ['$modal', function($modal) {
@@ -897,54 +1070,6 @@
             });
             return {headers: attributes, rows: entityList, pager: grid.metaData.pager};                                    
         },   
-        formatForReport: function(grid){
-            if(!grid || !grid.rows){
-                return;
-            }
-            
-            //grid.headers[0-4] = Instance, Created, Last updated, Org unit, Tracked entity
-            //grid.headers[5..] = Attribute, Attribute,.... 
-            var attributes = [];
-            var entityList = [];
-            for(var i=5; i<grid.headers.length; i++){
-                attributes.push({id: grid.headers[i].name, name: grid.headers[i].column, type: grid.headers[i].type});
-            }
-
-            OrgUnitService.open().then(function(){
-
-                angular.forEach(grid.rows, function(row){
-                    var entity = {};
-                    var isEmpty = true;                   
-
-                    entity.id = row[0];
-                    var rDate = row[1];
-                    rDate = DateUtils.format(rDate);
-                    entity.created = rDate;
-                    entity.orgUnit = row[3];                              
-                    entity.type = row[4];  
-
-                    OrgUnitService.get(row[3]).then(function(ou){
-                        if(ou){
-                            entity.orgUnitName = ou.n;
-                        }                                                       
-                    });
-
-                    for(var i=5; i<row.length; i++){
-                        if(row[i] && row[i] !== ''){
-                            isEmpty = false;
-                            entity[grid.headers[i].name] = row[i];
-                        }
-                    }
-                    
-                    if(!isEmpty){                        
-                        entityList[entity.id] = entity;
-                    }        
-                });
-                var returnVal = {headers: attributes, rows: entityList};
-                console.log('the return is:  ', returnVal);
-                return returnVal;
-            });            
-        },
         generateGridColumns: function(attributes, ouMode){
             
             var columns = attributes ? angular.copy(attributes) : [];

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/tracker-capture.js'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/tracker-capture.js	2014-07-09 09:33:55 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/scripts/tracker-capture.js	2014-07-13 13:08:50 +0000
@@ -58,6 +58,7 @@
         
         promise = promise.then( dhis2.tc.store.open );
         promise = promise.then( getUserProfile );
+        promise = promise.then( getLoginDetails );
         promise = promise.then( getRelationships );
         promise = promise.then( getAttributes );
         promise = promise.then( getOptionSetsForAttributes );
@@ -187,6 +188,20 @@
     return def.promise();
 }
 
+function getLoginDetails()
+{
+    var def = $.Deferred();
+
+    $.ajax({
+        url: '../api/me',
+        type: 'GET'
+    }).done( function(response) {            
+        localStorage['LOGIN_DETAILS'] = JSON.stringify(response);           
+        def.resolve();
+    });
+    
+    return def.promise(); 
+}
 
 function getRelationships()
 {
@@ -434,7 +449,7 @@
         return $.ajax( {
             url: '../api/programStages.json',
             type: 'GET',
-            data: 'filter=id:eq:' + id +'&fields=id,name,dataEntryForm,reportDateDescription,minDaysFromStart,repeatable,programStageDataElements[displayInReports,allowProvidedElsewhere,allowDateInFuture,compulsory,dataElement[id,name,formName,type,optionSet[id]]]'
+            data: 'filter=id:eq:' + id +'&fields=id,name,version,dataEntryForm,captureCoordinates,reportDateDescription,minDaysFromStart,repeatable,programStageDataElements[displayInReports,allowProvidedElsewhere,allowDateInFuture,compulsory,dataElement[id,name,formName,type,optionSet[id]]]'
         }).done( function( response ){            
             _.each( _.values( response.programStages ), function( programStage ) {                
                 dhis2.tc.store.set( 'programStages', programStage );

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/styles/style.css'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/styles/style.css	2014-07-08 19:07:43 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/styles/style.css	2014-07-13 13:08:50 +0000
@@ -428,6 +428,7 @@
     padding-left: 30px;
     padding-right: 30px;
 }
+
 .vertical-spacing{
     margin-top: 10px;   
     margin-bottom: 10px;
@@ -494,14 +495,14 @@
     -webkit-text-overflow: ellipsis;
 }
 
-.relationship-modal-window .modal-dialog {
+.modal-full-window .modal-dialog {
     width: 100%;
     height: 100%;
 }
 
 .modal-dialog {
     top: 50%;
-    
+
 }
 .expanded{
     border: 1px solid #aaa;

=== modified file 'dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/views/home.html'
--- dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/views/home.html	2014-07-08 08:30:39 +0000
+++ dhis-2/dhis-web/dhis-web-tracker-capture/src/main/webapp/dhis-web-tracker-capture/views/home.html	2014-07-13 13:08:50 +0000
@@ -14,10 +14,10 @@
     <div class="row top-bar">        
         <div class="col-sm-12">            
             <span ng-if='searchState'>
-                {{'search'| translate}} {{selectedProgram.trackedEntity.name}}
+                {{selectedProgram.trackedEntity.name}} {{'search'| translate}}
             </span>
             <span ng-if='showRegistrationDiv'>
-                {{'register'| translate}} {{selectedProgram.trackedEntity.name}}
+                {{selectedProgram.trackedEntity.name}} {{'register'| translate}}
             </span>        
             <span ng-if='showReportDiv'>
                 {{selectedProgram.name}} {{'report'| translate}}