Jump to content
GreenSock

Search In
  • More options...
Find results that contain...
Find results in...
kylegach

SVG viewBox not behaving as expected

Warning: Please note

This thread was started before GSAP 3 was released. Some information, especially the syntax, may be out of date for GSAP 3. Please see the GSAP 3 migration guide and release notes for more information about how to update the code to GSAP 3's syntax. 

Recommended Posts

Animation/Workflow tip: Don’t forget - you can animate the viewBox attribute

I don’t see this technique in practice (or talked about) very much, but sometimes it may be a better solution than trying to scale elements and center them.

 

To illustrate this easy, but powerful method of SVG animation, I’ve made a simple house tour complete with some GreenSock home décor and a few nods to our great moderators. Take a look:

 

See the Pen OMabPa by PointC (@PointC) on CodePen

I’m looking for some help, please.
 
I’d like to use the zooming effect like in the quoted Pen, but the viewBox attribute isn't behaving as I expected and I can’t tell what I’m doing differently.
  • Here’s the original Pen with the issue:  (Edit: this is now fixed, but the simplified one still exhibits the issue, for reference)
  • And here’s a simplified test case without GSAP to show that even a static viewBox isn’t behaving the same as PointC’s example:

    See the Pen ONzzaG by kylegach (@kylegach) on CodePen

I’ve also read this (excellent) explanation of the SVG viewport, viewBox, and preserveAspectRatio: https://sarasoueidan.com/blog/svg-coordinate-systems/, but I just cannot determine why mine isn’t working.
 
Any help would be appreciated. Thanks!

See the Pen jqYaYp by kylegach (@kylegach) on CodePen

  • Like 1
Link to post
Share on other sites

Hi kylegach  :)

 

Welcome to the forums.

 

I think there is just a little problem with the coordinates you're using. The viewBox can be a bit strange to start using at first, but we can get you fixed up.

 

Let's look at your simplified static demo (thank you for that - much easier to help with stripped down demos)

// this is your current viewBox
<svg xmlns="http://www.w3.org/2000/svg" version="1.1" viewBox="420 310 1004 748">

// but to zoom to the orange rectangle, it should be
<svg xmlns="http://www.w3.org/2000/svg" version="1.1" viewBox="420 310 584 438">

The starting x/y is indeed 420/310, but the 1004/748 that you're using are not ending coordinates. (I thought the same thing the first time I used the viewBox.) The second set of numbers is how far along the x/y you want the view to extend. So in your example, the actual end coordinates are 1424/1058 which is why the zoom to orange box isn't working correctly.

 

The orange box is 584 units by 438 units so that is how far we want to extend the viewBox. That is also in the exact aspect ratio as your SVG so this works perfectly. We then use a viewBox="420 310 584 438" and it should zoom correctly.

 

Hopefully that makes sense and helps a bit.

 

Let us know if you have any more problems.

 

Happy tweening and welcome aboard.

:)

  • Like 1
Link to post
Share on other sites

Thank you!! I suppose I shouldn’t be surprised it was something so relatively simple when I was operating on ~4 hrs sleep while working on it last night. :P

 

That explanation was very helpful and solved my issue exactly. And yes, I intentionally made the aspect ratios match, per your comments in that quoted post.

 

Thanks also for your original house Pen. It was obviously inspirational. The animation I shared is part of a larger effort, which I’ll be sure to share here once it’s complete so you can see what you helped create. :P

  • Like 1
Link to post
Share on other sites

You're welcome. I'm happy to help and glad you found my house tour animation inspirational.

 

Yes - please share your finished work when it's ready. I'd love to see it.

 

:)

Link to post
Share on other sites

Great job, Craig!

 

Kylegach, thanks for moving the topic here. Glad to see you were well taken care of.

 

Best,

 

Carl

  • Like 1
Link to post
Share on other sites

Thanks Carl.

 

It's my new mission to get everyone hooked on animating the viewBox with GSAP. :-P  

Link to post
Share on other sites

I’m still working on the site in which they’ll be featured, but here’s the finished animation from this thread (I changed it a bit from my original zooming-in plan) and another one that also animates the viewBox:

I’m all ears for suggestions of improvement, if you feel like sharing. :) Specifically, in that first one, I had to do some funny stuff (see the tweens ending with “_strokeReset”) because I couldn’t get the onComplete parameter of TweenLite.to() to work. It would fire immediately, instead of after the animation finished, which had the result of completely cancelling the line drawing effect. And in both, I had to redefine any width and height that I changed with a tween, because GSAP was setting them to “auto” once the animation looped. Simple enough, but it seemed like there should be a better way.

 

