TL;DR: Animating transform attribute on an SVG.Set doesn't act as expected, see https://codepen.io/AlexisBRENON/pen/LyPZRG when you hover the svg. Are there some bugs in my code?
Full version:
I'm trying to animate a simple SVG logo, in a similar way as the 'Abstergo' logo in 'Assassin's Creed' games (https://youtu.be/vbLz8JzFGXo).
The SVG has been drawn with Inkscape, and then exported as 'optimised SVG' to remove most of the Inkscape's namespace stuff. I don't want to use SVG.js to draw my SVG, just to animate it.
As you can see here (https://codepen.io/AlexisBRENON/pen/LyPZRG), the first translate animation works well, but I apply it to each part separately. Then, the rotate transform, applied to the SVG.Set, works for only 4 of the 5 parts, but when you move your mouse out of the SVG, all parts are affected by the reversed animation, before all the things collapse in some very strange animations...
By the way, the 'mouseover', 'mouseout' events seem to be triggered even when you just move your mouse over the SVG, which lead to strange behaviours when you don't stop to move your mouse. Any idea to fix this?
Kind regards,
Alexis
Related
I am using CSS animations to move two rectangle div tags across the screen. Each one is like a pole (taller than it is wide). The animations make each div rotate so it is at an angle before going back to pointing upwards.
One animation is triggered by the user, and the other is constantly moving itself towards the other div.
I have tried using getBoundingClientRect() to detect when the corner of one div intercepts the div that is moving towards it. I also used jQuery to get the .position() of them, but they return left: 0.
The div that is moving across the screen is done using the margin-left property.
Are there any methods I should be looking into or does anyone have a solution to a similar problem?
Thanks,
DH
You should use transform: translate to move them.
Also, since you're moving the elements in javascript you should just keep their state stored in memory and do your collision detection entirely in javascript.
There should be no need to use DOM APIs for this.
There's no method on the DOM for you to be able to detect overlapping objects. I would suggest using a geometric model of the scene and doing the trigonometry yourself to see when there is an intersection between the two boxes. Animating your objects explicitly using JS is also easier, since you wouldn't have to worry about getting out of sync with the browser's CSS animations or transitions.
You'd basically be looking for a line-line intersection.
Part of my app requires the user to be able to use the mousewheel to zoom in on an image which is already centered inside a larger container element.
I am using jQueryUI to provide a slider with which the zoom is controlled manually.
When zooming withe mousewheel, the viewport adjusts so that the user is always zooming towards to mouse cursor providing exactly the same behaviour as google maps in terms of zoom functionality.
Also, in order to provide a better experience than using css transitions I have written a momentum based smooth scroll algorithm to make the zooming as smooth as possible.
Everything works perfectly with one exception.
To replicate the problem please follow these steps on the provided jsFiddle:
move mouse cursor to the center of the image.
Very gently move the mousewheel one notch so that the smoothwheel takes over an zooms you in a little.
Then move the mouse cursor to another point of the already slightly zoomed image
Zoom in again, as far as you want this time
Finally zoom all the way out
You will see that the zoomed out image is now misplaced (as the translates have not been removed).
The behaviour I want is for the zoomed out image to return to its original position once the scale is set back to 1.
If you remove the css translate from the image in Firebug you will see that the image returns to the correct location.
Therefore this could easily be achieved with a simple conditional like so:
if(scale == 1){
//remove transforms completely
}
However doing this would provide a jumpy experience and I would like the image to gradually zoom back out to the original position as the user zooms out.
It is worth mentioning that if you zoom all the way in without moving the mouse you will find that everything is correct when you zoom back out. This is simple because no translate gets added to the elements transform, simply a scale and transform-origin. In my code the translate only gets added when you change zoom position with the mouse mid zoom.
Unfortunately I cant seem to get my head around the best way of going about this.
Here is a working jsFiddle:
http://jsfiddle.net/3k332/15/
Thanks in advance for any help.
NOTE: I am well aware that there is some redundant code in my fiddle and that its not particularly elegant but this is merely a quick mock up to help you understand the problem.
I've came across wunderlist.com site and just fell in love with the zoom-like pop-up they have on the image just beneath the header "Learn more about Wunderlist".
I'd love to implement something like this on my site.
Can somebody tell me how this is done? I tried to reverse-engineer, but with no luck :)
I'm not hoping for the whole ready code, but maybe some guidelines on how to achieve this with CSS/jQuery.
Or maybe you know some jQuery plugin that I could use?
They are using all CSS. Pretty simple really.. I would code a full js fiddle example for you but I don't have the time, so instead I will list out the different elements you need and how they interact.
First the large image is just a div with a background image with set
dimensions.
The circular images themselves are generated from one large image containing all of the circles in one spot, this is called a sprite. The circles are just div's with background images and background positioning to position the correct circle inside the box from the sprite image.
The text boxes themselves are also div's with a standard H2 and P tags for the text.
Everything is absolute positioned in order to achieve the proper layout.
The small circles are div's with :hover states that are absolute positioned over their respective targeted areas.
The animation on :hover is achieved by the use of css3 transition and css3 transforms.
This should get you started.
Comment if you have questions.
Had some time to have some fun: http://khill.mhostiuckproductions.com/siteLSSBoilerPlate/fun-experiment-mh/
Try looking at two main aspects:
Open up your inspector tool of choice and look at what happens to body.login .feature
...more specifically, look at what happens to its transform: scale and opacity values upon :hover.
Hint: the transition is mainly on them.
Still in your inspector, change the scale to (1) and the opacity to 1. How it smoothly gets from one state to the other is dictated by the transition property.
This isn't meant to tell you exactly how to achieve it, but to get you on your way :)
It's not that hard actually. The Wunderlist team has even made it easier. They have a large sprite image with the zoomed images cropped and ready with rounded corners, borders and shadows. You can see it here: https://wunderlist2.s3.amazonaws.com/179510ff7c929bfcc6e9819f3c2539baca5d3325/images/welcome-screen.png
What you do is on mouseover you show a half transparent black background (can be position: fixed with full width and height). Then you create a element with the sprite as the background image (even better, have a class ready in your css and append it to your newly created element). Set position to the position of the hovered element.
When added to the dom animate the transform scale of the element (starting with something like scale(.24) as they do).
Well since you tried reverse engineering. I'll try and guide you along that path.
There is only one div with id overlay which is changes it's place & content, on hover of any div with class feature. Work your way further from their app js, it's not minified.
The content of the popup in this case is an image moved to different positions.
I have a container of some HTML divs and with some CSS if I hover over them, the background color changes. I want to overlay a canvas on top of the container so that I can draw lines. The problem is that when the canvas is overlaid, the hovering changes of the divs no longer works. Is there a way to overlay a canvas but still have CSS or JavaScript onmouseover events still work on the elements beneath?
So you want sort of a transparent canvas which passes all mouse events except clicks to the elements behind it?
IMHO, you'd need to use JS for that: Capture all the events on the canvas, then manually pass them on to the div behind the canvas. If you have multiple divs, you'd need some sort of lookup depending on the (x,y) coordinates of the mouse.
An alternative to going through all that hassle would be by using the pointer-events CSS attribute. Mozilla,Webkit and IE6-8(excanvas) all support this. Opera does not, but I really don't care.
<canvas style="pointer-events:none;"></canvas>
Is there a way to create the effect shown here on msi.com main image? Though done in flash, I'd prefer doing it with jquery. I've also tried with 'mosaic generators', but haven't been able to replicate the effect well, but use of a generator with js would be acceptable too.
[edit] I failed to mention, I'm only interested in emulated the tiled/mosaic aspect of the effect, not animation. I'd like a large image (e.g. 400px by 300px) separated by whitespace (or color customizable borders) into 9 equally sized blocks or tiles each.
While I would like to apply a individual hover effect to each image, giving each the effect they are separate entities, I don't necessarily need any further animation.
Rounded corners aren't important or wanted.
[/edit]
It would be pretty interesting to do it with jquery. You'd have a table of images, each with a hover event that toggled an animation when mousing on and off. The logic isn't too hard; getting the images and the animation to look nice would be a little harder, but not undoable. It depends on how closely you want to replicate the effect. :D
edit: you just want a mosaic of images? you can just use a table to position all of the images, and use js for the events. What else do you want or need js for? :D
Here's an idea. Load a large image into a DIV. Decide on the size of your windows and create a PNG with transparency where you'd like the windows to be. (Opaque at the borders with thickness to control how wide you'd like the whitespace.) To create the effect, use three layers. The image at the bottom layer (which you can swap out as needed). The middle and top layer will be repeated along the x and y axises and controlled individually by jQuery. The middle layer will have the PNG with transparency and on top of that, the top layer with just a solid color (matching your page's background to "seem" invisible?). To create any "pretty" effects, you can adjust the opacity or animate the top layer of the separate boxes to show/hide the image on the bottom layer which will be visible through the middle layer's transparent area in the PNG.
Hope my explanation was clear. With some smart coding, this can be packaged and reused anywhere you'd like.