JSFiddle - React, Tailwind, and code Playground
by mackry
HTML
<ul>
<li class="challenge">Eat More Broccoli 1</li>
<li class="challenge">Eat More Broccoli 2</li>
<li class="challenge">Eat More Broccoli 3</li>
<li class="challenge">Eat More Broccoli 4</li>
</ul>
<div id="modal">
<div class="dialog">
<div>
<span>1 of 1</span>
<a href="#previous" title="Previous Challenge">⇽</a>
<a href="#next" title="Next Challenge">⇾</a>
<a href="#close" title="Close">×</a>
</div>
<h3>Eat More Broccoli 1</h3>
</div>
<div class="dialog">
<div>
<span>1 of 1</span>
<a href="#previous" title="Previous Challenge">⇽</a>
<a href="#next" title="Next Challenge">⇾</a>
<a href="#close" title="Close">×</a>
</div>
<h3>Eat More Broccoli 2</h3>
</div>
<div class="dialog">
<div>
<span>1 of 1</span>
<a href="#previous" title="Previous Challenge">⇽</a>
<a href="#next" title="Next Challenge">⇾</a>
<a href="#close" title="Close">×</a>
</div>
<h3>Eat More Broccoli 3</h3>
</div>
<div class="dialog">
<div>
<span>1 of 1</span>
<a href="#previous" title="Previous Challenge">⇽</a>
<a href="#next" title="Next Challenge">⇾</a>
<a href="#close" title="Close">×</a>
</div>
<h3>Eat More Broccoli 4</h3>
</div>
</div>
CSS
body {
background: #f7f7f7;
font-family: 'Helvetica Neue', Arial, sans-serif;
}
ul {
margin: 50px;
}
.challenge {
background: #fff;
border: 1px solid #ccc;
color: #555;
display: inline-block;
margin-right: 14px;
padding: 15px;
height: 100px;
width: 150px;
box-shadow: 0 1px 2px rgba(0, 0, 0, .07);
}
.challenge:hover {
border: 1px solid #999;
cursor: pointer;
}
#modal {
background: transparent;
display: block;
height: 0;
position: fixed;
top: 0;
right: 0;
bottom: 0;
left: 0;
overflow-x: auto;
overflow-y: scroll;
z-index: 0;
-webkit-perspective: 1000;
}
#modal.show {
height: auto;
z-index: 9999;
-moz-transform: translateZ(0);
-webkit-transform: translateZ(0);
transform: translateZ(0);
-moz-transition: background 500ms ease-out 200ms;
-webkit-transition: background 500ms ease-out 200ms;
transition: background 500ms ease-out 200ms;
}
#modal .dialog {
background: white;
border: solid 1px #999;
opacity: 1;
padding: 15px;
position: absolute;
top: 0;
left: 0;
visibility: hidden;
height: 100px;
width: 150px;
-moz-box-shadow: 0px 20px 60px rgba(0,0,0,.2);
-webkit-box-shadow: 0px 20px 60px rgba(0,0,0,.2);
box-shadow: 0px 20px 60px rgba(0,0,0,.2);
}
#modal.show .active {
visibility: visible;
height: 300px;
width: 350px;
-moz-transform: translateZ(0);
-webkit-transform: translateZ(0);
transform: translateZ(0);
-moz-transition: all 200ms ease-out;
-webkit-transition: all 200ms ease-out;
transition: all 200ms ease-out;
}
#modal .dialog div {
color: #999;
font-size: 13px;
line-height: 0;
position: absolute;
right: 13px;
top: 16px;
}
#modal h3 {
background: #fff;
}
.dialog div a {
color: #0084ff;
font-size: 18px;
text-decoration: none;
}
.dialog div span {
margin: 0 5px; ...
JavaScript
$(document).ready(function() {
var modal = $('#modal'),
dialogs = $('#modal .dialog'),
close = dialogs.find('a[href="#close"]'),
challenges = $('.challenge'),
selectedChallenge = null,
activeDialog = null;
challenges.each(function() {
var $this = $(this);
$this.click(function() {
selectedChallenge = $this;
activeDialog = dialogs.eq($this.index());
positionModal();
setTimeout(function() {
modal.addClass('show');
activeDialog.addClass('active');
}, 1);
});
});
close.click(closeModal);
function closeModal() {
modal.removeClass('show');
activeDialog.removeClass('active');
}
function positionModal() {
var xPos = selectedChallenge.offset().left,
yPos = selectedChallenge.offset().top;
activeDialog.css({
left: xPos,
top: yPos
});
}
// keyboard left right arrow keys
$(document).keydown(function(e) {
if (e.keyCode == 37) {
togglePrevChallenge();
return false;
} else if (e.keyCode == 39) {
toggleNextChallenge();
return false;
}
});
$('a[href="#previous"]').click(togglePrevChallenge);
$('a[href="#next"]').click(toggleNextChallenge);
function togglePrevChallenge() {
var prevChallenge = selectedChallenge.prev();
if (prevChallenge.is('li')) {
selectedChallenge = prevChallenge;
} else {
selectedChallenge = challenges.last();
}
activeDialog.removeClass('active');
activeDialog = dialogs.eq(selectedChallenge.index());
positionModal();
setTimeout(function() {
activeDialog.addClass('active');
}, 1);
}
function toggleNextChallenge() {
...