mirror of
https://github.com/flynx/ImageGrid.git
synced 2025-10-29 10:20:08 +00:00
added skipping images one screen left/right, some more refactoring...
Signed-off-by: Alex A. Naanou <alex.nanou@gmail.com>
This commit is contained in:
parent
3e7711e829
commit
85414c77fe
@ -52,7 +52,7 @@ function setup(){
|
|||||||
setDefaultInitialState()
|
setDefaultInitialState()
|
||||||
|
|
||||||
// XXX
|
// XXX
|
||||||
setBackgroundMode('dark')
|
toggleSingleImageMode('off')
|
||||||
enableTransitions()
|
enableTransitions()
|
||||||
|
|
||||||
// setup event handlers...
|
// setup event handlers...
|
||||||
@ -68,11 +68,6 @@ function setup(){
|
|||||||
// XXX STUB
|
// XXX STUB
|
||||||
loadImages(image_list)
|
loadImages(image_list)
|
||||||
|
|
||||||
// setup the dragging framework...
|
|
||||||
// XXX make this work seamlessly with touchSwipe...
|
|
||||||
// XXX cancel clicks while dragging...
|
|
||||||
$('.field').draggable()
|
|
||||||
|
|
||||||
// set the default position and init...
|
// set the default position and init...
|
||||||
$('.current.image').click()
|
$('.current.image').click()
|
||||||
|
|
||||||
|
|||||||
@ -1,6 +1,8 @@
|
|||||||
// XXX need a uniform way to address images (filename?)
|
// XXX need a uniform way to address images (filename?)
|
||||||
/******************************************* Setup Data and Globals **/
|
/******************************************* Setup Data and Globals **/
|
||||||
|
|
||||||
|
var DEBUG = true
|
||||||
|
|
||||||
// the list of style modes...
|
// the list of style modes...
|
||||||
// these are swithched through in order by toggleBackgroundModes()
|
// these are swithched through in order by toggleBackgroundModes()
|
||||||
var BACKGROUND_MODES = [
|
var BACKGROUND_MODES = [
|
||||||
@ -9,29 +11,50 @@ var BACKGROUND_MODES = [
|
|||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
|
// remember the default backgrounds for modes...
|
||||||
|
// ...this effectively makes the modes independant...
|
||||||
|
// NOTE: null represent the default value...
|
||||||
|
// NOTE: these will change if changed in runtime...
|
||||||
|
var NORMAL_MODE_BG = 'dark'
|
||||||
|
var SINGLE_IMAGE_MODE_BG = BACKGROUND_MODES[BACKGROUND_MODES.length-1]
|
||||||
|
|
||||||
|
|
||||||
|
// ribbon/single view modes...
|
||||||
|
// store the scale before we went into single image mode...
|
||||||
|
// NOTE: these will change if changed in runtime...
|
||||||
|
var ORIGINAL_FIELD_SCALE = 1.0
|
||||||
|
|
||||||
|
|
||||||
// this sets the zooming factor used in manual zooming...
|
// this sets the zooming factor used in manual zooming...
|
||||||
var ZOOM_FACTOR = 2
|
var ZOOM_FACTOR = 2
|
||||||
|
|
||||||
|
|
||||||
// sets the amoun of move when a key is pressed...
|
// sets the amount of move when a key is pressed...
|
||||||
var MOVE_DELTA = 50
|
var MOVE_DELTA = 50
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/********************************************************** Helpers **/
|
/********************************************************** Helpers **/
|
||||||
|
|
||||||
|
|
||||||
// this will create a function that will add/remove a css_class to elem
|
// this will create a function that will add/remove a css_class to elem
|
||||||
// calling the callbacks before and/or after.
|
// calling the optional callbacks before and/or after.
|
||||||
// NOTE: of only one callback is given then it will be called after the
|
//
|
||||||
// class change...
|
// elem is a jquery compatible object; default use-case: a css selector.
|
||||||
// a way around this is to pass an empty function as callback_b
|
//
|
||||||
// the resulting function understands the folowing arguments:
|
// the resulting function understands the folowing arguments:
|
||||||
// - 'on' : switch mode on
|
// - 'on' : switch mode on
|
||||||
// - 'off' : switch mode off
|
// - 'off' : switch mode off
|
||||||
// - '?' : return current state ('on'|'off')
|
// - '?' : return current state ('on'|'off')
|
||||||
// - no arguments : toggle the state
|
// - no arguments : toggle the state
|
||||||
|
//
|
||||||
|
// NOTE: of only one callback is given then it will be called after the
|
||||||
|
// class change...
|
||||||
|
// a way around this is to pass an empty function as callback_b
|
||||||
|
//
|
||||||
function createCSSClassToggler(elem, css_class, callback_a, callback_b){
|
function createCSSClassToggler(elem, css_class, callback_a, callback_b){
|
||||||
// prepare the pre/post callbacks...
|
// prepare the pre/post callbacks...
|
||||||
if(callback_b == null){
|
if(callback_b == null){
|
||||||
@ -204,9 +227,13 @@ function setupEvents(){
|
|||||||
$('.current.image').click()
|
$('.current.image').click()
|
||||||
})
|
})
|
||||||
// keyboard...
|
// keyboard...
|
||||||
$(document)
|
if(DEBUG){
|
||||||
.keydown(makeKeyboardHandler(keybindings, function(k){alert(k)}))
|
$(document)
|
||||||
//.keydown(handleKeys)
|
.keydown(makeKeyboardHandler(keybindings, function(k){alert(k)}))
|
||||||
|
} else {
|
||||||
|
$(document)
|
||||||
|
.keydown(makeKeyboardHandler(keybindings))
|
||||||
|
}
|
||||||
// swipe...
|
// swipe...
|
||||||
$('.viewer')
|
$('.viewer')
|
||||||
.swipe({
|
.swipe({
|
||||||
@ -215,13 +242,19 @@ function setupEvents(){
|
|||||||
swipeUp: shiftImageUp,
|
swipeUp: shiftImageUp,
|
||||||
swipeDown: shiftImageDown
|
swipeDown: shiftImageDown
|
||||||
})
|
})
|
||||||
|
// dragging...
|
||||||
|
// XXX make this work seamlessly with touchSwipe...
|
||||||
|
// XXX cancel clicks while dragging...
|
||||||
|
// XXX this does not work on android...
|
||||||
|
$('.field').draggable()
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
function setupControlElements(){
|
function setupControlElements(){
|
||||||
// images...
|
// images...
|
||||||
$(".image").click(setCurrentImage)
|
$(".image").click(handleImageClick)
|
||||||
|
|
||||||
// buttons...
|
// buttons...
|
||||||
$('.screen-button.next-image').click(nextImage)
|
$('.screen-button.next-image').click(nextImage)
|
||||||
@ -259,7 +292,7 @@ function loadImages(json){
|
|||||||
.css({ 'background-image': 'url('+images[i]+')' })
|
.css({ 'background-image': 'url('+images[i]+')' })
|
||||||
// set a unique id for each image...
|
// set a unique id for each image...
|
||||||
.attr({'id': i})
|
.attr({'id': i})
|
||||||
.click(setCurrentImage)
|
.click(handleImageClick)
|
||||||
.appendTo(ribbon)
|
.appendTo(ribbon)
|
||||||
}
|
}
|
||||||
ribbon.children().first().click()
|
ribbon.children().first().click()
|
||||||
@ -324,7 +357,7 @@ function loadJSON(data){
|
|||||||
$('<div class="image"></div>')
|
$('<div class="image"></div>')
|
||||||
.css({ 'background-image': 'url('+image.attr('url')+')' })
|
.css({ 'background-image': 'url('+image.attr('url')+')' })
|
||||||
.attr({'id': j})
|
.attr({'id': j})
|
||||||
.click(setCurrentImage)
|
.click(handleImageClick)
|
||||||
.appendTo(ribbon)
|
.appendTo(ribbon)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -332,9 +365,10 @@ function loadJSON(data){
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The folowing two functions will get the vertical and horizontal
|
* The folowing two functions will get the vertical and horizontal
|
||||||
* distance components between the pints a and A, centers of the small
|
* distance components between the points a and A, centers of the small
|
||||||
* and large squares respectively.
|
* and large squares respectively.
|
||||||
* One of the squares is .field and the other is .container,
|
* One of the squares is .field and the other is .container,
|
||||||
* which is small or big is not important.
|
* which is small or big is not important.
|
||||||
@ -382,9 +416,6 @@ function getCurrentVerticalOffset(image){
|
|||||||
var mh = h - ribbons.outerHeight()
|
var mh = h - ribbons.outerHeight()
|
||||||
// current ribbon position (1-based)
|
// current ribbon position (1-based)
|
||||||
var rn = ribbons.index(ribbon) + 1
|
var rn = ribbons.index(ribbon) + 1
|
||||||
// XXX compensating for margin error buildup... really odd!
|
|
||||||
// ...why is this still different for the first three ribbons?!
|
|
||||||
// ....sub-pixel error?
|
|
||||||
// relative position to field...
|
// relative position to field...
|
||||||
// XXX is there a better way to get this?
|
// XXX is there a better way to get this?
|
||||||
var t = rn * (h - mh/2)
|
var t = rn * (h - mh/2)
|
||||||
@ -465,9 +496,13 @@ function alignRibbon(image, position){
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*************************************************** Event Handlers **/
|
/*************************************************** Event Handlers **/
|
||||||
|
|
||||||
function setCurrentImage(){
|
// handle click for images...
|
||||||
|
function handleImageClick(){
|
||||||
// set classes...
|
// set classes...
|
||||||
$('.current').removeClass('current')
|
$('.current').removeClass('current')
|
||||||
$(this)
|
$(this)
|
||||||
@ -524,7 +559,7 @@ function alignRibbons(){
|
|||||||
* Basic key format:
|
* Basic key format:
|
||||||
* <key-code> : <callback>,
|
* <key-code> : <callback>,
|
||||||
* <key-code> : {
|
* <key-code> : {
|
||||||
* default: [<callback>, <doc>],
|
* 'default': <callback>,
|
||||||
* // a modifier can be any single modifier, like shift or a
|
* // a modifier can be any single modifier, like shift or a
|
||||||
* // combination of modifers like 'ctrl+shift', given in order
|
* // combination of modifers like 'ctrl+shift', given in order
|
||||||
* // of priority.
|
* // of priority.
|
||||||
@ -570,7 +605,7 @@ function makeKeyboardHandler(keybindings, unhandled){
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// callback...
|
// simple callback...
|
||||||
handler()
|
handler()
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
@ -583,52 +618,39 @@ function makeKeyboardHandler(keybindings, unhandled){
|
|||||||
|
|
||||||
/************************************************************ Modes **/
|
/************************************************************ Modes **/
|
||||||
|
|
||||||
// ribbon/single view modes...
|
|
||||||
// global: stores the scale before we went into single image mode...
|
|
||||||
// XXX HACK
|
|
||||||
var _ORIGINAL_FIELD_SCALE = 1
|
|
||||||
|
|
||||||
|
|
||||||
// remember the default backgrounds for modes...
|
|
||||||
// ...this effectively makes the modes independant...
|
|
||||||
// NOTE: null represent the default value...
|
|
||||||
// XXX HACK
|
|
||||||
var _NORMAL_MODE_BG = null
|
|
||||||
var _SINGLE_IMAGE_MODE_BG = BACKGROUND_MODES[BACKGROUND_MODES.length-1]
|
|
||||||
|
|
||||||
|
|
||||||
var toggleSingleImageMode = createCSSClassToggler('.viewer', 'single-image-mode',
|
var toggleSingleImageMode = createCSSClassToggler('.viewer', 'single-image-mode',
|
||||||
// pre...
|
// pre...
|
||||||
function(action){
|
function(action){
|
||||||
if(action == 'on'){
|
if(action == 'on'){
|
||||||
_NORMAL_MODE_BG = getBackgroundMode()
|
NORMAL_MODE_BG = getBackgroundMode()
|
||||||
_ORIGINAL_FIELD_SCALE = getElementScale($('.field'))
|
ORIGINAL_FIELD_SCALE = getElementScale($('.field'))
|
||||||
} else {
|
} else {
|
||||||
_SINGLE_IMAGE_MODE_BG = getBackgroundMode()
|
SINGLE_IMAGE_MODE_BG = getBackgroundMode()
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
// post...
|
// post...
|
||||||
function(action){
|
function(action){
|
||||||
if(action == 'on'){
|
if(action == 'on'){
|
||||||
fitImage()
|
fitImage()
|
||||||
setBackgroundMode(_SINGLE_IMAGE_MODE_BG)
|
setBackgroundMode(SINGLE_IMAGE_MODE_BG)
|
||||||
} else {
|
} else {
|
||||||
setContainerScale(_ORIGINAL_FIELD_SCALE)
|
setContainerScale(ORIGINAL_FIELD_SCALE)
|
||||||
setBackgroundMode(_NORMAL_MODE_BG)
|
setBackgroundMode(NORMAL_MODE_BG)
|
||||||
}
|
}
|
||||||
clickAfterTransitionsDone()
|
clickAfterTransitionsDone()
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
||||||
// wide view mode toggle...
|
// wide view mode toggle...
|
||||||
var toggleWideView = createCSSClassToggler('.viewer', 'wide-view-mode', function(action){
|
var toggleWideView = createCSSClassToggler('.viewer', 'wide-view-mode',
|
||||||
if(action == 'on'){
|
function(action){
|
||||||
_ORIGINAL_FIELD_SCALE = getElementScale($('.field'))
|
if(action == 'on'){
|
||||||
setContainerScale(0.1)
|
ORIGINAL_FIELD_SCALE = getElementScale($('.field'))
|
||||||
} else {
|
setContainerScale(0.1)
|
||||||
setContainerScale(_ORIGINAL_FIELD_SCALE)
|
} else {
|
||||||
}
|
setContainerScale(ORIGINAL_FIELD_SCALE)
|
||||||
}, function(){})
|
}
|
||||||
|
}, function(){})
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -741,7 +763,7 @@ function centerOrigin(){
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
// XXX for some odd reason these are not liner... something to do with origin?
|
// XXX these work oddly when page is scaled in maxthon...
|
||||||
// XXX virtually identical, see of can be merged...
|
// XXX virtually identical, see of can be merged...
|
||||||
function moveViewUp(){
|
function moveViewUp(){
|
||||||
var t = parseInt($('.field').css('top'))
|
var t = parseInt($('.field').css('top'))
|
||||||
@ -784,20 +806,40 @@ function centerCurrentImage(){
|
|||||||
|
|
||||||
// basic navigation...
|
// basic navigation...
|
||||||
function firstImage(){
|
function firstImage(){
|
||||||
$('.current.ribbon').children('.image').first().click()
|
return $('.current.ribbon').children('.image').first().click()
|
||||||
}
|
}
|
||||||
function prevImage(){
|
function prevImage(){
|
||||||
$('.current.image').prev('.image').click()
|
return $('.current.image').prev('.image').click()
|
||||||
}
|
}
|
||||||
function nextImage(){
|
function nextImage(){
|
||||||
$('.current.image').next('.image').click()
|
return $('.current.image').next('.image').click()
|
||||||
}
|
}
|
||||||
function lastImage(){
|
function lastImage(){
|
||||||
$('.current.ribbon').children('.image').last().click()
|
return $('.current.ribbon').children('.image').last().click()
|
||||||
}
|
}
|
||||||
|
|
||||||
// XXX add skip N images back and forth handlers...
|
|
||||||
// XXX
|
|
||||||
|
// add skip screen images in direction...
|
||||||
|
function skipScreenImages(direction){
|
||||||
|
// calculate screen width in images...
|
||||||
|
var W = $('.viewer').width()
|
||||||
|
var w = $('.current.image').width()
|
||||||
|
var scale = getElementScale($('.field'))
|
||||||
|
var n = Math.max(Math.floor(W/(w*scale))-1, 0)
|
||||||
|
|
||||||
|
var img = $('.current.image')[direction + 'All']('.image').eq(n)
|
||||||
|
if(img.length > 0){
|
||||||
|
return img.click()
|
||||||
|
} else if(direction == 'next'){
|
||||||
|
return lastImage()
|
||||||
|
} else if(direction == 'prev'){
|
||||||
|
return firstImage()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var nextScreenImages = function(){ return skipScreenImages('next') }
|
||||||
|
var prevScreenImages = function(){ return skipScreenImages('prev') }
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
function focusRibbon(direction){
|
function focusRibbon(direction){
|
||||||
@ -808,20 +850,16 @@ function focusRibbon(direction){
|
|||||||
// NOTE: direction is accounted for to make the up/down shifts
|
// NOTE: direction is accounted for to make the up/down shifts
|
||||||
// symmetrical in the general case...
|
// symmetrical in the general case...
|
||||||
if(next.length == 0 || direction == 'next'){
|
if(next.length == 0 || direction == 'next'){
|
||||||
prev.click()
|
return prev.click()
|
||||||
} else {
|
} else {
|
||||||
next.click()
|
return next.click()
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
$('.current.ribbon')[direction]('.ribbon').children('.image').first().click()
|
return $('.current.ribbon')[direction]('.ribbon').children('.image').first().click()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
function focusAboveRibbon(){
|
var focusAboveRibbon = function(){ return focusRibbon('prev') }
|
||||||
focusRibbon('prev')
|
var focusBelowRibbon = function(){ return focusRibbon('next') }
|
||||||
}
|
|
||||||
function focusBelowRibbon(){
|
|
||||||
focusRibbon('next')
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -855,7 +893,7 @@ function getElementScale(elem){
|
|||||||
|
|
||||||
|
|
||||||
function setElementScale(elem, scale){
|
function setElementScale(elem, scale){
|
||||||
elem.css({
|
return elem.css({
|
||||||
'transform': 'scale('+scale+', '+scale+')',
|
'transform': 'scale('+scale+', '+scale+')',
|
||||||
'-moz-transform': 'scale('+scale+', '+scale+')',
|
'-moz-transform': 'scale('+scale+', '+scale+')',
|
||||||
'-o-transform': 'scale('+scale+', '+scale+')',
|
'-o-transform': 'scale('+scale+', '+scale+')',
|
||||||
@ -867,9 +905,7 @@ function setElementScale(elem, scale){
|
|||||||
|
|
||||||
|
|
||||||
function scaleContainerBy(factor){
|
function scaleContainerBy(factor){
|
||||||
var scale = getElementScale($('.field'))*factor
|
return setContainerScale(getElementScale($('.field'))*factor)
|
||||||
|
|
||||||
setContainerScale(scale)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -1019,19 +1055,11 @@ function shiftImage(direction){
|
|||||||
.detach()
|
.detach()
|
||||||
.prependTo($('.current.ribbon')[direction]('.ribbon'))
|
.prependTo($('.current.ribbon')[direction]('.ribbon'))
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
$('.current.image').click()
|
$('.current.image').click()
|
||||||
}
|
}
|
||||||
|
var shiftImageDown = function(){ return shiftImage('next') }
|
||||||
|
var shiftImageUp = function(){ return shiftImage('prev') }
|
||||||
|
|
||||||
function shiftImageDown(){
|
|
||||||
return shiftImage('next')
|
|
||||||
}
|
|
||||||
function shiftImageUp(){
|
|
||||||
return shiftImage('prev')
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -48,7 +48,8 @@ function setup(){
|
|||||||
setDefaultInitialState()
|
setDefaultInitialState()
|
||||||
|
|
||||||
// XXX
|
// XXX
|
||||||
setBackgroundMode('dark')
|
// this will set the defaults...
|
||||||
|
toggleSingleImageMode('off')
|
||||||
enableTransitions()
|
enableTransitions()
|
||||||
|
|
||||||
// setup event handlers...
|
// setup event handlers...
|
||||||
@ -64,11 +65,6 @@ function setup(){
|
|||||||
// XXX STUB
|
// XXX STUB
|
||||||
loadImages(image_list)
|
loadImages(image_list)
|
||||||
|
|
||||||
// setup the dragging framework...
|
|
||||||
// XXX make this work seamlessly with touchSwipe...
|
|
||||||
// XXX cancel clicks while dragging...
|
|
||||||
$('.field').draggable()
|
|
||||||
|
|
||||||
// set the default position and init...
|
// set the default position and init...
|
||||||
$('.current.image').click()
|
$('.current.image').click()
|
||||||
|
|
||||||
|
|||||||
@ -22,11 +22,21 @@ var keybindings = {
|
|||||||
36: firstImage, // Home
|
36: firstImage, // Home
|
||||||
35: lastImage, // End
|
35: lastImage, // End
|
||||||
|
|
||||||
37: prevImage, // Left
|
//37: prevImage, // Left
|
||||||
|
37: {
|
||||||
|
'default': prevImage, // Right
|
||||||
|
'ctrl': prevScreenImages, // ctrl-Right
|
||||||
|
'alt': prevScreenImages, // alt-Right
|
||||||
|
},
|
||||||
80: 37, // BkSp
|
80: 37, // BkSp
|
||||||
188: 37, // p
|
188: 37, // p
|
||||||
8: 37, // <
|
8: 37, // <
|
||||||
39: nextImage, // Right
|
//39: nextImage, // Right
|
||||||
|
39: {
|
||||||
|
'default': nextImage, // Left
|
||||||
|
'ctrl': nextScreenImages, // ctrl-Left
|
||||||
|
'alt': nextScreenImages, // alt-Left
|
||||||
|
},
|
||||||
32: 39, // Space
|
32: 39, // Space
|
||||||
190: 39, // m
|
190: 39, // m
|
||||||
78: 39, // >
|
78: 39, // >
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user