I'm trying to use getEleementById to display two different elements with two unique IDs on different pages. One is for the main index page and another is for the project page. The code below works on the index page but doesn't work on the project page. But if I get rid of the call in animation1, then it works on the project page. Any reason why document.getElementById can only be used once even though it's being called on two unique ids?
function displayTitle(id) {
var elem = document.getElementById(id);
elem.style.display = "block";
}
function animation1() {
displayTitle("main-bnb-logo");
var title1 = new TimelineMax();
title1.staggerFromTo(".title span", 0.5,
{ease: Back.easeOut.config(1.7), opacity: 0, bottom: -80},
{ease: Back.easeOut.config(1.7), opacity: 1, bottom: 0}, 0.05);
}
function animation2() {
displayTitle("project-title-content-wrapper");
var title2 = new TimelineMax();
title2.staggerFromTo(".project-title span", 0.5,
{ease: Back.easeOut.config(1.7), opacity: 0, bottom: -80},
{ease: Back.easeOut.config(1.7), opacity: 1, bottom: 0}, 0.05);
}
$(document).ready(function() {
animation1();
}, 1000);
$(document).ready(function() {
animation2();
}, 1000);
Problem solved. Like Tapas said in the comments, I needed to do a null check on the displayTitle function:
Updated code:
function displayTitle(id) {
var elem = document.getElementById(id);
if (elem == null) {
console.log('no id selected');
} else {
elem.style.display = "block";
}
}
function animation1() {
displayTitle("main-bnb-logo");
var title1 = new TimelineMax();
title1.staggerFromTo(".title span", 0.5,
{ease: Back.easeOut.config(1.7), opacity: 0, bottom: -80},
{ease: Back.easeOut.config(1.7), opacity: 1, bottom: 0}, 0.05);
}
function animation2() {
displayTitle("project-title-content-wrapper");
var title2 = new TimelineMax();
title2.staggerFromTo(".project-title span", 0.5,
{ease: Back.easeOut.config(1.7), opacity: 0, bottom: -80},
{ease: Back.easeOut.config(1.7), opacity: 1, bottom: 0}, 0.05);
}
$(document).ready(function() {
animation1();
animation2();
}, 1000);
Related
I have a problem with Fabric Text Box: user can't select TextBox & edit value. And using function canvas.MoveTo to set image of cloud to index 2 & Text Box to index 7, I expect TextBox is above Image, but actually, the Text box is always display behind the cloud image.
Here is my code
var canvasObject = document.getElementById("editorCanvas");
// set canvas equal size with div
$(canvasObject).width($("#canvasContainer").width());
$(canvasObject).height($("#canvasContainer").height());
var canvas = new fabric.Canvas('editorCanvas', {
backgroundColor: 'white',
selectionLineWidth: 2,
width: $("#canvasContainer").width(),
height: $("#canvasContainer").height()
});
canvas.setBackgroundImage('https://futushigame.firebaseapp.com/Background.svg', canvas.renderAll.bind(canvas), {
// Needed to position backgroundImage at 0/0
originX: 'left',
originY: 'top'
});
fabric.Image.fromURL("https://futushigame.firebaseapp.com/group5.svg", function(img) {
img.left = 0.2;
img.top = 54.94981;
canvas.add(img);
canvas.moveTo(img, 2);
canvas.renderAll();
});
var textbox7 = new fabric.Textbox("LITTLE PRINCESS", {
left: 0,
top: -14.620352,
width: 169.598436,
fontSize: 19.3302,
fontFamily: 'Nunito-Bold',
fill: "#000000",
editable: true,
});
textbox7.editable = true;
canvas.add(textbox7);
canvas.moveTo(textbox7, 7);
textbox7.transformMatrix = [1, 0, 0, 1, 64.7895, 169.1073];
textbox7.setCoords();
canvas.renderAll();
#canvasContainer {
width: 100%;
height: 100vh;
background-color: gray;
}
<script src="https://code.jquery.com/jquery-3.3.1.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/fabric.js/2.4.3/fabric.js"></script>
<div id="canvasContainer">
<canvas id="editorCanvas"></canvas>
</div>
For moveTo index, better choose a number between 0 and number of object present in canvas.
And as I see you are changing left and top using tansformMatrix, so just set left and top to the object.
var canvas = new fabric.Canvas('editorCanvas', {
backgroundColor: 'white',
selectionLineWidth: 2,
width: $("#canvasContainer").width(),
height: $("#canvasContainer").height()
});
canvas.setBackgroundImage('https://futushigame.firebaseapp.com/Background.svg', canvas.renderAll.bind(canvas), {
// Needed to position backgroundImage at 0/0
originX: 'left',
originY: 'top'
});
fabric.Image.fromURL("https://futushigame.firebaseapp.com/group5.svg", function(img) {
img.left = 0.2;
img.top = 54.94981;
canvas.add(img);
canvas.moveTo(img, 0);
canvas.renderAll();
});
var textbox7 = new fabric.Textbox("LITTLE PRINCESS", {
left: 64.7895,
top: 154.4856948,
width: 169.598436,
fontSize: 19.3302,
fontFamily: 'Nunito-Bold',
fill: "#000000",
editable: true,
});
canvas.add(textbox7);
canvas.moveTo(textbox7, 1);
//textbox7.transformMatrix = [1, 0, 0, 1, 64.7895, 169.1073];
textbox7.setCoords();
canvas.renderAll();
#canvasContainer {
width: 100%;
height: 100vh;
background-color: gray;
}
<script src="https://code.jquery.com/jquery-3.3.1.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/fabric.js/2.4.3/fabric.js"></script>
<div id="canvasContainer">
<canvas id="editorCanvas"></canvas>
</div>
I don't get it, what am I doing wrong? The element slides out on mouse click, but never slides in.
$(document).ready(function() {
var $okviric = $('#okviric');
var $slide = false;
if ($slide){
$okviric.on('click', function(){
TweenLite.to($okviric, 0.7, {bottom: 180, opacity: 0.7, ease:Power4.easeInOut});
$slide = false;});
}else{
$okviric.on('click', function(){
TweenLite.to($okviric, 0.7, {bottom: 0, opacity: 1, ease:Power4.easeInOut});
$slide = true;});
};
});
The problem is that you are checking for condition only once.
If $slide is false. The else part sets the onclick. After that this condition is never checked again until you reload the page. But as soon as you reload $slide is again set to false.
Solution is check this condition inside your onclick method.
$okviric.on('click', function(){
if($slide){
//
TweenLite.to($okviric, 0.7, {bottom: 180, opacity: 0.7, ease:Power4.easeInOut});
$slide = false;});
} else {
//
TweenLite.to($okviric, 0.7, {bottom: 0, opacity: 1, ease:Power4.easeInOut});
$slide = true;});
}
Now it will work properly.
So I want to save the canvas based on scale 1 and I want to include all existing/visible objects.
So right now, my canvas is 600x400 and if I were to save it, it would only save what's inside that 600x400, and it respects zoom level (a higher zoom will see less things, a lower zoom will see more things but smaller).
I've gotten around this by running this code:
let zoom = this.canvas.getZoom();
this.canvas.setZoom(1);
let url = this.canvas.toDataURL({width: 1000, height: 700, multiplier: 1});
this.canvas.setZoom(zoom);
window.open(
url,
'_blank' // <- This is what makes it open in a new window.
);
What this does is save the image as 1000x700, so stuff that were past 600px but under 1000 still gets saved.
However, this is hard coded. So I was wondering if there was an existing function or a clean/simple way to detect where all the objects are in and returns the full size (width and height).
fiddle: http://jsfiddle.net/1pxceaLj/3/
Update 1:
var gr = new this.fabric.Group([], {
left: 0,
top: 0
});
this.canvas.forEachObject( (o) => {
gr.add(o);
});
this.canvas.add(gr);
this.canvas.renderAll();
console.log(gr.height, gr.width); // 0 0
Solution
Using group was the best idea. Best example: http://jsfiddle.net/softvar/mRA8Z/
function selectAllCanvasObjects(){
var objs = canvas.getObjects().map(function(o) {
return o.set('active', true);
});
var group = new fabric.Group(objs, {
originX: 'center',
originY: 'center'
});
canvas._activeObject = null;
canvas.setActiveGroup(group.setCoords()).renderAll();
console.log(canvas.getActiveGroup().height);
}
One possibility would be to create a kind of Container using a fabricjs group and adding all created objects to this container.
I updated your fiddle here: http://jsfiddle.net/1pxceaLj/4/
Thus, you could just use group.width and group.height, perhaps adding a little offset or minimum values, and there you are having dynamical value to pass into toDataUrl even when having a smaller canvas.
code:
var canvas = new fabric.Canvas('c');
var shadow = {
color: 'rgba(0,0,0,0.6)',
blur: 20,
offsetX: 10,
offsetY: 10,
opacity: 0.6,
fillShadow: true,
strokeShadow: true
}
var rect = new fabric.Rect({
left: 100,
top: 100,
fill: "#FF0000",
stroke: "#000",
width: 100,
height: 100,
strokeWidth: 10,
opacity: .8
});
var rect2 = new fabric.Rect({
left: 800,
top: 100,
fill: "#FF0000",
stroke: "#000",
width: 100,
height: 100,
strokeWidth: 10,
opacity: .8
});
rect.setShadow(shadow);
//canvas.add(rect);
//canvas.add(rect2);
var gr = new fabric.Group([ rect, rect2 ], {
left: 0,
top: 0
});
canvas.add(gr);
function save()
{
alert(gr.width);
alert(gr.height);
let zoom = canvas.getZoom();
var minheight = 700;
canvas.setZoom(1);
let url = this.canvas.toDataURL({width: gr.width, height: gr.height > minheight ? gr.height : minheight, multiplier: 1});
canvas.setZoom(zoom);
window.open(
url,
'_blank'
);
}
I'm still in the learning stage of ajax and scripting. I recently stumbled upon this website http://www.maisonbertine.com/ found it very interesting using this script for loading the menu and contents.
I tried to learn and mimic the code on my testing website http://www.ztest.ca but I couldn't get it to work. If it works, it should load the Left Menu and Right Main H1 from www.ztest.ca/en/en.html
The after clicking on the language link, it does not change the url to www.ztest.ca/en/ so I guess the pushState method didn't execute. Also Firefox console is showing POST ztest.ca/en/ [HTTP/1.1 200 OK 209ms].
Below are the current code:
Language selection container:
<div id="container"><aside id="leftsidebar" class="is-white is-left"></aside>
<div class="lang" id="lang">
<div class="lang_logo"></div>
<div class="lang_selection" id="lang_selection">
<ul>
<li>English</li>
<li>Français</li>
</ul>
</div>
</div>
</div>
Script used to perform the TweenMax animation:
<script>window.jQuery || document.write('<script src="/js/libs/jquery-1.11.0.min.js"><\/script>')</script>
<script src="/js/libs/TweenMax.min.js"></script>
<script src="/js/libs/CSSPlugin.min.js"></script>
<script src="/js/script.js"></script>
<script>
$(function () {
if($(document).width()<736){
return false;
}
var tween1 = new TimelineMax();
tween1.add([
TweenMax.to("#lang", 1.3, {delay: 1, z: 0, left: 160, autoAlpha: 1, ease: Expo.easeOut,force3D:true}),
]);
tween1.add([
TweenMax.to("#lang_selection", 0.5, {z: 0, left: 160, ease: Expo.easeOut, force3D:true})
]);
$lang = $('#lang_selection');
$lang.on('click', 'a', function(e){
e.preventDefault();
$a = $(this);
var href= $a.attr('href');
$.ajax({
url:href,
type:'post',
dataType:'json',
success: function(response){
$html = $(response.page.html);
$wrapright = $($html[0]);
var nav = response.mainnav;
$container = $('#container');
$container.prepend($wrapright);
$('#leftsidebar').html(nav);
if(Modernizr.history){
window.history.pushState({href:'/'},'','/');
window.history.pushState({href:href},'',href);
document.title = response.page.seotitel;
}
tween1.add([
TweenMax.to("#lang_selection", 0.8, {z: 0, left: 0, ease: Expo.easeOut,force3D:true})
]);
tween1.add([
TweenMax.to("#lang", 0.8, {z: 0, left: -200, ease: Expo.easeOut,force3D:true})
]);
tween1.add([
TweenMax.to("#leftsidebar", 1.5, {z: 0, left: 0, ease: Expo.easeOut,force3D:true})
]);
tween1.add([
TweenMax.to("#overlay", 0.9, {z: 0, autoAlpha: 1,force3D:true})
]);
tween1.add([
TweenMax.to("#main h1", 2, {z: 0, top: '25%', autoAlpha: 1, ease: Expo.easeOut,force3D:true}),
]);
}
});
});
});
</script>
I think the problem is occurring here:
$lang = $('#lang_selection');
$lang.on('click', 'a', function(e){
e.preventDefault();
$a = $(this);
var href= $a.attr('href');
$.ajax({
url:href,
type:'post',
dataType:'json',
success: function(response){
$html = $(response.page.html);
$wrapright = $($html[0]);
var nav = response.mainnav;
$container = $('#container');
$container.prepend($wrapright);
$('#leftsidebar').html(nav);
if(Modernizr.history){
window.history.pushState({href:'/'},'','/');
window.history.pushState({href:href},'',href);
document.title = response.page.seotitel;
}
Please help me find the mistake I made here. Thank you!
I am quite new to js and jQuery and wanted to achieve a simple animation that has been discussed many times here: a bouncing ball. However, I did not find the answer to my specific question as topics discussed already were much more sophisticated.
I want a quite simple animation: five bounces and stay on the ground with the sixth. That one I have achieved so far. But for the five bounces I want to decrease the distance of bounce by 20% of the initial distance. Say the distance is 100, it should bounce to 80 first then to 60... to 20 to 0.
You can see my attempts here.
Or just the js code here:
$(function() {
var time = 500;
var bounces = 5;
function bounceDown(){
$(".ball").animate({top: 200}, time, function(){
bounceUp();
});
};
function bounceUp() {
$(".ball").animate({top: 100}, time);
};
function shadowUp(){
$(".shadow").animate({width: 100, height: 10, left: 85, top: 245, opacity: 1}, time,
function(){
shadowDown();
});
};
function shadowDown() {
$(".shadow").animate({width: 0, height: 0, left: 130, top: 225, opacity: 0}, time);
};
function finalDown(){
$(".ball").animate({top: 200}, time);
};
function finalShadow(){
$(".shadow").animate({width: 100, height: 10, left: 85, top: 245, opacity: 1}, time);
};
$(".button").on("click", function(){
for (var i = 0; i < bounces; i++){
setTimeout(function(){
bounceDown();
shadowUp();
}, time*2*i);
setTimeout(function(){
finalDown();
finalShadow();
}, 5000);
};
});
});
You can declare your initial top_bounce value:
var top_bounce = 100;
And then change your bounceUp function to:
function bounceUp() {
$(".ball").animate({top: top_bounce}, time);
top_bounce = top_bounce + 20;
};
Like you can see here: http://jsfiddle.net/darkajax/5wASf/
And about the "bonus question" mentioned in your comment, it'd be something similar, declare a variable like: var shadow_size = 0; and then your function like:
function shadowDown() {
console.log(shadow_size);
$(".shadow").animate({width: shadow_size*100, height: shadow_size*10, left: 110, top: 225, opacity: 0}, time);
shadow_size += 0.2;
};
You can see the fiddle updated, also you'd just have to do something similar with left to make it look centered