jaures24 jaures24 - 6 months ago 29
jQuery Question

Catching specific event on carousel

I'm trying to make carousel and catch some specific user's action on slide moves on custom events.


  • slide restore

  • during the touch moves



I tried using slick, but slick's custom events fires not as I expected.
Here is code I tried.



<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0, user-scalable=no, target-densitydpi=medium-dpi">
<link rel="stylesheet" type="text/css" href="//cdn.jsdelivr.net/jquery.slick/1.5.9/slick.css"/>
<link rel="stylesheet" type="text/css" href="https://rawgit.com/kenwheeler/slick/master/slick/slick-theme.css"/>
<style type="text/css">
.slider {
width: auto;
margin: 30px 50px 50px; }

.slick-slide {
background: #3a8999;
color: white;
padding: 40px 0;
font-size: 30px;
font-family: "Arial", "Helvetica";
text-align: center; }

.slick-prev:before, .slick-next:before {
color: black; }

.slick-dots {
bottom: -30px; }

.slick-slide:nth-child(odd) {
background: #e84a69; }

</style>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script type="text/javascript" src="//cdn.jsdelivr.net/jquery.slick/1.5.9/slick.min.js"></script>
</head>
<body>

<section class="slider">
<div>slide1</div>
<div>slide2</div>
<div>slide3</div>
<div>slide4</div>
<div>slide5</div>
<div>slide6</div>
</section>

<div id="log" style="height:300px;overflow-y:auto"></div>

<script>
$(".slider").slick({
autoplay: false,
dots: true
}).on("afterChange beforeChange edge init reInit setPosition swipe breakpoint", handler);

function handler(event, slick, direction) {
var $log = $("#log");
event.type == "beforeChange" && $log.html("");

$log.html(event.type +"<br>"+ $log.html());
}
</script>
</body>
</html>





There is no restore events

When slide isn't reach touchThreshold condition, slide is going back to the last position, but the events are fired in below order.

beforeChange -> afterChange -> setPosition


whereas for normal slide moves, events are fired like :

beforeChange -> swipe -> afterChange -> setPosition


The only difference is 'swipe'. To distinguish from normal move and restoring move,
I need to figure out from that difference which is something tedious work.

There's no way to catch user's touch moves

When user moves slide during the touch, there's no custom events firing
at that point.
The events fires right after when touch is up.

My question is what are the jQuery based carousel plugin to recommend which meet that conditions above?

Answer

One of the alternatives is egjs flicking component based on jQuery. You can check out basic demo at http://naver.github.io/egjs/demo/flicking/

Here is the sample working demo code:

<!doctype html>
<html lang="en">
<head>
	<meta charset="utf-8">
	<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0, user-scalable=no, target-densitydpi=medium-dpi">
	<style type="text/css">
		.slider{height:130px;background-color:grey}
		.eg-flick-panel {font-size:2em;text-align:center}
	</style>
	<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
	<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/egjs/1.1.0/pkgd/flicking.pkgd.min.js"></script>
</head>
<body>

<section class="slider">
	<div id="item1" style="background-color:#CC66CC">
		<p>slide1</p>
	</div>
	<div id="item2" style="background-color:#66cccc">
		<p>slide2</p>
	</div>
	<div id="item3" style="background-color:#ffc000">
		<p>slide3</p>
	</div>
	<div id="item3" style="background-color:#f5871f">
		<p>slide4</p>
	</div>
	<div id="item3" style="background-color:#66ff66">
		<p>slide5</p>
	</div>
	<div id="item3" style="background-color:#8a6d3b">
		<p>slide6</p>
	</div>
</section>

<div id="log" style="height:300px;overflow-y:auto"></div>

<script>
	new eg.Flicking(".slider", {
		duration: 300,
		circular: true
	}).on({
		beforeFlickStart: handler,
		flick: handler,
		flickEnd: handler,
		beforeRestore: handler,
		restore: handler
	});

	function handler(event) {
		var $log = $("#log"), direction = { "2": "&larr;", "4": "&rarr;" };

		/^before/.test(event.eventType) && $log.html("");
		$log.html(event.eventType +": "+ direction[event.direction] +"<br>"+ $log.html());
	}
</script>
</body>
</html>

Restore event

As you noticed running the above code, when slide isn't moved passing threshold the restore events fired in this order:

beforeRestore -> flick ... flick -> restore

Touch moves

And during the touch panel moves, multiple flick events are fired as many as your moves and also you can determine direction of the moves with the event parameter value.

The events are fired in this order:

(during the touch down moves) flick ... flick -> (when touch is up) beforeFlickStart -> flick ... flick -> flickEnd

Hope this answers to your questions.