translate3d with a transition not being accelerated (being blocked by JS) - css-transitions

I am trying to animate a (100% width) div offscreen by moving it using translate3d(100%,0,0) with a 1s transition. I believe the animation should be fully offloaded to the GPU and not affected by JS, but it is freezing as I do JS computations.
Note that it doesn't freeze when I use a pixel value, e.g. translate3d(500px,0,0)
See this in effect: http://jsfiddle.net/khufzte9/
This is the code I'm using:
CSS:
html, body {
margin: 0;
padding: 0;
}
#blue {
background-color: blue;
width: 100%;
height: 100%;
-webkit-transition: all 1s;
}
HTML:
<div id='blue'></div>
JS:
document.body.addEventListener('click', function () {
var blue = document.querySelector('#blue');
blue.style.transform = 'translate3d(100%,0,0)';
// Do some blocking work after the animation starts
setTimeout(function () {
for (var i = 0; i < 1000000000; i++) {
var j = 5/3;
}
}, 300);
});
Any thoughts or advice would be much appreciated!

Related

How to reveal an element (ex. button) after hovering on a certain element of the site?

The problem is I want to make the gray button hidden and get revealed after hovering on a card with hotel pictures.
Currently, I have this site as an example: https://cofffelo.github.io/HotelShop/#
I tried to hide the buttons at their default state by display:none and make it display:block by executing :hover pseudo-index, but because it was hidden from the start, there was nothing to hover, and because I'm kind of a newbie, I ran out of ideas.
The code I tried to add:
.cardbutton{
display: none;
}
.cardbutton:hover{
transform: translateY(30px);
display: block;
background-color: #333;
}
You can use a transition delay
.cardbutton:after {
opacity: 0;
content: "";
}
.cardbutton:hover:after {
opacity: 1;
transition: opacity 0s linear 1.5s;
content: "content text here";
}

JS switch onlick between two colors w/ if else

I'm working on my portfolio and need to switch between to stylings states of an element. Currently, I'm trying to make it work on the following example. In this particular case, my goal is to click the button and switch between green and red background with every click. But something won't work. I can switch from green to red, but not from red to green. What am I missing?
<button id="button">Toggle</button>
<div class="test" id="test"></div>
.test {
width: 100px;
height: 100px;
background: green;
margin-top: 20px;
}
var btn = document.getElementById("button");
var test = document.getElementById("test");
btn.onclick = function() {
if (test.style.background = "green") {test.style.background = "red";} else {test.style.background = "green";}};
Codepen Demo https://codepen.io/yanniksturm/pen/rNVmqJe
Thanks a lot!
In if condition there should be double (==) equal sign and also check by backgroundColor instead of background because of some browsers has more properties with background like background: green none repeat scroll 0% 0%; so condition will not execute.
I recommend use backgroundColor instead of background.
var btn = document.getElementById("button");
var test = document.getElementById("test");
btn.onclick = function() {
if (test.style.backgroundColor == "red") {
test.style.backgroundColor = "green";}
else {
test.style.backgroundColor = "red";
}
}
.test {
width: 100px;
height: 100px;
background: green;
margin-top: 20px;
}
<button id="button">Toggle</button>
<div class="test" id="test"></div>

google visualization chart, size in percentage

How do you set the size of a google chart in percentage :
I have this in the html:
<div id="chart_div" width="90%" height="20%"></div>
and no width nor height in the options in the js.
But the chart size doesn't adapt to the viewport.
First, use styles to set your dimensions, not attributes:
<div id="chart_div" style="width: 90%; height: 20%;"></div>
The chart will draw to the size of the div by default, but the charts are not responsive. You have to hook a "resize" event handler to the window (or other element if you are resizing within a window) that redraws the chart:
function resizeChart () {
chart.draw(data, options);
}
if (document.addEventListener) {
window.addEventListener('resize', resizeChart);
}
else if (document.attachEvent) {
window.attachEvent('onresize', resizeChart);
}
else {
window.resize = resizeChart;
}
By multiplying with appropriate factor to $(window).width() or $(window).height() in the chart options
var options = {
width: $(window).width(),
height: $(window).height()*0.75
};
Google recommend that you style, like the answer above, with correct CSS and this makes a less-glitchy Chart.
However, you can size it up in Javascript...
https://developers.google.com/chart/interactive/docs/basic_customizing_chart
So, for the options when you draw the chart (using chart.draw(data, options) as above)...
var options = {
width:400,
height:300
}
A good fiddle for a responsive design is here...
http://jsfiddle.net/toddlevy/pyAz5/
$(window).resize(function(){
var container = document.getElementById("chart_div").firstChild.firstChild;
container.style.width = "100%";
chart.draw(data, options);
});
Please Remove the width and the height properties from the options in the scripts and then add the following style to your page
<style>
.chart {
width: 100%;
min-height: 450px;
}
.row {
margin: 0 !important;
}
</style>

