/*!
License: refer to LICENSE file
*/
// last time the toggleMenu is called
var lastToggleMenu = (new Date()).getTime();
// initialize book object
var book;
// set gallery global variable so it can be accessed outside
var gallery;
// set date
var date = new Date();
// set battery
var battery_level = '-1';
// how long it takes to trigger actions in ms
var onFlipActionDelay = 1000;
function readBook(bc, bp) {
console.log('readBook', arguments)
// bc, bookcode
// bp, bookpage
// destroy exiting gallery already exists
destroyGallery(false);
// set screen size so if the image is resized, server remember the screen size
setScreenSize();
$.get('/listbooks', { bookcodes: bc }, function(jData) {
$('#container').removeClass('hidden');
book = jData[bc];
book.bookcode = bc;
book.lastpage = bp || book.page || 1;
$('#booktitle').html('
' + book.title + '
');
// set #pageslider max
$('#pageslider').attr('max', book.pages);
$('#pageslider').val(book.lastpage);
// set location hash if not set or diff
var hstr = '#book=' + book.bookcode + '&page=' + book.lastpage;
if (window.location.hash !== hstr) window.location.hash = hstr;
// create gallery
createGallery(bp);
// force trigger hashchange to load correct page
// window.dispatchEvent(new HashChangeEvent('hashchange'));
});
}
function updateDivCurrentInfo(page) {
if (typeof page === 'number') {
$('#pageCounter').html( gallery.pageIndex + '/' + book.pages );
}
$('#clock').html( date.toTimeString().slice(0,5) );
$('#battery').html( '🔋' + battery_level);
}
function sliderValue(el, e) {
var el = $(el);
var min = Number(el.attr('min'));
var max = Number(el.attr('max'));
var t;
if (e.originalEvent.touches) {
t = e.originalEvent.touches[0];
}
// else {
// t = e.originalEvent;
// }
var w = Number(el.width());
var x = w / max;
var l = el.position().left;
// approximate value on the slider position
var i = Math.ceil((t.pageX - l)/x );
if (i < min) {
i = min;
}
else if (i > max) {
i = max;
}
return i;
}
// destroy and remove the gallery
function destroyGallery(resetHash) {
if (gallery) gallery.destroy;
$('#wrapper').empty();
// remove listener
$(window).unbind('hashchange');
$(window).unbind('keydown');
if (resetHash === false) return;
// clear hash
window.location.hash = '';
}
// create the gallery
function createGallery(goPage) {
//document.addEventListener('touchmove', function (e) { e.preventDefault(); }, false);
// initialize gallery
var el,
i,
page;
//dots = document.querySelectorAll('.thumbnails ul li');
// initialize pages
var slides = [];
for (i=1; i<=book.pages; i++) {
if (isEasternBook()) {
// eastern book
slides.push( {
img: "/cbz/" + book.bookcode + "/" + (book.pages - i + 1),
page: book.pages - i + 1
} );
}
else {
// western book
slides.push( {
img: "/cbz/" + book.bookcode + "/" + i,
page: i
} );
}
}
gallery = new SwipeView('#wrapper', { numberOfPages: slides.length, loop: false, zoom: true });
// Load initial data
for (i=0; i<3; i++) {
page = i==0 ? slides.length-1 : i-1;
el = document.createElement('div');
el.id = 'swipeview-div-' + i;
el.className = 'loading';
// el.innerHTML = i + 1;
gallery.masterPages[i].appendChild(el);
el = document.createElement('img');
el.id = 'swipeview-img-' + i;
el.className = 'loading';
el.removeAttribute('src');
// el.src = '';
// el.src = slides[page].img;
el.onload = function () {
this.className = '';
this.previousSibling.className = '';
}
gallery.masterPages[i].appendChild(el);
}
// stagger loading image to reduce load
staggerImages(goPage);
gallery.onFlip(function () {
console.log('flip event!');
// global
if (!window.timerOnFlipSlide) window.window.timerOnFlipSlide = {};
var el,
upcoming,
i;
for (i=0; i<3; i++) {
upcoming = gallery.masterPages[i].dataset.upcomingPageIndex;
if (upcoming != gallery.masterPages[i].dataset.pageIndex) {
el = gallery.masterPages[i].querySelector('div');
el.className = 'loading';
el.innerHTML = slides[upcoming].page;
el = gallery.masterPages[i].querySelector('img');
el.className = 'loading';
// called by staggerImages
if (window.stopOnFlipImg) {
el.removeAttribute('src');
}
// normal flip
else {
// if (window.timerOnFlipSlide[i]) {
// console.log('stop load image!', i)
// clearTimeout(window.timerOnFlipSlide[i]);
// window.timerOnFlipSlide[i] = false;
// }
// window.timerOnFlipSlide[i] = setTimeout(function() {
// console.log('load image!', this.src)
// this.el.src = this.src;
// }.bind({
// el: el,
// src: slides[upcoming].img
// }), onFlipActionDelay);
el.src = slides[upcoming].img;
}
}
// else {
// if (window.timerOnFlipSlide[i]) {
// console.log('stop load image!!!', i)
// clearTimeout(window.timerOnFlipSlide[i]);
// window.timerOnFlipSlide[i] = false;
// }
// }
}
// reset
window.stopOnFlipImg = false;
// get current page
var pg = gallery.pageIndex;
if (isEasternBook()) {
pg = book.pages - gallery.pageIndex;
}
// update div current info
updateDivCurrentInfo(pg);
// change title according to page
document.title = "(" + pg + "/" + book.pages + ")";
// set the page hash
window.noHashchange = true; // make sure no hashchange is triggered
window.location.hash = fullhash(pg);
// set bookmark only if stopped at page
if (window.timerOnFlipSlide.bookmark) {
clearTimeout(window.timerOnFlipSlide.bookmark);
window.timerOnFlipSlide.bookmark = false;
}
window.timerOnFlipSlide.bookmark = setTimeout(function() {
setBookmark(this.bookcode, this.pg);
}.bind({
bookcode: book.bookcode,
pg: pg
}), onFlipActionDelay);
// set the slider displayed page
$('#pageinput').val(pg);
$('#pageslider').val(pg);
});
gallery.onMoveOut(function () {
console.log('moveout');
gallery.masterPages[gallery.currentMasterPage].className = gallery.masterPages[gallery.currentMasterPage].className.replace(/(^|\s)swipeview-active(\s|$)/, '');
// get current page
var pg = gallery.pageIndex;
if (isEasternBook()) {
pg = book.pages - gallery.pageIndex;
}
var el = gallery.masterPages[gallery.currentMasterPage].querySelector('div');
el.innerHTML = pg;
el.className += 'loading';
// update current info
updateDivCurrentInfo(pg);
});
gallery.onMoveIn(function () {
console.log('movein');
var className = gallery.masterPages[gallery.currentMasterPage].className;
/(^|\s)swipeview-active(\s|$)/.test(className) || (gallery.masterPages[gallery.currentMasterPage].className = !className ? 'swipeview-active' : className + ' swipeview-active');
});
// end of gallery code
// go to page if specified
if (goPage) {
// launch a moment later, to go around loading issue
window.setTimeout( function(e) { goToPage(goPage); }, 300);
}
// now add listener
// hash change
$(window).bind('hashchange', function() {
// do no trigger, because of onFlip
if (window.noHashchange) {
// reset
window.noHashchange = false;
return;
}
// replace the history
if (getpage() < 1) {
window.location.replace( '#' + fullhash( 1 ) );
}
else if (getpage() > book.pages) {
window.location.replace( '#' + fullhash( book.pages ) );
}
// launch a moment later, to go around loading issue
window.setTimeout( function(e) { goToPage(getpage()); }, 50);
});
// // keyboard commands
$(window).bind('keydown', function h_kd(e) {
e = e || window.event;
switch (e.keyCode) {
case 37:
// left button, previous page
goToPage( getpage() - 1 );
break;
case 39:
// right button, next page
goToPage( getpage() + 1 );
break;
case 27:
// escape button, go back to browse
closeReader();
return false;
break;
case 13:
// enter key, show/hide menu
togglemenu();
break;
}
});
}
// set the bookmark
function setBookmark(bookcode, page) {
var page = getpage();
if (book.lastpage == page || page < 1 || page > book.pages) return false;
$.ajax({
url: "/setbookmark/" + bookcode + "/" + page,
beforeSend: function ( xhr ) {
xhr.overrideMimeType("text/plain; charset=x-user-defined");
}
}).done(function ( data ) {
if( 1==2 && console && console.log ) {
console.log("Sample of data:", data);
}
});
// update last rendered page
book.lastpage = page;
}
function closeReader() {
$('#container').addClass('hidden');
destroyGallery();
reload_books( $('#bookinfo').attr('bookcodes') );
}
function isEasternBook() {
return ( $('#readdirection :radio:checked').attr('id') == 'readtoleft' ) ? true : false;
}
// go to particular page
// in relative to book
// not relative to gallery, which u can find out by page - 1
function goToPage(page) {
page = Number(page);
console.log('going to page', page);
if (page < 1) return false;
if (isEasternBook()) {
gallery.goToPage(book.pages - page);
}
else {
gallery.goToPage(page - 1);
}
staggerImages(page);
}
function staggerImages(page) {
var i;
if (isEasternBook()) {
i = book.pages - page;
}
else {
i = page - 1;
}
// global
window.stopOnFlipImg = true;
window.imageQueue = [
// current page
{
igal: '[data-page-index=' + i + ']',
url: "/cbz/" + book.bookcode + "/" + page
},
// next page
{
igal: '[data-page-index=' + (i+1) + ']',
url: "/cbz/" + book.bookcode + "/" + (page + 1)
},
// prev page
{
igal: '[data-page-index=' + (i-1) + ']',
url: "/cbz/" + book.bookcode + "/" + (page - 1)
},
];
// do first image
loadImage();
}
function loadImage() {
var dat = window.imageQueue.shift();
// double trigger, stop
if (window.currentImage && window.currentImage.url === dat.url) return;
window.currentImage = dat;
var img = el = $('
');
img.on('load', function() {
console.log('loaded image in background', this.dat)
// change img src
var el = $(this.dat.igal);
el.find('img').attr('src', this.dat.url).removeClass('loading');
el.find('div').removeClass('loading');
el.css('visibility','visible');
// do more if exists
if (window.imageQueue && window.imageQueue.length > 0) {
loadImage();
}
// all done, clear
else {
window.currentImage = false;
}
}.bind({
dat: dat
}));
// exec
console.log('starting image', dat)
img.attr('src', dat.url);
}
// get the page from hash
function getpage() {
var i = parseInt( getHashParams()['page'] );
if (typeof i == "number" && ! isNaN(i) ) {
return i;
}
return -1;
}
// toggle menu
function togglemenu() {
if ($('#readermenu').hasClass('showtop')) {
hidemenu();
}
else {
showmenu();
}
var t = new Date();
lastToggleMenu = t.getTime();
}
// show menu
function showmenu() {
// show the menu
$('#booktitle').addClass('showtop');
$('#readermenu').addClass('showtop');
}
function hidemenu() {
// set header & footer hidden
$('#booktitle').removeClass('showtop');
$('#readermenu').removeClass('showtop');
}
// show/hide menu when touch the page
function hasMoved(b,e) {
// move threshold
var mt = 5;
// shortcut for getting object
//var b = begin.originalEvent.changedTouches[0];
//var e = end.originalEvent.changedTouches[0];
// **hack**
// changed to array form because iOS+jQuery dont handle originalEvent and changedTouches correctly
// it doesn't store the last_touchstart correctly (it holds current one instead, so touchstart and touchend always ended up same value)
if (Math.abs(b[0] - e[0]) > mt || Math.abs(b[1] - e[1]) > mt) {
//console.log('moved');
return true;
}
else {
//console.log('not moved');
return false;
}
}
function toggleFullScreen(id) {
var elem = document.getElementById(id);
var btn = $('#gofullscreen'); // button for toggle full screen
if (isFullScreen()) {
btn.text('full screen');
exitFullScreen();
}
else {
btn.text('exit full screen');
goFullScreen(id);
}
// refresh button text
btn.button('refresh');
}