How to call jQuery function on CSS change

I have an image slider plugin in my Joomla website, and I want to make the opacity of each slider image gradually increase after initial display. To do this, I have a jQuery function I'd like to call whenever a particular CSS transition occurs: div's z-index value. As each slide becomes the featured one, its container div's z-index goes from 10 to 20.

Here's my jQuery function so far:

$(document).ready(function() {
	$(".sp-image").fadeTo(4000, 0.2);
});

Open in new window


That function fades all slider images one time only, on page load. I'd like to instead call the function whenever the "z-index" property of <div class="sp-slide"> changes to a value of 20 (from 10).

How can my function be written so it's called whenever the z-index of <div class="sp-slide"> changes to 20? (Assuming this is even doable.)

Thanks!

Regards,
Jon
Jonathan GreenbergAsked:
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

x
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

Chris StanyonWebDevCommented:
Not sure you can hook into CSS changes. Instead you could maybe hook into whatever is causing the z-index to change (assuming it's some other javascript elsewhere in your page - part of the slider code maybe). You may also want to take a look at the slider plugin (if that's what you're using) as most of them tend to have some way to configure the transitions already built in.
0
Jonathan GreenbergAuthor Commented:
Ok, Chris, thanks. But I'm really hesitant - and it's pretty far over my head - to get into the script that's affecting the z-index. That script is unbelievably long.

How about this. I just observed that the containing image div "grows" a class whenever it's active. Is there a way for a jQuery function to listen to all (3) divs of that class, 'sp-slide', and execute something when the additional class, 'sp-selected', shows up?
0
Chris StanyonWebDevCommented:
Hmm. Not easily doable, unless you're really comfortable messing with scripts. Having a quick google around and it looks like it could possibly be done with a MutationObserver, but it's not something I've ever done or even considered doing.

Have you checked the plugin's documentation. Like I said most offer some way to override the transition and some will even offer an event function for when the slider changes. That's really where you should be hooking into this.

If it isn't built in then there probably isn't an easy way to add this functionality.
0
Big Business Goals? Which KPIs Will Help You

The most successful MSPs rely on metrics – known as key performance indicators (KPIs) – for making informed decisions that help their businesses thrive, rather than just survive. This eBook provides an overview of the most important KPIs used by top MSPs.

Jonathan GreenbergAuthor Commented:
No, it's definitely not something that's built in to the plugin's functionality.

But... I just found the code in the plugin's script that's adding the class! Now I need help adding my own action.

Here's the code that's adding the class:

// Re-assign the 'sp-selected' class to the currently selected slide
this.$slides.find( '.sp-selected' ).removeClass( 'sp-selected' );
this.$slides.find( '.sp-slide' ).eq( this.selectedSlideIndex ).addClass( 'sp-selected' );

Open in new window


How can I hook into this last line and add my own action?

Thank you, Chris!
0
Chris StanyonWebDevCommented:
You should just be able to add your fade onto the end of it:

this.$slides.find( '.sp-slide' ).eq( this.selectedSlideIndex ).addClass( 'sp-selected' ).fadeTo(4000, 0.2);

Open in new window


You'll probably have to find some way to reset the opacity back to 1 again, otherwise it's still likely to be set to 0.2 the next time the slide comes around.
0
Chris StanyonWebDevCommented:
Just had a quick Google. If you're using the Slider Pro from BQWorks (the sp-selected class looks like you might be), then you do have direct access to the event function for when a slide changes. You would be much better off using that instead of directly editing the plug-in:

$('#my-slider').sliderPro({
    gotoSlideComplete: function( event ) {
        this.getSlideAt(event.index).$slide.fadeTo(1000, 0.2);
        this.getSlideAt(event.previousIndex).$slide.css('opacity', 1);
    }
});

Open in new window

0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
Jonathan GreenbergAuthor Commented:
Chris, thank you, that was so thoughtful of you!

I'm actually not using Slider Pro, but AP Smart LayerSlider. The strange thing is that the code appears very similar. Looks like someone borrowed from someone!

Assuming for a moment that they're similar enough that what you're suggesting would apply to both, I'm missing one thing, which is: what am I supposed to do with the first parenthetical text - '#my-slider' ? Would that get replaced with something?
0
Jonathan GreenbergAuthor Commented:
It's working! I don't want you to take anymore time on this, as I've figured out the answer to my question. I'll post back here shortly.
0
Chris StanyonWebDevCommented:
OK. As it's a Joomla plugin, you may not easily be able to get at the actual initialisation code, which is where you'd need to hook up the events. The code I posted above assumed you were initialising the PlugIn yourself. The #my-slider part is basically the HTML selector for the slider, so in my example it would turn a DIV with an ID of my-slider into the animated Slider.

I don't know Joomla, so can't offer you any advice on how to get at the init code for a plug-in. As it's a commercial plugin, you should have access to some kind of support from the developers, so an email to them may get you precisely the help you need.
0
Jonathan GreenbergAuthor Commented:
Actually, this is working perfectly, except for one thing. It's doing exactly what I said I needed to do, but I was a little off in saying what I need. I need to affect the opacity of an image 2 levels down in the dom; so the child's child of the div that's currently being acted upon.

Here's the script that's now working:

$('#ap-smart-layerslider-mod_171').sliderPro({
	gotoSlideComplete: function( event ) {
		this.getSlideAt(event.index).$slide.fadeTo(5000, 0.2);
		this.getSlideAt(event.previousIndex).$slide.css('opacity', 1);
	}
});

Open in new window


I need to target the class 'sp-image', which is an image and the child's child of the div currently being targeted.

What do you think - can it be done?
0
Jonathan GreenbergAuthor Commented:
Got it!

<script type="text/javascript">
jQuery(function($) { 
    $('#ap-smart-layerslider-mod_171').sliderPro({
        gotoSlideComplete: function( event ) {
            this.getSlideAt(event.index).$slide.find(".sp-image").fadeTo(5000, 0.2);
            this.getSlideAt(event.previousIndex).$slide.find(".sp-image").css('opacity', 1);
        }
    });
});
</script>

Open in new window


All that's missing is that the very first slide isn't being affected. This code is kicking in at each transition, but it's doing noting on the very first slide. Maybe I should do this with $( document ).ready() ?
0
Jonathan GreenbergAuthor Commented:
And here it is:

<script type="text/javascript">
jQuery(function($) { 
    $(document).ready(function() {
        $(".sp-selected").find(".sp-image").fadeTo(5000, 0.2);
    });
    $('#ap-smart-layerslider-mod_171').sliderPro({
        gotoSlideComplete: function( event ) {
            this.getSlideAt(event.index).$slide.find(".sp-image").fadeTo(5000, 0.2);
            this.getSlideAt(event.previousIndex).$slide.find(".sp-image").css('opacity', 1);
        }
    });
});
</script>

Open in new window


Chris, if you think there's any better way to do any of this than what I've done, please let me know. Otherwise, I think I'm good to go.

Thanks so much for your help!
0
Chris StanyonWebDevCommented:
Hey Jonathan,

That looks good. As an alternative to running your first fade on document.ready, you may be able to hook into the init event. Can't test it currently, but something like this may work:

$('#ap-smart-layerslider-mod_171').sliderPro({
    init: function() {
        this.getSlideAt(this.getSelectedSlide()).$slide.find(".sp-image").fadeTo(5000, 0.2);
    },
    gotoSlideComplete: function( event ) {
        this.getSlideAt(event.index).$slide.find(".sp-image").fadeTo(5000, 0.2);
        this.getSlideAt(event.previousIndex).$slide.find(".sp-image").css('opacity', 1);
    }
});

Open in new window

0
Jonathan GreenbergAuthor Commented:
Chris, that works perfectly!

Just so I understand, can you tell me why this is a preferable method to hooking into document.ready? Less taxing on the page as it loads, perhaps?
0
Chris StanyonWebDevCommented:
Hey Jonathan,

It's really just about keeping things in a sensible order. The document.ready block will fire when the document is ready i.e. the DOM has loaded. Now in your case, the DOM will be loaded before the Slider has been activated which may cause the first slider to fade before it's even part of the slider.

By adding it to the init event, you know it won't fire until the Slider is ready.

Also, for me, it just 'feels' right to keep all the Slider code in the slider methods.
0
Jonathan GreenbergAuthor Commented:
Thanks so much for your help on this, Chris! And thanks for letting me in on your thinking - it really helps.

All the best,
Jonathan
0
Chris StanyonWebDevCommented:
No worries Jonathan.

Glad you've got it working.
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
CSS

From novice to tech pro — start learning today.