Scrollable Foundation Section headers

Looking through http://foundation.zurb.com/docs/components/section.html, is there anyway I can add horizontal scroll for Section headers ( Tabs) . I am looking something like http://www.seyfertdesign.com/jquery/ui.tabs.paging.html in foundation sections with horizontal scroll and continue to use accordion in small screen
I found a solution for those interested : https://codepen.io/gdyrrahitis/pen/BKyKGe
.tabs {
overflow-x: auto;
white-space: nowrap;
-webkit-overflow-scrolling: touch;
.tabs-title {
float: none;
display: inline-block;
}
}
if someone needs an angularjs with jquery implementation, below code can help you, for pure jquery replace angularjs directive method with a native js method with respective attributes.
I tried to search for similar implementation but found nothing, so I have written a simple angular directive which can transform a foundation CSS tabs to scrollable tabs
angular.module("app.directives.scrollingTabs", [])
.directive("scrollingTabs", ScrollingTabsDirective);
//#ngInject
function ScrollingTabsDirective($timeout, $window) {
return {
restrict: 'A',
link: function (scope, element, attr) {
if(attr.scrollingTabs == "true"){
element.addClass('scrolling-tabs-container');
element.find('.nav-buttons').remove();
element.append('<div class="scrolling-tabs nav-buttons nav-buttons-left"></div>');
element.append('<div class="scrolling-tabs nav-buttons nav-buttons-right"></div>');
let scrolledDiv = $(element).find('.tabs');
let scrolled;
let scrolling;
let scrollFn = (step, animationTime, cb) => {
scrolled = Math.max(scrolled + step, 0);
scrolledDiv.animate({
scrollLeft: scrolled
}, animationTime, ()=>{
if (scrolling) {
scrollFn(step, animationTime, cb)
}else{
if(cb){cb()}
}
});
};
let checkActiveNavButtonsClasses = () => {
scrolled = scrolledDiv.scrollLeft();
let scrollWidth = scrolledDiv.get(0).scrollWidth;
let scrolledDivWidth = scrolledDiv.get(0).clientWidth;
if(scrollWidth > scrolledDivWidth){
element.addClass('nav-active');
scrollWidth = scrolledDiv.get(0).scrollWidth;
if(scrolled == 0){
element.removeClass('nav-active-left').addClass('nav-active-right')
}else if(scrolled > 0 && scrolled + scrollWidth < scrolledDivWidth){
element.addClass('nav-active-left').addClass('nav-active-right');
}else if(scrolled > 0 && scrolled + scrollWidth >= scrolledDivWidth){
element.addClass('nav-active-left').removeClass('nav-active-right');
}else{
element.removeClass('nav-active-left').removeClass('nav-active-right')
}
}else{
element.removeClass('nav-active-left').removeClass('nav-active-right').removeClass('nav-active');
}
};
let scrollToActiveTab = () => {
let activeDD = scrolledDiv.find('dd.active');
let tabsOffset = scrolledDiv.offset();
let activeTaboffset = activeDD.offset();
let activeTabwidth = activeDD.width();
let scrolledStep = activeTaboffset.left - tabsOffset.left - scrolledDiv.width() + activeTabwidth;
scrollFn(scrolledStep, 100, checkActiveNavButtonsClasses);
};
element.find(".nav-buttons.nav-buttons-left")
.off("click.scrolling")
.on("click.scrolling", (event)=>{
event.preventDefault();
scrolling = false;
scrollFn(-100, 100, checkActiveNavButtonsClasses);
})
.off("mouseover.scrolling")
.on("mouseover.scrolling", function (event) {
scrolling = true;
scrollFn(-2, 1, checkActiveNavButtonsClasses);
})
.off("mouseout.scrolling")
.on("mouseout.scrolling", function (event) {
scrolling = false;
});
element.find(".nav-buttons.nav-buttons-right")
.off("click.scrolling")
.on("click.scrolling", (event)=>{
event.preventDefault();
scrolling = false;
scrollFn(100, 100, checkActiveNavButtonsClasses);
})
.off("mouseover.scrolling")
.on("mouseover.scrolling", function (event) {
scrolling = true;
scrollFn(2, 1, checkActiveNavButtonsClasses);
})
.off("mouseout.scrolling")
.on("mouseout.scrolling", function (event) {
scrolling = false;
});
$timeout(()=>{
checkActiveNavButtonsClasses();
scrollToActiveTab()
},1000);
$($window).off('resize.scrolling').on('resize.scrolling', _.debounce(()=> {
checkActiveNavButtonsClasses();
}, 500));
scope.$on('$destroy', function() {
$($window).off('resize.scrolling');
});
}
}
}}
css:
.scrolling-tabs-container {
position: relative;
.tabs {
overflow-x: hidden;
white-space: nowrap;
-webkit-overflow-scrolling: touch;
display: block;
margin-right: 18px;
dd {
display: inline-block;
float: none;
margin: 0px -3px 0px 0px;
}
.tabs-title {
float: none;
display: inline-block;
}
}
.scrolling-tabs {
&.nav-buttons {
display: none;
position: absolute;
width: 19px;
height: 38px;
border: 1px solid #c1c1c1;
top: 1px;
background-color: rgba(255, 255, 255, 0.5);
opacity: 0.4;
cursor: pointer;
&:hover {
opacity: 1;
&:before {
color: #444;
}
}
&:before {
position: absolute;
left: 7px;
top: 8px;
color: #777;
}
&.nav-buttons-left {
left: 0;
&:before {
content: '<';
}
}
&.nav-buttons-right {
right: 18px;
&:before {
content: '>';
}
}
}
}
&.nav-active{
.tabs{
margin-right: 36px;
margin-left: 18px;
}
.scrolling-tabs {
&.nav-buttons {
display: inline-block !important;
}
}
}
&.nav-active-left{
.scrolling-tabs{
&.nav-buttons-left{
opacity: 0.8;
}
}
}
&.nav-active-right{
.scrolling-tabs{
&.nav-buttons-right{
opacity: 0.8;
}
}}}
HTML: Foundation Tabs template.
<tabset class="list-tabs" scrolling-tabs="true">
<tab heading="tab1"></tab>
<tab heading="tab2"></tab>
<tab heading="tab2"></tab>
</tabset>
Before you start you'll want to verify that both jQuery (or Zepto) and foundation.js are available on your page. These come with foundation package so just uncomment them in your footer or include them accordingly.
<div class="section-container auto" data-section>
<section class="active">
<p class="title" data-section-title>Section 1</p>
<div class="content" data-section-content>
<p>Content of section 1.</p>
</div>
</section>
<section>
<p class="title" data-section-title>Section 2</p>
<div class="content" data-section-content>
<p>Content of section 2.</p>
</div>
</section>
</div>
The foundation documentation has all of the information for this :
http://foundation.zurb.com/docs/components/section.html#panel2
This will get you your section tabular headers. You then want to manage the content to be scrollable.
<div class="content" data-section-content>
<p>Content of section 1.</p>
</div>
This content here will be the area to work on, try adding a new class called .scrollable
Within this class use something like:
.scrollable{
overflow:scroll;
}
You may want to add some more to this however this will get you started. Your HTML should now look like this :
<div class="content scrollable" data-section-content>
<p>Content of section 1. This content will be scrollable when the content has exceeded that of the div size. </p>
</div>
This this is what you are looking for.

