PageSourceSearch

https://cinemaportuguesmemoriale.pt/DesktopModules/MVC/AlgoritmiaAngular/js/APP/Common/TocUI.js?cdv=615

js cinemaportuguesmemoriale.pt collected 2026-10-02 06:19:51 UTC 7,992 bytes, 204 lines download raw bytes

1angular.module('TocUI', []);
2
3/*Templates*/
4angular.module("TocUI").run(["$templateCache",function ($templateCache) {
5    /*Modal Templates*/
6    $templateCache.put('uiTocRoot.html', [
7        '<div class="toc list-group">',
8        '   <div ng-repeat="row in $data.hierarchy" ui-toc-node="row"></div>',
9        '</div>'
10    ].join(''));
11    $templateCache.put('uiTocNode.html', [
12        '<div>',
13        '   <a data-toggle="collapse" data-target="#menu-{{row.item._id}}" class="list-group-item" ng-class="{\'active\':row.item.active, \'active-path\':row.item.activePath}">',
14        '       <span ng-click="go()">{{row.item.title}}</span> <b class="caret" ng-if="row.child.length>0"></b>',
15        '   </a>',
16        '   <div class="list-group collapse" id="menu-{{row.item._id}}" ng-if="row.child.length>0"  ng-class="{\'in\':row.item.active || row.item.activePath}">',
17        '       <div ng-repeat="item in row.child" ui-toc-node="item"></div>',
18        '   </div>',
19        '</div>'
20    ].join(''));
21}]);
22
23
24/*
25Panel
26*/
27angular.module("TocUI").directive('uiToc', ['tocService', function (tocService) {
28    return {
29        restrict: 'A',
30        scope: {
31            selector:'@uiToc'
32        },
33        templateUrl: 'uiTocRoot.html',
34        link: function (scope, element, attrs) {
35            tocService.setSelector(scope.selector);
36            scope.$data = tocService.data;
37
38            scope.$on('$locationChangeSuccess', function (event) {
39                $('.sidebar').removeClass('active');
40            });
41        }
42    };
43}]);
44
45angular.module("TocUI").directive('uiTocNode', ['tocService', '$anchorScroll', '$location', function (tocService, $anchorScroll, $location) {
46    return {
47        restrict: 'A',
48        scope: {
49            row: '=uiTocNode'
50        },
51        templateUrl: 'uiTocNode.html',
52        replace: true,
53        link: function (scope, element, attrs) {
54            scope.go = function () {
55                var newHash = scope.row.id;
56                if ($location.hash() !== newHash) {
57                    // set the $location.hash to `newHash` and $anchorScroll will automatically scroll to it
58                    $location.hash(newHash);
59                } else {
60                    // call $anchorScroll() explicitly, since $location.hash hasn't changed
61                    $anchorScroll();
62                }
63            }
64        }
65    };
66}]);
67
68angular.module("TocUI").directive('tocItem', ['tocService', function (tocService) {
69    return {
70        restrict: 'C',
71        scope: false,
72        link: function (scope, element, attrs) {
73            /*Fires TOC Update on create or destroy*/
74            tocService.update();
75            scope.$on('$destroy', function () {
76                tocService.remove(element);
77            });
78        }
79    };
80}]);
81
82angular.module("TocUI").service('tocService', ['$rootScope', function ($rootScope) {
83    var svc = {
84        _selector: 'body',
85        data: {
86            items: [],
87            hierarchy: []
88        },
89        activeItem: {},
90        lastId: 0
91    };
92    svc.setSelector = function (newVal) {
93        $(svc._selector).unbind('scroll');
94        svc._selector = newVal;
95        $(svc._selector).bind('scroll', _.debounce(svc._onScroll, 100));
96    };
97    svc._update = function () {
98        svc.elements = $(svc._selector).find('.toc-item');
99        svc.elements.each(function (i, ui) {
100            var el = $(ui), tocItem;
101            if (el.data('tocItem')) tocItem = el.data('tocItem');
102            if (!tocItem) {
103                var tocItem = { _id: svc.lastId++ };
104                if (!el.attr('id')) el.attr('id', 'toc-' + tocItem._id);
105                tocItem.id = el.attr('id');
106
107                var parents = el.parents('.toc-item');
108                if (parents) {
109                    tocItem.parentId = parents.attr('id');
110                }
111
112                /*find a suitable title*/
113                if (!tocItem.title) tocItem.title = svc.findTextRecursive(el, function (el) { return el.attr('title'); });
114                if (!tocItem.title) tocItem.title = svc.findTextRecursive(el, function (el) { return (el[0].nodeType === 3)?el.text():''; });
115                tocItem.top = el.offset().top;
116                el.data('tocItem', tocItem);
117                svc.data.items.push(tocItem);
118            }
119            //Always update top positions because elements afftect eachother
120            tocItem.top = el.offset().top;
121        });
122
123        //Rebuild Hierarchy
124        svc.data.hierarchy = svc.getChild(null);
125        svc._onScroll();
126        $rootScope.$applyAsync();
127    }
128    svc.update = _.debounce(svc._update, 100);
129    svc.remove = function (element) {
130        var el = $(element);
131        var id = el.attr('id');
132        _.remove(svc.data.items, function (i) { return i.id == id; });
133        svc.update();
134    }
135
136    svc.findTextRecursive = function (element, fn) {
137        var title = fn(element);
138        if (title && title.match(/\S/)) return title;
139        var child = element.contents();
140        for (var i = 0; i < child.length; i++) {
141            var t = svc.findTextRecursive($(child[i]),fn);
142            if (t != '') return t;
143        }
144        return '';
145    };
146    svc.getChild = function (parentId) {
147        return _(svc.data.items)
148            .filter(function (i) { return i.parentId == parentId; })
149            .sortBy('top')
150            .map(function (i) {
151                return {
152                    id: i.id,
153                    item: i,
154                    child: svc.getChild(i.id)
155                };
156            })
157            .value();
158    }
159
160    //Start watching for scroll events
161    svc._onScroll = function () {
162        if (svc.elements) {
163            if (svc.activeItem) svc.activeItem.active = false;
164            var pageTop = $(svc._selector).offset().top;//$(window).scrollTop();
165            var pageBottom = $(window).height() - pageTop;// pageTop + $(window).height();
166            var activeItems = [], lastElementBottom=0;
167            for (var i = 0; i < svc.elements.length; i++) {
168                var element = $(svc.elements[i]);
169                var elementTop = $(element).offset().top;
170                var elementBottom = elementTop + $(element).height();
171                if (lastElementBottom < elementBottom) lastElementBottom = elementBottom;
172                var item = _.find(svc.data.items, function (o) { return o.id == element.attr('id'); }) || {};
173                item.top = elementTop;
174                if ((pageTop < elementBottom) && (pageBottom > elementTop)) {
175                    activeItems.push(item);
176                }
177            }
178            var newActiveItem = activeItems[0];
179            var positionTarget = pageTop;//$(svc._selector).height() * $(svc._selector).scrollTop() / ($(svc._selector).offset().top + $(svc._selector).scrollTop() + lastElementBottom - $(svc._selector).height());
180            //Select the item clostst to the top
181            _.forEach(activeItems, function (i) { if (Math.abs(i.top - positionTarget) < Math.abs(newActiveItem.to
181p - positionTarget)) newActiveItem = i; });
182            if (newActiveItem != svc.activeItem) {
183                svc.activeItem = newActiveItem;
184                svc.clearPath();
185                if (svc.activeItem) {
186                    svc.activeItem.active = true;
187                    svc.updatePath(svc.activeItem);
188                }
189                $rootScope.$applyAsync();
190            }
191
192        }
193    }
194    svc.clearPath = function () {
195        _.forEach(svc.data.items, function (i) { i.activePath=false; });
196    }
197    svc.updatePath = function (item){
198        item.activePath = true;
199        var parent = _.find(svc.data.items, function (o) { return o.id == item.parentId; });
200        if (parent) svc.updatePath(parent);
201    }
202
203    return svc;
204}]);

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.