3

I'm using the progress bar that comes with the Ninja Forms Multi-Part Form addon and here's the setup of the progress bar.

<div class="nf-progress-container">
    <div class="nf-progress" style="width: 0%;"></div>
</div>

When I advance to each subsequent part of the multi-part form, some JS or jQuery changes the width of the inline style attribute in the .nf-progress div and the progress bar fills in with each step completed.

To help you visualize, here's what my UI looks like with styling.

Here's what my styles progress bar looks like, to help you visualize it

I'd like for the progress bar to animate the .nf-progress div as each step is completed. I thought it was going to be as simple as transition: width 1s ease;, but it's not working (even with -webkit-transition). Here's what I tried.

.nf-progress-container .nf-progress {
    transition: width 1s ease;
    -webkit-transition: width 1s ease;
}

I did a little more investigating and found that you can't animate inline styles with the transition css property. Not sure why, but you can't do it, apparently.

I kept digging and found an article that gets me closer here with pure css animation keyframes.

@-webkit-keyframes progress-bar {
   0% { width: 0; }
}
@-moz-keyframes progress-bar {
   0% { width: 0; }
}
@keyframes progress-bar {
   0% { width: 0; }
}

.nf-progress-container .nf-progress { 
  -webkit-animation: progress-bar 1s;
  -moz-animation: progress-bar 1s;
  animation: progress-bar 1s;
}

The benefit here is that I actually get some kind of animation. The problem with this approach though is that the animation starts at width:0% for every step of the progress bar. I want the element to transition from the previous width, whatever it was, to the new inline style width.

Does anyone know how to do this with CSS or if there is a way to accomplish this with jQuery?

Bobby
  • 113
  • 1
  • 11

1 Answers1

1

Where did you read it's impossible to transition the width of an element with inline styles? This is possible:

function increaseWidth() {
  var elem = document.querySelector('span');
  elem.style.width = elem.clientWidth + 50 + 'px';
}

setInterval(increaseWidth, 600)
span {
  height: 20px;
  width: 50px;
  transition: width 0.5s;
  background: purple;
  display: inline-block;
}
<span/>

In your case, a third party JavaScript library you are using is deleting then recreating the bar element you want to animate. This will prevent your animations from running.

If you really need the bar to animate, you can modify the source code of the third party app to ensure it mutates but does not destroy and recreate the bar element. Or you can write your own animating bar, which is quite straightforward (see above).

duhaime
  • 25,611
  • 17
  • 169
  • 224
  • I might have misread it, but seemed that this article (https://css-tricks.com/forums/topic/inline-styles-not-accepting-transition/) was saying that he couldn't use the css `transition` property to animate styles that were inline on the html element itself. I'd love to be able to do this with css alone, if possible. – Bobby Sep 01 '18 at 02:46
  • @BobbyBosler it looks like the OP in the thread you linked had a problem but later it gets resolved in the thread, as this is certainly possible (I did it above). When you say you want to do this with CSS alone, what do you mean -- no js on the page and the bar transitions? If so you could use keyframes, but how will you know when to run the animations? My hunch from your graphic above was that the bar grows in response to some user action--is that right? If so, why not use JS after the user action to grow the bar? – duhaime Sep 01 '18 at 02:50
  • I don't know JS that well and I've just gotten my feet wet in jQuery enough to be dangerous. I'm still not sure how to use the inspector to see what's going on in scripts on the page. I'm sure that the form is using JS/jQuery to change the inline width of the `.nf-progress` when the next button is clicked, but I have no idea how to hook into that and create an animation. What would probably be easier is if I linked to the project. You can access it at http://50.87.230.223/bcmedu/apply-now/ (password to view is "morethanacollege"). – Bobby Sep 01 '18 at 02:54
  • 1
    @Bobby ah, it appears that the JS library you're using is actually removing the element with the bar then creating a new one with a new width. That will prevent transitions. This would not be hard at all to code with custom JavaScript. I would highly recommend trying to do so if you're up for it, as this really won't take more than a few dozen lines of javascript and when you're done you'll be even more dangerous! If you get stuck you can just raise questions on SO and folks will be able to help... – duhaime Sep 01 '18 at 03:09
  • I wondered if something like that was going on. I couldn't figure out for the life of me why the width wasn't animating. It seemed like it theoretically should. How could you tell what the JS library was? I can't seem to figure out how to use the inspector to find that kind of thing. – Bobby Sep 01 '18 at 03:16
  • @Bobby well the source code is evidently available on Github for one thing, but I used my dev tools to investigate the bar element, then I removed it from the DOM with the dev tools. Then I hit the 'next' button, and presto-chango the bar was back! Also you can look at the methods that are bound to the click events on the previous and next buttons, and you can see the setElement function bound there -- this is a method built into Backbone (an old client-side MVC framework) that blows away and recreates a DOM element... FF dev tools screenshot: https://imagebin.ca/v/4E9tqPDEADeP – duhaime Sep 01 '18 at 03:26