]> git.evergreen-ils.org Git - Evergreen.git/blob - Open-ILS/web/js/ui/default/staff/cat/services/marcedit.js
LP#1402797 Context menu infrastructure
[Evergreen.git] / Open-ILS / web / js / ui / default / staff / cat / services / marcedit.js
1 /**
2  *  A MARC editor...
3  */
4
5 angular.module('egMarcMod', ['egCoreMod', 'ui.bootstrap'])
6
7 .directive("egContextMenuItem", ['$timeout',function ($timeout) {
8     return {
9         restrict: 'E',
10         replace: true,
11         template: '<li><a ng-click="setContent(item.value,item.action)">{{item.label}}</a></li>',
12         scope: { item: '=', content: '=' },
13         controller: ['$scope','$element',
14             function ($scope , $element) {
15                 if (!$scope.item.label) $scope.item.label = $scope.item.value;
16                 if ($scope.item.divider) {
17                     $element.style.borderTop = 'solid 1px';
18                 }
19
20                 $scope.setContent = function (v, a) {
21                     var replace_with = v;
22                     if (a) replace_with = a($scope,$element,$scope.item.value,$scope.$parent.$parent.content);
23                     $timeout(function(){
24                         $scope.$parent.$parent.$apply(function(){
25                             $scope.$parent.$parent.content = replace_with
26                         })
27                     }, 0);
28                     console.log('well, replaced it');
29                     $($element).parent().css({display: 'none'});
30                 }
31             }
32         ]
33     }
34 }])
35
36 .directive("egMarcEditEditable", ['$timeout', '$compile', '$document', function ($timeout, $compile, $document) {
37     return {
38         restrict: 'E',
39         replace: false,
40         transclude: true,
41         template: '<input style="font-family: \'Lucida Console\', Monaco, monospace;" ng-model="content" size="{{content.length * 1.1}}" maxlength="{{max}}" class="" type="text"/>',
42         scope: {
43             field: '=',
44             subfield: '=',
45             content: '=',
46             contextItemContainer: '@',
47             max: '@',
48             type: '@'
49         },
50         controller : ['$scope',
51             function ( $scope ) {
52
53 /* XXX Example, for testing.  We'll get this from the tag-table services for realz
54  *
55                 if (!$scope.contextItemContainer) {
56                     $scope.contextItemContainer = "default_context";
57                     $scope[$scope.contextItemContainer] = [
58                         { value: 'a' },
59                         { value: 'b' },
60                         { value: 'c' },
61                     ];
62                 }
63
64  *
65  */
66
67                 if ($scope.contextItemContainer)
68                     $scope.item_container = $scope[$scope.contextItemContainer];
69
70                 $scope.showContext = function (event) {
71                     if ($scope.context_menu_element) {
72                         console.log('Reshowing context menu...');
73                         $($scope.context_menu_element).css({ display: 'block', top: event.pageY, left: event.pageX });
74                         return false;
75                     }
76
77                     if (angular.isArray($scope.item_container)) { // we have a list of values or transforms
78                         console.log('Showing context menu...');
79
80                         var tmpl = 
81                             '<ul class="dropdown-menu" role="menu">'+
82                                 '<eg-context-menu-item ng-repeat="item in item_container" item="item" content="content"/>'+
83                             '</ul>';
84             
85                         var tnode = angular.element(tmpl);
86                         console.log('... got element ...');
87
88                         $document.find('body').append(tnode);
89                         console.log('... attached to DOM ...');
90
91                         $(tnode).css({
92                             display: 'block',
93                             top: event.pageY,
94                             left: event.pageX
95                         });
96                         console.log('... displayed ...');
97
98                         $scope.context_menu_element = tnode;
99                         console.log('... captured for later ...');
100
101                         $timeout(function() {
102                             var e = $compile(tnode)($scope);
103                             console.log('... compiled: ' + e);
104                         }, 0);
105
106                         return false;
107                     }
108             
109                     return true;
110                 }
111
112             }
113         ],
114         link: function (scope, element, attrs) {
115
116             element.bind('change', function (e) { element.size = scope.max || parseInt(scope.content.length * 1.1) });
117             if (scope.contextItemContainer && angular.isArray(scope[scope.contextItemContainer]))
118                 element.bind('contextmenu', scope.showContext);
119         }
120     }
121 }])
122
123 .directive("egMarcEditSubfield", function () {
124     return {
125         restrict: 'E',
126         template: '<span>'+
127                     '<span><eg-marc-edit-editable type="sfc" class="marcsfcode" field="field" subfield="subfield" content="subfield[0]" max="1"/></span>'+
128                     '<span><eg-marc-edit-editable type="sfv" class="marcsfvalue" field="field" subfield="subfield" content="subfield[1]"/></span>'+
129                   '</span>',
130         scope: { field: "=", subfield: "=" },
131         replace: false
132     }
133 })
134
135 .directive("egMarcEditInd", function () {
136     return {
137         restrict: 'E',
138         template: '<span><eg-marc-edit-editable type="ind" field="field" content="ind" max="1"/></span>',
139         scope: { ind : '=', field: '=' },
140         replace: false,
141     }
142 })
143
144 .directive("egMarcEditTag", function () {
145     return {
146         restrict: 'E',
147         template: '<span><eg-marc-edit-editable type="tag" field="field" content="tag" max="3"/></span>',
148         scope: { tag : '=', field: '=' },
149         replace: false
150     }
151 })
152
153 .directive("egMarcEditDatafield", function () {
154     return {
155         restrict: 'E',
156         template: '<div>'+
157                     '<span><eg-marc-edit-tag class="marctag" field="field" tag="field.tag"/></span>'+
158                     '<span><eg-marc-edit-ind class="marcind" field="field" ind="field.ind1"/></span>'+
159                     '<span><eg-marc-edit-ind class="marcind" field="field" ind="field.ind2"/></span>'+
160                     '<span><eg-marc-edit-subfield ng-repeat="subfield in field.subfields" subfield="subfield" field="field"/></span>'+
161                   '</div>',
162         scope: { field: "=" }
163     }
164 })
165
166 .directive("egMarcEditControlfield", function () {
167     return {
168         restrict: 'E',
169         template: '<div>'+
170                     '<span><eg-marc-edit-tag class="marctag" field="field" tag="field.tag"/></span>'+
171                     '<span><eg-marc-edit-editable type="cfld" field="field" class="marcdata" content="field.data"/></span>'+
172                   '</div>',
173         scope: { field: "=" }
174     }
175 })
176
177 .directive("egMarcEditLeader", function () {
178     return {
179         restrict: 'E',
180         template: '<div>'+
181                     '<span><eg-marc-edit-editable class="marctag" content="tag"/></span>'+
182                     '<span><eg-marc-edit-editable class="marcdata" type="ldr" max="{{record.leader.length}}" content="record.leader"/></span>'+
183                   '</div>',
184         controller : ['$scope',
185             function ( $scope ) {
186                 $scope.tag = 'LDR';
187             }
188         ],
189         scope: { record: "=" }
190     }
191 })
192
193 /// TODO: fixed field editor and such
194 .directive("egMarcEditRecord", function () {
195     return {
196         template: '<form ng-submit="saveRecord()">'+
197                   '<div class="marcrecord">'+
198                     '<div><eg-marc-edit-leader record="record"/></div>'+
199                     '<div><eg-marc-edit-controlfield ng-repeat="field in controlfields" field="field"/></div>'+
200                     '<div><eg-marc-edit-datafield ng-repeat="field in datafields" field="field"/></div>'+
201                   '</div>'+
202                   '<button class="btn btn-default" type="submit">Save</button>'+
203                   '</form>'+
204                   '<button class="btn btn-default" ng-click="seeBreaker()">Breaker</button>',
205         restrict: 'E',
206         replace: false,
207         scope: { recordId : '=' },
208         controller : ['$scope','egCore',
209             function ( $scope , egCore ) {
210
211                 function loadRecord() {
212                     return egCore.pcrud.retrieve(
213                         'bre', $scope.recordId
214                     ).then(function(rec) {
215                         $scope.bre = rec;
216                         $scope.record = new MARC.Record();
217                         $scope.record.fromXmlString( $scope.bre.marc() );
218                         $scope.controlfields = $scope.record.fields.filter(function(f){ return f.isControlfield() });
219                         $scope.datafields = $scope.record.fields.filter(function(f){ return !f.isControlfield() });
220                     });
221                 }
222
223                 $scope.saveRecord = function () {
224                     $scope.bre.marc($scope.record.toXmlString());
225                     return egCore.pcrud.update(
226                         $scope.bre
227                     ).then(loadRecord);
228                 };
229
230                 $scope.seeBreaker = function () {
231                     alert($scope.record.toBreaker());
232                 };
233
234                 $scope.$watch('recordId',
235                     function(newVal, oldVal) {
236                         if (newVal && newVal !== oldVal) {
237                             loadRecord();
238                         }
239                     }
240                 );
241
242
243                 $scope.controlfields = [];
244                 $scope.datafields = [];
245
246                 if ($scope.recordId)
247                     loadRecord();
248
249             }
250         ]          
251     }
252 })
253
254 ;