Thanks again for your help, Craig & Carl! I’ve felt very welcome here, and had fun learning GSAP for the first time. Now I just need to get it working in my statically-generated React site... Done!

  • Like 1
Link to post
Share on other sites

It's my new mission to get everyone hooked on animating the viewBox with GSAP. :-P  

 

Why don't you take it to next level and create an SVG camera plugin?

 

This demo is using Pixi, but how cool would it be to do something like that in SVG?

https://gameofbombs.com/demos/railroad/v2.1/

  • Like 1
Link to post
Share on other sites

Holy cow - that is cool!  8-)

 

Every time I animate the viewBox, I want to animate a camera like I do in After Effects. 

 

I'll leave the creation of the new plugin to Master Blake. Can that be ready by Friday?  :-P

Link to post
Share on other sites

I honestly don't think the tracking part would be too difficult to implement. You can look at any platform/side scrolling game to see how it's done. You could even add in a nice parallax effect like this.

 

http://www.yeahbutisitflash.com/pixi-parallax-scroller/tutorial-4/index.html

 

Now being able to zoom in/out of the viewBox, that might require a little more code and thought. I don't think I'll be able to have it done by Friday, so I'll just delegate this task out to Mr. @GreenSock.

  • Like 1
Link to post
Share on other sites

That's funny you posted that parallax demo. I've been working on a new CodePen demo that's quite similar. I was also tinkering with blur filters on zoom in/out to simulate depth of field.

 

I agree - Jack should probably take over this whole operation. I don't think he has anything else to do anyway.  :-D

  • Like 1
Link to post
Share on other sites

I have a really cool idea for a camera/viewBox animation, but I'm not sure how to go about it using pure SVG. I might have to use canvas for the underlying data. 

 

My idea is to create animations using the A* (A star) search algorithm, which can find a path between 2 points. So you would animate the camera/viewBox moving from start to finish. The user would have the ability to select the start and ending destination. Think of it like a maze...

 

oF5Uys8.png

 

You can play around with that editor here...

http://qiao.github.io/PathFinding.js/visual/

 

 

Now let's take that a step further. I want to animate my route between different cities. This would work well for your flight path animation.

 

4qZC6To.png?1

 

You can play with that demo here...

http://www.jsgl.org/doku.php?id=pathfinder

 

You could even apply this to your house tour demo. Just add in some stairs and the camera would follow a path using the stairs when moving between rooms on different floors.

 

Those are both really cool demos, but they could be so much better using camera/viewBox animations.

  • Like 2
Link to post
Share on other sites

Blake I can't help but think that the "real work" you do is holding you back from much greater things!

 

;)

  • Like 2
Link to post
Share on other sites

I couldn't agree with you more! Unfortunately, it's the "real work" that brings in the income... at least for the time being. I'm sure one these days I'll come across a job that will give me more creative control to research and test out new ideas.

Link to post
Share on other sites

Very cool! How about this, animate it using path data. So allow to it accept an array of values and animate it using the BezierPlugin.

Link to post
Share on other sites

Yeah, I'm not sure if there's any easy way to extend the BezierPlugin. But I was thinking that you could just incorporate the Bezier plugin into yours instead of having to do an onUpdate call.

 

You could also interpolate the path manually, but there won't be any time resolution. Kind of a long formula, but for each segment you input the 4 points, and t is the progress of that segment. 

// B(t) = (1-t)^3 * p0 + 3*(1-t)^2 * t * p1 + 3*(1-t)* t^2 * p2 + t^3 * p3

function interpolate(p0, p1, p2, p3, t, target) {

  var t2 = t * t;
  var t3 = t * t2;

  var m1 =  1 - t;
  var m2 = m1 * m1;
  var m3 = m1 * m2;

  target.x = m3 * p0.x;
  target.y = m3 * p0.y;

  target.x += 3 * t * m2 * p1.x;
  target.y += 3 * t * m2 * p1.y;

  target.x += 3 * t2 * m1 * p2.x;
  target.y += 3 * t2 * m1 * p2.y;

  target.x += t3 * p3.x;
  target.y += t3 * p3.y;
}
  • Like 3
Link to post
Share on other sites

That's really great Diaco. :)

 

Let's see - we've got Blake and Diaco revving up their giant brains at the same time on the same thread. We should probably all be careful because this could potentially rip a hole in the fabric of the universe.  :D

  • Like 3
Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    No registered users viewing this page.

×