CSS Transitions when display:none is set

How do you transition using CSS the properties of elements with display none?
My current solution is to set display to block with JavaScript, wait 10 milliseconds for repaint, then apply the class that changes the properties I want to animate.
Note: I'm using jQuery for code brevity.
CSS - animating opacity as an example. Don't care about $.show().
.element
{
display:none;
opacity:0;
-webkit-transition:all 0.5s;
-moz-transition:all 0.5s;
-ms-transition:all 0.5s;
-o-transition:all 0.5s;
transition:all 0.5s;
}
.element.shown
{
opacity:1;
}
JavaScript
function show()
{
var $element=$('.element');
$element.css({display:'block'});
//Add class a few moments later than chaning display to block, otherwise animations CSS Transitions won't fire
setTimeout(function(){
$element.addClass('shown');
},10);
}
function hide()
{
var $element=$('.element');
$element.removeClass('shown');
//Remove element from display after transition ends
$element.on('webkitTransitionEnd otransitionend oTransitionEnd MSTransitionEnd transitionend',function()
{
$element.css({display:'none'});
});
}
I feel there should be a better way though, a CSS-only way. Is there?
I just found workaround. All you need is use animation and start it little bit after you apply display:block. Like this:
#keyframes submenu_animation {
from {
opacity: 0;
}
1% {
opacity: 0;
}
99% {
opacity: 1;
}
to {
opacity: 1;
}
}
li ul {
opacity: 0;
display: none;
animation-name: submenu_animation;
animation-duration: 300ms;
animation-direction: reverse;
li ul.open {
display: block;
}
li:hover ul {
animation-direction: normal;
opacity: 1;
}
Javascript is pretty the same, It will apply class "open" once you hover on required element. When you hover-out it will remove "open" class little bit later, when animation is finished.