Cheerify.it started with a simple idea: What would a website look like if you could decorate it with Christmas lights and sync it music. We've been wanting to play with using browser bookmarks to manipulate the contents of a website, so we extended the original idea to be able to "Cheerify" any website.
Building The Prototype
We had seen bookmarks manipulate elements on screen to music before. The tricky part was going to be building a framework that allowed us to easily sync animations to music.
First, I want to give a huge shout out to Moovweb for their Harlem Shake bookmarklet. Not only did it serve as a source of inspiration but it gave me a great place to start building out my framework. The original Harlem Shake bookmarklet works by inserting an HTML5 audio element into the page and using a setTimeout to wait 15 seconds before making everything on the screen go crazy. They've since updated their code on GitHub to a more reliable method, but I'll get to that in a second.
So using the Harlem Shake code as a starting point, we built a framework for adding effects to a timeline. Our framework uses a
setInterval() to check the HTML5 audio's currentTime property every 10th of a second. We then iterate through an array of effects to trigger as we approach each timestamp. The array is made up of smaller arrays that include a timestamp and a function to call. Using anonymous functions within our effects array kept our code readable and made it easy for other developers to help orchestrate.
It's important to note I could have also used the timeupdate event of the audio element instead of set interval; however, setInterval allowed us to control our proprietary frame rate.
As browsers become smarter, we can do cooler things with them. In this case, we used Cheerify.it as an excuse to play with some of the more cutting edge features of modern browsers like CSS3 animations and HTML5 audio.
Html5 Audio has come a long way. For this experience, we didn't worry about creating fallbacks for older browsers like we normally would. We've used MediaElements.js on several websites in the past with great success. This time around we kept it simple using only two source files, MP3 and OGG. We then took advantage of the audio element's methods and properties to keep the animations in sync with the music as well as create a little music player that allows users to play/pause and mute the whole experience.
The real fun was coming up with CSS3 animations. Every animation was made using pure CSS3, even the dancing snowman. Only thing we could have done better with the snowman is used the animation-delay property instead of
- How big they were
- Where they were located
- Whether they were hidden or not
- Whether they were within the viewport or not
Creating An Easier Way To Share The Experience
Our solve for this was to allow people to Cheerify their site by typing a URL into an input box and then pressing "Cheerify It".
To accomplish this we used PHP to test if we had a site to cheerify. After grabbing and cleaning up the URL, we used CURL to get the contents of the web page. This is where it got a bit mucky. We assumed that the destination site had well-formed HTML and attempted to insert our cheerify script before the closing body tag. Believe it or not, there are sites out there that have more than one body tag and others with no body tag at all.
So, now we had a URL that looked something like http://www.cheerify.it/?site=https://www.ampagency.com with all of the contents of that page grabbed, manipulated and ready to output to the browser. We then echoed out our manipulated HTML and hoped all was well. It wasn't, yet.
Using this method, we made several assumptions about how the HTML was formatted. We also had broken paths to all assets using relative URLs. To fix this, we did a very primitive
alert() function to silently output to the console to avoid any other interruptions.
One of my favorite development automation tools is Grunt. It played a huge part in automating the staging, minification, auto-prefixing and de-linting of the code during the development process. I've included a modified version of the Gruntfile.js we used in the Cheerify.it GitHub repo.
The Cheerify site was a lot of fun to work on and and the team did a great job turning the whole project around in a short time frame. Check out the Cheerify.it Source Code on Github and leave a comment below with your thoughts.
Finally, don't forget to Cheerify this page.