Better Grrif Player
How do I make an better grrif player?
Weekend project: a better player for http://www.grrif.ch/. Made with lots of love, using jPlayer (http://jplayer.org/), JSONProxy (https://jsonp.afeld.me/) and ticktack.js (https://github.com/meodai/ticktack.js) inspired by by Y7K (http://y7k.ch/en/). What is a better grrif player? How do you make a better grrif player? This script and codes were developed by David A. on 28 November 2022, Monday.
Better Grrif Player - Script Codes HTML Codes
<!DOCTYPE html>
<html >
<head> <meta charset="UTF-8"> <title>Better Grrif Player</title> <meta name="viewport" content="width=device-width,initial-scale=1.0, user-scalable=no">
<link rel="shortcut icon" href="http://www.grrif.ch/favicon.ico" type="image/x-icon" />
<link rel="icon" href="http://www.grrif.ch/favicon.ico" type="image/x-icon" /> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/normalize/5.0.0/normalize.min.css"> <link rel="stylesheet" href="css/style.css">
</head>
<body>
<section class="player js-player is-loading no-autoplay is-paused"> <div class="record-wrap js-current"> <div class="record js-record"> <div class="cover js-cover"></div> </div> </div> <div class="controls"> <div class="controls__buttons"><a class="controls__play js-play" href="#"></a></div> </div> <header class="header"><a class="logo" href="http://www.grrif.ch/" target="_blank"><img class="logo__image" src="http://www.grrif.ch/Htdocs/Images/player-logo.png" alt="griff logo"/></a> <article class="meta"> <h1 class="meta__title"><a class="js-title" href="#" title="open in spotify"></a></h1> <h2 class="meta__artist"><a class="js-artist" href="#" title="open in spotify"></a></h2> </article> </header> <footer class="copy"> <span>fait avec <span class="heart js-textcolor">♥ </span>par <a href="https://twitter.com/meodai" target="_blank">@meodai</a></span></footer> <div id="player"></div>
</section> <script src='http://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min.js'></script>
<script src='https://cdnjs.cloudflare.com/ajax/libs/jplayer/2.9.2/jplayer/jquery.jplayer.min.js'></script>
<script src='http://rawgit.com/meodai/ticktack.js/master/ticktack.js'></script>
<script src='https://s3-us-west-2.amazonaws.com/s.cdpn.io/102565/jquery.shuffleText.min.js'></script> <script src="js/index.js"></script>
</body>
</html>
Better Grrif Player - Script Codes CSS Codes
@import url(https://fonts.googleapis.com/css?family=Roboto:400,100,300);
body, html { font-size: 16px;
}
@media only screen and (max-width: 740px) and (orientation: portrait) { body, html { font-size: 25px; }
}
body, html, h1, h2, h3 { font-family: 'Roboto', sans-serif; font-weight: 100;
}
a { text-decoration: none; text-transform: none;
}
a, a:visited, a:active { color: #000; -webkit-tap-highlight-color: transparent;
}
a:hover { text-decoration: underline; -webkit-tap-highlight-color: transparent;
}
.player { position: absolute; top: 0; right: 0; bottom: 0; left: 0; overflow: hidden; -webkit-perspective: 600px; perspective: 600px; -webkit-transform-style: preserve-3d; transform-style: preserve-3d;
}
@media only screen and (max-width: 740px) and (orientation: portrait) { .player { top: 0.5rem; right: 0.5rem; bottom: 0.5rem; left: 0.5rem; }
}
.copy { opacity: 0.8; position: absolute; left: 1rem; bottom: 0.8rem; font-weight: 400; font-size: calc(0.2rem + 1vw); line-height: 1.4; text-transform: uppercase;
}
@media only screen and (max-width: 740px) and (orientation: portrait) { .copy { font-size: calc(0.3rem + 1vw); }
}
.header { position: absolute; top: 1rem; left: 1rem; right: 1rem; overflow: hidden;
}
.meta__title, .meta__artist { line-height: 1; margin: 0;
}
.meta__title, .meta__title a, .meta__artist, .meta__artist a { text-transform: uppercase;
}
.meta__artist { font-size: calc( .8rem + 1vw ); font-weight: 100;
}
.meta__title { font-size: calc( 1rem + 1vw ); font-weight: 300; margin-bottom: 0.2rem;
}
.logo { display: block; width: 25%; min-width: 200px;
}
.logo__image { width: 100%;
}
@media only screen and (max-width: 740px) and (orientation: portrait) { .logo { width: 100%; max-width: 100%; }
}
.record-wrap, .record, .cover, .controls, .controls__buttons { position: absolute; border-radius: 50%; top: 50%; left: 50%; -webkit-transform: translate(-50%, -50%); transform: translate(-50%, -50%);
}
@media only screen and (max-width: 740px) and (orientation: portrait) { .record { top: 58%; }
}
@media only screen and (max-width: 740px) and (orientation: portrait) { .controls { top: calc(58% + 10px); }
}
.record-wrap { height: 120vh; width: 120vh; -webkit-transition: none; transition: none;
}
.record-wrap--prev { -webkit-transform: translate(-50%, 250%) scale(0.9); transform: translate(-50%, 250%) scale(0.9); -webkit-transition: 3s -webkit-transform cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 3s -webkit-transform cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 3s transform cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 3s transform cubic-bezier(0.6, 0.04, 0.98, 0.335), 3s -webkit-transform cubic-bezier(0.6, 0.04, 0.98, 0.335);
}
.record-wrap--next { -webkit-transform: translate(-50%, -250%) scale(1.1); transform: translate(-50%, -250%) scale(1.1); -webkit-transition-delay: 300ms; transition-delay: 300ms; background: pink; -webkit-transition: 3s -webkit-transform cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 3s -webkit-transform cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 3s transform cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 3s transform cubic-bezier(0.6, 0.04, 0.98, 0.335), 3s -webkit-transform cubic-bezier(0.6, 0.04, 0.98, 0.335);
}
.record { height: 100%; width: 100%; box-shadow: inset 0 0 0 5px rgba(0, 0, 0, 0.05); will-change: transform; background: #999; -webkit-transform: translate3d(-50%, -50%, 0) rotate(0deg); transform: translate3d(-50%, -50%, 0) rotate(0deg); will-change: transform;
}
.cover { height: 43vh; width: 43vh; border: 10px solid rgba(0, 0, 0, 0.05); background: #000; background-clip: padding-box; background-repeat: no-repeat; background-size: cover;
}
.controls { height: 45vh; width: 45vh;
}
.controls__buttons { width: 10vh; height: 10vh; min-width: 100px; min-height: 100px; background: #fff; box-shadow: 0 0 0 5px rgba(0, 0, 0, 0.1); -webkit-transform: translate3d(-50%, -50%, 0) scale(0.2); transform: translate3d(-50%, -50%, 0) scale(0.2); -webkit-transition: 200ms box-shadow 50ms cubic-bezier(0.6, 0.04, 0.98, 0.335), 300ms -webkit-transform cubic-bezier(0.645, 0.015, 0.35, 1.33); transition: 200ms box-shadow 50ms cubic-bezier(0.6, 0.04, 0.98, 0.335), 300ms -webkit-transform cubic-bezier(0.645, 0.015, 0.35, 1.33); transition: 300ms transform cubic-bezier(0.645, 0.015, 0.35, 1.33), 200ms box-shadow 50ms cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 300ms transform cubic-bezier(0.645, 0.015, 0.35, 1.33), 200ms box-shadow 50ms cubic-bezier(0.6, 0.04, 0.98, 0.335), 300ms -webkit-transform cubic-bezier(0.645, 0.015, 0.35, 1.33); cursor: pointer;
}
.no-autoplay .controls__buttons { -webkit-transform: translate3d(-50%, -50%, 0) scale(1); transform: translate3d(-50%, -50%, 0) scale(1);
}
.no-autoplay.is-playing .controls__buttons { -webkit-transform: translate3d(-50%, -50%, 0) scale(0.2); transform: translate3d(-50%, -50%, 0) scale(0.2);
}
.controls__play { display: block; position: absolute; top: 0; right: 0; bottom: 0; left: 0; opacity: 0; -webkit-transform: scale(0.5); transform: scale(0.5);
}
.controls__play:after, .controls__play:before { position: absolute; top: 50%; display: block; content: ""; background: #000; width: 10%; height: 45%; -webkit-transform: translate3d(-50%, -50%, 0); transform: translate3d(-50%, -50%, 0); -webkit-transition: 300ms height ease-in, 300ms -webkit-transform ease-in; transition: 300ms height ease-in, 300ms -webkit-transform ease-in; transition: 300ms transform ease-in, 300ms height ease-in; transition: 300ms transform ease-in, 300ms height ease-in, 300ms -webkit-transform ease-in;
}
.controls__play:before { left: calc(50% - 11px);
}
.controls__play:after { left: calc(50% + 11px);
}
.controls:hover .controls__buttons, .is-paused .controls .controls__buttons, .no-autoplay .controls .controls__buttons { -webkit-transform: translate3d(-50%, -50%, 0) scale(1); transform: translate3d(-50%, -50%, 0) scale(1); box-shadow: 0 0 0 10px rgba(0, 0, 0, 0.15);
}
.controls:hover .controls__play, .is-paused .controls .controls__play, .no-autoplay .controls .controls__play { opacity: 1; -webkit-transform: scale(1); transform: scale(1); -webkit-transition: 150ms opacity 200ms cubic-bezier(0.6, 0.04, 0.98, 0.335), 300ms -webkit-transform 150ms cubic-bezier(0.645, 0.015, 0.35, 1.5); transition: 150ms opacity 200ms cubic-bezier(0.6, 0.04, 0.98, 0.335), 300ms -webkit-transform 150ms cubic-bezier(0.645, 0.015, 0.35, 1.5); transition: 300ms transform 150ms cubic-bezier(0.645, 0.015, 0.35, 1.5), 150ms opacity 200ms cubic-bezier(0.6, 0.04, 0.98, 0.335); transition: 300ms transform 150ms cubic-bezier(0.645, 0.015, 0.35, 1.5), 150ms opacity 200ms cubic-bezier(0.6, 0.04, 0.98, 0.335), 300ms -webkit-transform 150ms cubic-bezier(0.645, 0.015, 0.35, 1.5);
}
.is-paused .controls .controls__buttons { -webkit-transform: translate3d(-50%, -50%, 0) scale(1) rotate(-90deg); transform: translate3d(-50%, -50%, 0) scale(1) rotate(-90deg);
}
.is-paused .controls .controls__play { -webkit-transform: scale(0.6); transform: scale(0.6);
}
.is-paused .controls .controls__play:after, .is-paused .controls .controls__play:before { height: 39.5%;
}
.is-paused .controls .controls__play:after { -webkit-transform: translate3d(-50%, -50%, 0) rotate(45deg); transform: translate3d(-50%, -50%, 0) rotate(45deg);
}
.is-paused .controls .controls__play:before { -webkit-transform: translate3d(-50%, -50%, 0) rotate(-45deg); transform: translate3d(-50%, -50%, 0) rotate(-45deg);
}
@media only screen and (max-width: 740px) and (orientation: portrait) { .heart { color: #fff !important; }
}
.notclickable { pointer-events: none;
}
@-webkit-keyframes pulse { 0% { -webkit-transform: translate3d(-50%, -50%, 0); transform: translate3d(-50%, -50%, 0); } 50% { -webkit-transform: translate3d(-50%, -50%, 50px); transform: translate3d(-50%, -50%, 50px); } 100% { -webkit-transform: translate3d(-50%, -50%, 0); transform: translate3d(-50%, -50%, 0); }
}
@keyframes pulse { 0% { -webkit-transform: translate3d(-50%, -50%, 0); transform: translate3d(-50%, -50%, 0); } 50% { -webkit-transform: translate3d(-50%, -50%, 50px); transform: translate3d(-50%, -50%, 50px); } 100% { -webkit-transform: translate3d(-50%, -50%, 0); transform: translate3d(-50%, -50%, 0); }
}
.warning { position: fixed; top: 50%; right: 1rem; left: 1rem; -webkit-transform: translate(0, -50%); transform: translate(0, -50%); box-sizeing: border-box; padding: 2rem 4rem; background: fuchsia; z-index: 1000; text-align: center;
}
@media only screen and (max-width: 740px) and (orientation: portrait) { .warning { font-size: .4rem; padding: 1rem 2rem; }
}
Better Grrif Player - Script Codes JS Codes
// MIT License
/** * Todo: * * - Link to streams * * - track history represented by a vynil * stack behind the currently playing record * * - animate track change */
var GriffPlayer, gp, $d, AUTOPLAY, FindTrack;
// test for autoplay
AUTOPLAY = false;
(function() { var mp3 = 'data:audio/mpeg;base64,/+MYxAAAAANIAUAAAASEEB/jwOFM/0MM/90b/+RhST//w4NFwOjf///PZu////9lns5GFDv//l9GlUIEEIAAAgIg8Ir/JGq3/+MYxDsLIj5QMYcoAP0dv9HIjUcH//yYSg+CIbkGP//8w0bLVjUP///3Z0x5QCAv/yLjwtGKTEFNRTMuOTeqqqqqqqqqqqqq/+MYxEkNmdJkUYc4AKqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqq'; try { var audio = new Audio(); var src = mp3; audio.autoplay = true; $(audio).on('play', function() { AUTOPLAY = true; }); audio.src = src; } catch(e) { console.log('[AUTOPLAY-ERROR]', e); }
})();
// find track on services
FindTrack = function($title, $artist, $cover){ this.$title = $title; this.$artist = $artist; this.$cover = $cover;
};
FindTrack.prototype = { spotify: function(query){ var self = this; $.ajax({ url: 'https://api.spotify.com/v1/search', data: { q: query, type: 'track' }, success: function (response) { var items = response.tracks.items; var obj = {}; if ( items.length ){ var item = items[0]; obj.uri = item.uri; obj.artisturi = item.artists[0].uri; self.$title.attr('href', obj.uri).removeClass('notclickable'); self.$artist.attr('href', obj.artisturi).removeClass('notclickable'); if(item.album && item.album.images) { this.$cover.css('background-image', 'url(' + item.album.images[0].url + ')'); } } else { self.$title.attr('href', '#').addClass('notclickable'); self.$artist.attr('href', '#').addClass('notclickable'); } } }); }
};
//actual radio
GriffPlayer = function (options) { var self = this; this.file = options.file || ""; this.fileFormat = options.fileFormat || "mp3"; this.player = options.player; this.$player = $(this.player); this.track = {}; this.wrap = options.wrap; this.$wrap = $(this.wrap); this.cover = options.cover; this.$cover = $(this.cover); this.artist = options.artist; this.$artist = $(this.artist); this.title = options.title; this.$title = $(this.title); this.playbutton = options.playbutton; this.metaInterval = options.metaInterval || 1000000; this.findTrack = new FindTrack(this.$title, this.$artist, this.$cover); this.playerReady = false; this.jPlayerTrack = { title: 'griff', mp3: self.file }; this.$player.jPlayer({ ready: function(event){ self.playerReady = true; self.$player.jPlayer("setMedia", self.jPlayerTrack); if( AUTOPLAY ){ self.play(); $('.js-player').addClass('has-autoplay').removeClass('no-autoplay'); } self.$wrap.removeClass('is-loading'); }, error: function(e){ console.log(e.jPlayer.error); if(self.playerReady && e.jPlayer.error.type === $.jPlayer.error.URL_NOT_SET) { self.$player.jPlayer("setMedia", self.jPlayerTrack).jPlayer("play"); } }, supplied: self.fileFormat, preload: "none", wmode: "window" }); this.getTrackInfo(); this.timer = setInterval(function(){ self.getTrackInfo(); },this.metaInterval); this.bindControls();
};
GriffPlayer.prototype = { getTrackInfo: function(){ var yql_url = 'https://query.yahooapis.com/v1/public/yql'; var url = 'https://www.grrif.ch/live/covers.json'; var self = this; $.ajax({ 'url': yql_url, 'data': { 'q': 'SELECT * FROM json WHERE url="'+url+(new Date().getTime())+'"', 'format': 'json', 'jsonCompat': 'new', }, 'dataType': 'jsonp', 'success': function(data) { var history = data.query.results.json.json; var track = history[history.length - 1]; console.log(track) self.trackChanged = (self.track.title != track.Title) || (self.track.artist != track.Artist); if ( self.trackChanged ) { self.track.title = track.Title || ""; self.track.album = track.Album || ""; self.track.artist = track.Artist || ""; self.track.cover = track.URLCover || ""; self.trackChange(); } }, }); }, trackChange: function(){ this.updateTrackInfo(); this.findTrack.spotify(this.track.title + ' ' + this.track.artist); }, updateTrackInfo: function(){ var self = this; this.$cover.css("background-image", "url('" + this.track.cover + "')"); self.$title.shuffleText(self.track.title, {complete: function(){ self.$artist.shuffleText(self.track.artist); }}); }, getPlayStatus: function(){ return this.isPlaying; }, pause: function(){ this.$player.jPlayer('pause'); this.isPlaying = false; this.$wrap.removeClass('is-playing').addClass('is-paused'); this.$player.jPlayer("clearMedia"); }, play: function(){ var self = this; this.isPlaying = true; this.$wrap.addClass('is-playing').removeClass('is-paused'); this.$player.jPlayer("setMedia", self.jPlayerTrack ).jPlayer("play"); }, bindControls: function(){ var self = this; self.$wrap.on('click', self.playbutton, function(e){ e.preventDefault(); if ( self.isPlaying ) { self.pause(); } else { self.play(); } }); }
}
gp = new GriffPlayer({ file: 'http://grrif.ice.infomaniak.ch/grrif-high.mp3', player: '#player', cover: '.js-cover', artist: '.js-artist', title: '.js-title', metaInterval: 10000, playbutton: '.js-play', wrap: '.js-player'
});
// record color
var $record = $(".js-record"), $text = $(".js-textcolor");
timeToColor = function( secondProgress,add ){ add = add || 0; return 'hsl(' + Math.floor( (secondProgress * 360 ) + add) % 360 + ',' + 95 +'%,' + 65 + '%)';
};
var rpm = 0;
var maxRpm = 1.25;
var minRpm = 0.075;
var rpmStep = 0.003;
var rotation = 0;
ticktack.on('tick', function(o){ var color, color2, progress; color = timeToColor( o.getMinute().progress ); color2 = timeToColor( o.getMinute().progress, 18 ); progress = o.getMinute().progress; if( !gp.getPlayStatus() ) { rpm += (minRpm - rpm) * rpmStep; } else if ( gp.getPlayStatus() ) { rpm += (maxRpm - rpm) * rpmStep; } rotation += Math.ceil(rpm * 1000) / 1000; $record.css({ "background-color": color, "background-image": "linear-gradient(180deg," + color + ", " + color2 + ")", "transform": "translate(-50%,-50%) rotate(" + rotation % 360 + "deg)" }); $text.css("color", color);
});
Developer | David A. |
Username | meodai |
Uploaded | November 28, 2022 |
Rating | 3 |
Size | 8,512 Kb |
Views | 10,120 |
Find the perfect freelance services for your business! Fiverr's mission is to change how the world works together. Fiverr connects businesses with freelancers offering digital services in 500+ categories. Find Developer!
Name | Size |
Social color-namer | 6,112 Kb |
All the 16k color names from the color-name-list API | 6,006 Kb |
DOM explosions | 8,919 Kb |
Color palette distribution for different color spaces | 10,909 Kb |
Textmask over random clouds animation | 3,929 Kb |
We Simplify animation | 48,169 Kb |
Cubehelix ticktack.js | 5,643 Kb |
Pseudo 3d css clouds | 5,199 Kb |
Color Watch | 7,929 Kb |
Pijama ninja falling | 5,513 Kb |
Jasper is the AI Content Generator that helps you and your team break through creative blocks to create amazing, original content 10X faster. Discover all the ways the Jasper AI Content Platform can help streamline your creative workflows. Start For Free!
Name | Username | Size |
RAQuote | Naderk007 | 4,412 Kb |
Multi-step GSAP animation | Acacheung | 2,668 Kb |
Cloudy Spiral CSS animation | Hakimel | 6,587 Kb |
Project Euler Problem 17 | Bfillmer | 2,739 Kb |
Airbnb Homepage | SindhujaD | 2,480 Kb |
Owl Carousel - jumpTo | OwlFonk | 2,553 Kb |
Canvas Orbital Trails v2 | Jackrugile | 3,421 Kb |
Animated Slide Hamburger Mobile Menu | BJack | 2,247 Kb |
Shop Talk logo made in CSS | Hugo | 19,368 Kb |
3D-box | Parthviroja | 2,346 Kb |
Surf anonymously, prevent hackers from acquiring your IP address, send anonymous email, and encrypt your Internet connection. High speed, ultra secure, and easy to use. Instant setup. Hide Your IP Now!