PageSourceSearch

https://edicoladigitale.italiaoggi.it/class/assets/js/areas/reader/SwiperUI.js?v=20

js italiaoggi.it collected 2026-09-24 08:52:43 UTC 15,136 bytes, 424 lines download raw bytes

1/**
2 * Created by Sara on 6/10/2019.
3 */
4function SwiperUi() {
5
6  var self = this;
7  var _container = '.vc_container_reader .swiper-container';
8  var edition = VNP.getEdition();
9  var totalPages = VNP.Areas.Reader.getTotalPages();
10  var booksPath = VNP.Areas.Reader.getBooksPath();
11  var dateFormat = "DD/MM/YYYY"; // date format from settings
12  var page = null;
13  var $activePageNumber = $(".activePageNumber");
14  var $totalPages = $(".totalPages");
15  self.regions = new Regions();
16
17  /* set double page */
18  self.setDoublePage = function (swiper) {
19
20    if( VNP.Areas.Reader.getActivePage() === 1 ){
21      //first page and ghost one
22      swiper.slideTo(1);
23      location.hash = "/1/";
24    }
25  };
26
27  /* set one page */
28  self.unsetDoublePage = function (swiper) {
29
30    if( $(swiper.slides[swiper.activeIndex]).attr("data-page") == 0 ){
31      //first page and ghost one
32      swiper.slideTo(1);
33      location.hash = "/1/";
34    }
35
36    if( VNP.Areas.Reader.getActivePage() > VNP.Areas.Reader.getTotalPages() ){
37      //last page and ghost one
38      swiper.slideTo(VNP.Areas.Reader.getTotalPages());
39      location.hash = "/" + VNP.Areas.Reader.getTotalPages() + "/";
40    }
41  };
42
43  /* when resize window set or unset double page*/
44  $(window).on("resize", function () {
45
46    var $contImg = $(".vc_cont_img");
47    VNP.Areas.Reader.isDoublePage = VNP.getDevice().isDoublePage;
48    VNP.setIsMobile( VNP.getDevice().isMobile );
49
50    renderCurrentPages();
51    // because it removes a slide we need to recalculate the page number
52    var page = (VNP.Areas.Reader.getActivePage() > VNP.Areas.Reader.getTotalPages()) ? VNP.Areas.Reader.getTotalPages() : VNP.Areas.Reader.getActivePage();
53    $activePageNumber.text(page);
54
55    // go to real slide and not the ghost one in monopage version
56    if( !VNP.Areas.Reader.isDoublePage && $(".swiper-slide-active").hasClass("vc_visibility_hidden") && page === 1 ){
57      swiper.slideTo(1, 0);
58    }
59
60    //resize the cont images for positioning regions
61    $contImg.width('auto');
62    $contImg.height('auto');
63
64  });
65
66
67  var forcedElementsOpened = [];
68  var triggerElementsForcedToShow = function (hashPageNumber) {
69    // If you go from page 1 to next page hashPageNumber is 2, so the below if returns false. If you go from page 4 the hasPageNumber is 3 but i need it is 2
70    if (hashPageNumber > 1 && hashPageNumber % 2 != 0) hashPageNumber = hashPageNumber - 1;
71    for (var pageNumber = hashPageNumber; pageNumber <= hashPageNumber + 1; pageNumber++) { // Cycle the left and right page
72      for (var i = 0; i < self.regions.getRegionsByPage(pageNumber).length; i++) { // Get all regions for these pages
73        var region = self.regions.getRegion(self.regions.getRegionsByPage(pageNumber)[i], pageNumber);
74        if (region.data.force_view && forcedElementsOpened.indexOf(region.id) < 0) { // Search the first one with force_view at 3 and open it
75          forcedElementsOpened.push(region.id);
76          $("#reg" + (i+1)).click();
77          return;
78        }
79      }
80    }
81  };
82
83
84  self.lockSwipes = function () {
85    swiper.allowSlideNext = false;
86    swiper.allowSlidePrev = false;
87  };
88
89
90  self.unlockSwipes = function () {
91    swiper.allowSlideNext = true;
92    swiper.allowSlidePrev = true;
93  };
94
95
96  self.getCurrentPages = function(){
97
98    const activePage = VNP.Areas.Reader.getActivePage();
99    const pages = [activePage];
100
101    if(!VNP.Areas.Reader.isDoublePage || activePage <= 1){
102      return pages;
103    }
104
105    const nextPage = activePage + 1;
106    const hasNextPage = nextPage <= totalPages;
107    if(hasNextPage){
108      pages.push(nextPage);
109    }
110
111    return pages;
112  };
113
114
115  /*
116   * remove regions from reader
117   * */
118  var removeRegions = function () {
119    $(_container).find('.region').remove();
120  };
121
122  // Render current visible pages
123  var renderCurrentPages = function () {
124    var pages = self.getCurrentPages();
125    for (var i = 0; i < pages.length; i++) {
126      self.renderPage(pages[i]);
127    }
128  };
129
130  /*
131   * get img by page
132   * @param page {Integer} : page number
133   *
134   * */
135  var getPageElement = function (page) {
136    return $(_container).find('.swiper-slide[data-page=' + page + '] img');
137  };
138
139  // Render single page
140  self.renderPage = function (page) {
141
142    $(_container).find("[data-page=" + page + "] .region").remove();
143    var regionsOnPage = self.regions.getRegionsByPage(page);
144    for (var i = 0; i < regionsOnPage.length; i++) {
145      renderRegionOnPage(regionsOnPage[i], page);
146    }
147
148    let regExtLinks = self.regions.getExternalRegionsByPage(page);
149    for(let j = 0; j < regExtLinks.length; j++){
150      renderRegionOnPage(regExtLinks[j], page);
151    }
152
153  };
154
155  //Render single region on page
156  var renderRegionOnPage = function (reg, page) {
157    /* Create region html element */
158    var region = self.regions.getRegion(reg, page);
159    var target = (region.object == "fullpage") ? "overlay" : "_blank";
160    var counter = 0;
161    var multimediaObject;
162
163    if( region.x == 0 && region.y == 0 ) {
164      return;
165    }
166
167    // check if the page is the same of the region and then remove it.
168    // sometimes ids of the article's regions have the same id of the multimedia regions
169
170    $(".swiper-slide[data-page=" + page + "]").find('#' + reg + "." + region.object).remove();
171
172    var $region = $('<div>').attr("id", reg).addClass('region').addClass(region.object);
173    $region.css({
174      "top": region.y + "%",
175      "left": region.x + "%",
176      "width": region.width + "%",
177      "height": region.height + "%"
178    });
179
180    $region.data("page", page);
181    $region.data("type", region.object);
182    var $infoBox = $("<div class='vc-info-box'></div>");
183
184    if (region.object == "jumppage" && region.data) {
185      $region.data("pageJump", region.data.page);
186      var $edition = moment(region.data.issue).format(dateFormat);
187      var $jumppage = $region.data("pageJump");
188
189      $infoBox.html(VNP.getLanguagesKey["edition"] + ": " + $edition + " <br> "+ VNP.getLanguagesKey["page"] +": <span='vc-num-page'>" + $jumppage + "</span>");
190      $region.append($infoBox);
191    }
192
193    getPageElement(page).before($region);
194
195    var iconPosition = self.regions.getRegion(reg, page).iconPosition;
196
197    $region.attr('data-id', region.id);
198    $region.attr('data-target', target);
199    $region.attr('data-num', counter);
200    if (region.object == "textual-article") {
201      $region.attr('data-url', region.data.url);
202    }
203
204    if(region.object === "fullpage"){
205      $region.attr('onclick', "window.open('"+region.data.html5+"');");
206    }
207
208    if (region.object == "jumppage") {
209      var titleEdition = region.data["titleEdition"];
210      var pageToJump = region.data.page;
211      if (region.data.page % 2 > 0) pageToJump = pageToJump - 1;
212
213      if (titleEdition == edition) {
214        $region.attr('onclick', "VNP.Areas.Reader.swiperUi.goToSlide(parseInt(" + pageToJump + "))");
215        $region.removeAttr("data-source");
216      } else {
217        var urlToJump = VNP.baseUrl + "/" + booksPath + "#" + pageToJump;
218        $region.addClass("jumppageWindow");
219        $region.attr("data-source", urlToJump);
220      }
221    }
222
223    $region.append("<p class='icon-media " + self.regions.getRegion(reg, page).class + "' style='left:" + iconPosition.x + "%;top:" + iconPosition.y + "%'></p>");
224
225    // bind click on multimedia object
226    $region.on("click", function () {
227      VNP.Areas.Reader.module.Multimedia.openSingleMedia(region);
228    });
229
230    counter++;
231    self.unlockSwipes();
232  };
233
234  /*
235   * Navigation controls
236   * */
237  self.goToSlide = function (slide) {
238    swiper.slideTo(slide, 10, true);
239  };
240
241  self.nextSlide = function () {
242    if(VNP.Areas.Reader.getActivePage() == totalPages ) return;
243    swiper.slideNext();
244  };
245
246  self.prevSlide = function () {
247    swiper.slidePrev();
248  };
249
250  self.firstSlide = function () {
251    self.goToSlide(parseInt(0));
252  };
253
254  self.lastSlide = function () {
255    self.goToSlide(totalPages);
256  };
257
258  /*
259   * The reader supports both Swiper 4 and Swiper 12, selected at runtime by the
260   * `useSwiper12` editore flag (surfaced by frontend.ftl as window.SWIPER12).
261   * The bundle that gets loaded matches the flag; here we build the matching
262   * config. Version differences:
263   *  - lazy loading: v4 `lazy:true`/`preloadImages:false` vs v12 `lazyPreloadPrevNext`
264   *  - breakpoints:  v4 max-width vs v12 min-width (changed in Swiper 5)
265   *  - page-change:  v4 fires slideChangeTransitionEnd reliably and its
266   *                  hashNavigation writes the URL hash; v12's transitionEnd is
267   *                  unreliable and hashNavigation no longer writes the hash, so
268   *                  v12 does the work on slideChange and writes the hash itself
269   *  - doubleTap args: v4 (event) vs v12 (swiper, event) — Swiper >= 9 prepends
270   *                  the swiper instance to every handler's arguments
271   *  - single-page first slide: v4 uses breakpoint `initialSlide`, v12 slideTo on init
272   */
273  var isSwiper12 = !!window.SWIPER12;
274
275  /* Shared page-change work: keep the active page, reader UI, regions,
276   * enrichments and zoom preloading in sync. Called from the version-appropriate
277   * Swiper event below. */
278  var handlePageChange = function () {
279    removeRegions();
280    VNP.Areas.Reader.setActivePage();
281    var page = VNP.Areas.Reader.getActivePage();
282    $activePageNumber.text(page);
283
284    if ( VNP.Areas.Reader.swiperPages != undefined )
285      VNP.Areas.Reader.setActivePageSwiperPages(page);
286
287    renderCurrentPages();
288    triggerElementsForcedToShow(page);
289    VNP.Areas.Reader.module.Zoom.preload();
290    VNP.Areas.Reader.module.Multimedia.setMultimediaByPage( page );
291    VNP.Areas.Reader.module.Articles.setArticlesByPage( page );
292
293    if (VNP.getDevice().isMobile) {
294      VNP.Areas.Reader.setTotalAmount();
295    }
296  };
297
298  var swiperInit = function () {
299
300    // v12 only: in single-page mode jump off the hidden ghost slide (index 0) to
301    // the real active page. Swiper 4 does this with `initialSlide:1` in the
302    // single-page breakpoints, no longer honoured in Swiper 9+.
303    // Deferred to a later tick: `init` fires *during* `new Swiper()`, before
304    // VNP.Areas.Reader.swiperUi is assigned, and a synchronous slideTo would fire
305    // slideChange -> Zoom.preload() -> getCurrentPages() on the undefined
306    // swiperUi and throw, aborting initialization.
307    if (isSwiper12 && this.params.slidesPerView === 1) {
308      var swiperInstance = this;
309      setTimeout(function () {
310        swiperInstance.slideTo(VNP.Areas.Reader.getActivePage(), 0);
311      }, 0);
312    }
313
314    // notify the user how to enable zoom
315    if( VNP.Areas.Reader.getConsultationTime() > 0 || VNP.Areas.Customer.getCanRead() ) {
316      var message = (VNP.getDevice().isMobile) ? VNP.getLanguagesKey["pageflip_how_zoom_mob"] : VNP.getLanguagesKey["pageflip_how_zoom_desk"];
317      VNP.Areas.Reader.module.Zoom.notify(message);
318    }
319
320    // callback for load multimedia elements to render the page active
321    VNP.Areas.Reader.module.Multimedia.loadMediaSwiper(edition, function (data) {
322      var page = VNP.Areas.Reader.getActivePage();
323      self.regions.setRegions(data);
324      VNP.Areas.Reader.module.Zoom.preload();
325      renderCurrentPages();
326
327      $activePageNumber.text(page);
328      $totalPages.text(totalPages);
329
330      if (VNP.getIsMobile()) {
331        VNP.Areas.Reader.setTotalAmount();
332      }
333
334    }, false);
335  };
336
337  var swiperEvents = {
338    init: swiperInit,
339    doubleTap: isSwiper12
340      ? function (swiper, event) { VNP.Areas.Reader.module.Zoom.toggle(event); }
341      : function (event) { VNP.Areas.Reader.module.Zoom.toggle(event); },
342    reachEnd: function () { this.slideTo(VNP.Areas.Reader.getTotalPages()); },
343    reachBeginning: function () { this.slideTo(1); }
344  };
345
346  if (isSwiper12) {
347    // v12: transitionEnd is unreliable and hashNavigation no longer writes the
348    // hash, so do the work on slideChange and write the hash ourselves.
349    swiperEvents.slideChange = function () {
350      var activeSlide = this.slides[this.activeIndex];
351      if (activeSlide) {
352        var slideHash = activeSlide.getAttribute("data-hash");
353        if (slideHash && location.hash !== "#" + slideHash) {
354          location.hash = slideHash;
355        }
356      }
357      handlePageChange();
358    };
359  } else {
360    // v4: hashNavigation writes the hash and slideChangeTransitionEnd fires
361    // reliably, so the hash is already set by the time we read it here. Regions
362    // are dropped at the start of the transition, as in the original.
363    swiperEvents.slideChangeTransitionStart = function () {
364      removeRegions();
365    };
366    swiperEvents.slideChangeTransitionEnd = function () {
367      handlePageChange();
368    };
369  }
370
371  var swiperOptions = {
372    slidesPerView       : 2,
373    slidesPerGroup      : 2,
374    centeredSlides      : false,
375    zoom                : false,
376    spaceBetween        : 0,
377    mousewheel          : true,
378    noSwiping           : true,
379    hashNavigation      : { watchState: true },
380    keyboard            : true,
381    runCallbacksOnInit  : false,
382    navigation          : { nextEl: "#vc_btn_next", prevEl: "#vc_btn_prev" },
383    on                  : swiperEvents,
384    breakpoints         : isSwiper12 ? {
385      /* Swiper >= 5 min-width breakpoints (same ranges as the v4 max-width set):
386       * 0-480 single, 481-569 double, 570-600 single, 601-736 double,
387       * 737-768 single, 769+ double */
388      0:   { slidesPerGroup: 1, slidesPerView: 1, centeredSlides: true },
389      481: { slidesPerGroup: 2, slidesPerView: 2, centeredSlides: false },
390      570: { slidesPerGroup: 1, slidesPerView: 1, centeredSlides: true },
391      601: { slidesPerGroup: 2, slidesPerView: 2, centeredSlides: false },
392      737: { slidesPerGroup: 1, slidesPerView: 1, centeredSlides: true },
393      769: { slidesPerGroup: 2, slidesPerView: 2, centeredSlides: false }
394    } : {
395      /* Swiper 4 max-width breakpoints (original) */
396      480:  { slidesPerGroup: 1, slidesPerView: 1, initialSlide: 1, centeredSlides: true },
397      481:  { slidesPerGroup: 2, slidesPerView: 2, initialSlide: 0, centeredSlides: false },
398      569:  { slidesPerGroup: 2, slidesPerView: 2, initialSlide: 0, centeredSlides: false },
399      600:  { slidesPerGroup: 1, slidesPerView: 1, initialSlide: 1, centeredSlides: true },
400      640:  { slidesPerGroup: 2, slidesPerView: 2, initialSlide: 0, centeredSlides: false },
401      731:  { slidesPerGroup: 2, slidesPerView: 2, initialSlide: 0, centeredSlides: false },
402      736:  { slidesPerGroup: 2, slidesPerView: 2, initialSlide: 0, centeredSlides: false },
403      768:  { slidesPerGroup: 1, slidesPerView: 1, initialSlide: 1, centeredSlides: true },
404      900:  { slidesPerGroup: 2, slidesPerView: 2, initialSlide: 0, centeredSlides: false },
405      1024: { slidesPerGroup: 2, slidesPerView: 2, initialSlide: 0, centeredSlides: false }
406    }
407  };
408
409  if (isSwiper12) {
410    swiperOptions.lazyPreloadPrevNext = 2;
411  } else {
412    swiperOptions.lazy = true;
413    swiperOptions.preloadImages = false;
414    swiperOptions.paginationClickable = true;
415  }
416
417  /* Initiliazing swiper script */
418  var swiper = new Swiper(_container, swiperOptions);
419
420  self.destroy = function () {
421    swiper.destroy(true);
422  };
423
424}

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.