reworked toolbar dragging (still disabled)...

Signed-off-by: Alex A. Naanou <alex.nanou@gmail.com>
This commit is contained in:
Alex A. Naanou 2023-08-17 17:16:49 +03:00
parent 8394c8e05f
commit c4783101a0

View File

@ -152,6 +152,113 @@ var getTouch = function(evt, id){
return evt.targetTouches[k] } } } } return evt.targetTouches[k] } } } }
// XXX need to check if element already set as movable...
var moveable = function(elem, options={}){
if(elem.dataset.movable){
throw new Error('element already movable.') }
elem.dataset.movable = true
var {
cls,
handle,
bounds,
start = function(elem, data){
bounds
?? (data.bounds = bounds)
return data },
beforeMove,
move = function(elem, data){
elem.style.left = data.x + 'px'
elem.style.top = data.y + 'px'
},
end,
} = options
handle = typeof(handle) == 'string' ?
elem.querySelector(handle)
: handle instanceof Element ?
handle
: elem
var data
var handleMoveStart = function(evt){
evt.preventDefault()
evt.stopPropagation()
if(!data){
cls
&& elem.classList.add(cls)
var x = evt.clientX
?? evt.targetTouches[0].clientX
var y = evt.clientY
?? evt.targetTouches[0].clientY
data = {
bounds: false,
offset: {
x: x - elem.offsetLeft,
y: y - elem.offsetTop,
},
touch: evt.targetTouches ?
evt.targetTouches[0].identifier
: undefined,
}
if(typeof(start) == 'function'){
var res = start(elem, data)
data = res != null ?
res
: data } } }
var handleMove = function(evt){
if(data){
var src = data.touch != null ?
getTouch(evt, data.touch)
: evt
if(!src){
return }
evt.preventDefault()
evt.stopPropagation()
var x = src.clientX
var y = src.clientY
data.x =
data.bounds != null ?
Math.min(data.bounds.right,
Math.max(data.bounds.left,
x - data.offset.x))
: x - data.offset.x
data.y =
data.bounds != null ?
Math.min(data.bounds.bottom,
Math.max(data.bounds.top,
y - data.offset.y))
: y - data.offset.y
// NOTE: we only allow a single requestAnimationFrame(..)
// to run per frame...
if(!data.animate){
data.animate = requestAnimationFrame(function(){
if(!data){
return }
move(elem, data)
delete data.animate }) } } }
var handleMoveEnd = function(evt){
if(data){
if(evt.targetTouches
&& (evt.targetTouches.length == 0
|| getTouch(evt, data.touch))){
return }
evt.preventDefault()
evt.stopPropagation()
cls
&& elem.classList.remove(cls)
end
&& end(elem, data)
data = false } }
// XXX can we reuse these???
// ...i.e. keep the data in the element???
handle.addEventListener('mousedown', handleMoveStart)
handle.addEventListener('touchstart', handleMoveStart)
document.addEventListener('mousemove', handleMove)
document.addEventListener('touchmove', handleMove)
document.addEventListener('touchend', handleMoveEnd)
document.addEventListener('mouseup', handleMoveEnd) }
//--------------------------------------------------------------------- //---------------------------------------------------------------------
// XXX add shift+arrow to select... // XXX add shift+arrow to select...
@ -947,87 +1054,24 @@ var Gallery = {
toolbar.addEventListener('mouseover', toolbarAutoHideCancel) toolbar.addEventListener('mouseover', toolbarAutoHideCancel)
toolbar.addEventListener('touchstart', toolbarAutoHideCancel) toolbar.addEventListener('touchstart', toolbarAutoHideCancel)
/* XXX problems: /* XXX needs more tweaking...
// - too many interactions: autohide, placement, ...
// - not sure if we need this...
// toolbar: move... // toolbar: move...
var handleToolbarMoveStart = function(evt){ // XXX to drag anywhere on the elem we need to prevent
evt.preventDefault()
evt.stopPropagation()
if(!toolbar_moving){
toolbar.classList.add('moving')
var x = evt.clientX
?? evt.targetTouches[0].clientX
var y = evt.clientY
?? evt.targetTouches[0].clientY
toolbar_moving = {
bounds: {
x: that.dom.offsetWidth - toolbar.offsetWidth - 20,
// XXX this gets off on high magnifications...
y: that.dom.offsetHeight - toolbar.offsetHeight - 20,
},
offset: {
x: x - toolbar.offsetLeft,
y: y - toolbar.offsetTop,
},
touch: evt.targetTouches ?
evt.targetTouches[0].identifier
: undefined,
} } }
var handleToolbarMoveEnd = function(evt){
if(toolbar_moving){
if(evt.targetTouches
&& (evt.targetTouches.length == 0
|| getTouch(evt, toolbar_moving.touch))){
return }
evt.preventDefault()
evt.stopPropagation()
toolbar.classList.remove('moving')
toolbar_moving = false } }
// XXX ignore non-local touches...
// XXX disable button clicking while moving...
var handleToolbarMove = function(evt){
if(toolbar_moving){
var src = toolbar_moving.touch != null ?
getTouch(evt, toolbar_moving.touch)
: evt
if(!src){
return }
evt.preventDefault()
evt.stopPropagation()
var x = src.clientX
var y = src.clientY
toolbar_moving.x =
toolbar_moving.bounds?.x != null ?
Math.min(toolbar_moving.bounds.x,
Math.max(0,
x - toolbar_moving.offset.x))
: x - toolbar_moving.offset.x
toolbar_moving.y =
toolbar_moving.bounds?.y != null ?
Math.min(toolbar_moving.bounds.y,
Math.max(0,
y - toolbar_moving.offset.y))
: y - toolbar_moving.offset.y
// NOTE: we only allow a single requestAnimationFrame(..)
// to run per frame...
if(!toolbar_moving.animate){
toolbar_moving.animate = requestAnimationFrame(function(){
if(!toolbar_moving){
return }
toolbar.style.setProperty('--move-x', toolbar_moving.x + 'px')
toolbar.style.setProperty('--move-y', toolbar_moving.y + 'px')
delete toolbar_moving.animate }) } } }
// XXX to drag anywhere on the toolbar we need to prevent
// clicks while dragging... // clicks while dragging...
toolbar.querySelector('.drag-handle') moveable(toolbar, {
.addEventListener('mousedown', handleToolbarMoveStart) cls: 'moving',
toolbar.querySelector('.drag-handle') handle: '.drag-handle',
.addEventListener('touchstart', handleToolbarMoveStart) // set bounds...
this.dom.addEventListener('mousemove', handleToolbarMove) start: function(elem, data){
this.dom.addEventListener('touchmove', handleToolbarMove) data.bounds = {
document.addEventListener('touchend', handleToolbarMoveEnd) top: 0,
document.addEventListener('mouseup', handleToolbarMoveEnd) left: 0,
right: that.dom.offsetWidth - elem.offsetWidth - 20,
bottom: that.dom.offsetHeight - elem.offsetHeight - 20,
} },
move: function(elem, data){
elem.style.setProperty('--move-x', data.x + 'px')
elem.style.setProperty('--move-y', data.y + 'px') }, })
//*/ //*/
// image clicks... // image clicks...