Site logo

[Support request] insert image on top of product thumbnail if product is sold out

Home Forums Support [Support request] insert image on top of product thumbnail if product is sold out

Home Forums Support insert image on top of product thumbnail if product is sold out

Viewing 12 posts - 16 through 27 (of 27 total)
  • Author
    Posts
  • #1581077
    Elvin
    Staff
    Customer Support

    Ah, I posted the wrong code. My bad.

    Here’s the one I was supposed to give.

    <script>
    
    function coming_soon_toggle(){
        var wcgallery = document.querySelector('figure.woocommerce-product-gallery__wrapper'); //woocommerce photo wrapper
        var comingsoon = wcgallery.querySelector('div.sold_out_loop_wrapper'); // coming soon wrapper
        comingsoon.style.transition = "opacity 0.1s ease-in-out"; // Added transition
    
        wcgallery.addEventListener("mouseout", function( event ) {   //hover out
            comingsoon.style.display = "block"; // puts it back on the DOM
            comingsoon.style.opacity = '1'; //display it when not hovering
        }, false);
    
        wcgallery.addEventListener("mouseover", function( event ) {   //while hovering
            comingsoon.style.opacity = "0"; //remove from display on hover
            setTimeout(function(){ comingsoon.style.display = "none"; }, 1000); //hides it from DOM
        }, false);
    
    }
    window.addEventListener('DOMContentLoaded', function(){
        coming_soon_toggle(); //run the script after loading all elements
    });
    
    </script>

    I guess this happens because the display of the coming soon image is not “none” and still there, isn’t it?

    That’s correct. That’s actually the issue why the CSS approach wasn’t working. We needed the JS to make use of setTimeout() function so it adds display:none; exactly after finishing the animation so there’s no DOM that blocks with WooCommerce image’s eventlisteners.

    #1581148
    nik9

    Hi Elvin,

    Hmm.. Now the Zoom is working sometime and sometime not.. and after hover out, the coming soon image is disappears after 1s.

    The first js works the best currently. There we only have not a very smooth transition. Is there a quick way to give the comingsoon.style.display = "none"; //remove from display on hover maybe a transition like transition: opacity 1s ease-out; or something?

    <script>
    
    function coming_soon_toggle(){
        var wcgallery = document.querySelector('figure.woocommerce-product-gallery__wrapper'); //woocommerce photo wrapper
        var comingsoon = wcgallery.querySelector('div.sold_out_loop_wrapper'); // coming soon wrapper
    
        wcgallery.addEventListener("mouseout", function( event ) {   //hover out
            comingsoon.style.display = 'block'; //display it when not hovering
        }, false);
    
        wcgallery.addEventListener("mouseover", function( event ) {   //while hovering
            comingsoon.style.display = "none"; //remove from display on hover
        }, false);
    
    }
    window.addEventListener('DOMContentLoaded', function(){
        coming_soon_toggle(); //run the script after loading all elements
    });
    
    </script>
    #1581208
    Elvin
    Staff
    Customer Support

    The first js works the best currently. There we only have not a very smooth transition. Is there a quick way to give the comingsoon.style.display = “none”; //remove from display on hover maybe a transition like transition: opacity 1s ease-out; or something?

    This is precisely why it may be better to get a plugin for this. Developing this requires some thought on how to add in more conditions to make 2 display none and transition work well together.

    You can try modifying the addeventlistener part of the script into this:

        wcgallery.addEventListener("mouseout", function( event ) {   //hover out
            comingsoon.style.opacity = '1'; //display it when not hovering
            if( comingsoon.style.opacity === '1'){
                comingsoon.style.display = "block"; // puts it back on the DOM
            }
        }, false);
    
        wcgallery.addEventListener("mouseover", function( event ) {   //while hovering
            comingsoon.style.opacity = '0'; //remove on hover
            if( comingsoon.style.opacity === '0'){
                comingsoon.style.display = "none"; // remove from DOM
            }
        }, false);

    But I can’t really be sure if this will work. Perhaps it needs a writeup to increment opacity from 0 to 1 and then fire display:none/block but that needs a longer code writeup and a few testing to do.

    To remind: As previously mentioned, this is a site customization of a third party plugin (WooCommerce) which is outside of our scope.

    #1581247
    nik9

    Hi Elvin,

    I see no problem. Thanks for the script. Its does not work but I go with the first one. 🙂

    Cheers & many thanks
    Nik

    #1581376
    nik9

    Elvin, Let me ask a last question. 🙂

    What is the best way to adjust the script in order that is checks for a second class div.on_sale_loop_wrapper_single instead only one. Currently I just add a script twice and just changed the class here var comingsoon = wcgallery.querySelector('div.on_sale_loop_wrapper_single');

    I guess it would be better not to add for each class check a whole script. 🙂

    This is the script:

    <script>
    
    function coming_soon_toggle(){
        var wcgallery = document.querySelector('figure.woocommerce-product-gallery__wrapper'); //woocommerce photo wrapper
        var comingsoon = wcgallery.querySelector('div.on_sale_loop_wrapper_single'); // coming soon wrapper
    
        wcgallery.addEventListener("mouseout", function( event ) {   //hover out
            comingsoon.style.display = 'block'; //display it when not hovering
        }, false);
    
        wcgallery.addEventListener("mouseover", function( event ) {   //while hovering
            comingsoon.style.display = "none"; //remove from display on hover
        }, false);
    
    }
    window.addEventListener('DOMContentLoaded', function(){
        coming_soon_toggle(); //run the script after loading all elements
    });
    
    </script>

    Cheers

    #1582143
    Elvin
    Staff
    Customer Support

    What is the best way to adjust the script in order that is checks for a second class div.on_sale_loop_wrapper_single instead only one. Currently I just add a script twice and just changed the class here var comingsoon = wcgallery.querySelector(‘div.on_sale_loop_wrapper_single’);

    I guess it would be better not to add for each class check a whole script. 🙂

    You can use the same function and just add in your extra eventlistener if its for a different one.

    But if you’re using the same event listener to affect extra classes, you can just add in more changes within its block functions.

    But to answer the question: You can check w/ if condition what’s existing first before assigning an eventlistener. You’ll have to loop check the gallery’s child for any specified classes and then assign the listener if found.

    Example:

    var wcgallery_children = wcgallery.querySelectorAll('*'); //selects all descendants of gallery
    
    for(i=0; i.wcgallery_children.length;i++){ //looping through the descendants
            if( wcgallery_children[i].classList.contains('on_sale_loop_wrapper_single') ){ 
                //if class specified in contains() is found, do addEventlistener here.
                /
            } if( wcgallery_children[i].classList.contains('on_sale_loop_wrapper') ){ 
                //if class specified in contains() is found, do addEventlistener here.
    
            } else { return } //do nothing
    }

    This way, you’ll only need one loop and just add in more if conditions for each class you want to do specific instructions with.

    #1582504
    nik9

    Hello Elvin

    I trying this… But I guess this is wrong.
    Currently we have 3 classes to add

    div.sold_out_loop_wrapper_single
    div.badge_loop_wrapper_single
    div.special_loop_wrapper_single

    <script>
    
    function coming_soon_toggle2(){
        var wcgallery = document.querySelector('figure.woocommerce-product-gallery__wrapper'); //woocommerce photo wrapper
       		var wcgallery_children = wcgallery.querySelectorAll('div.badge_loop_wrapper_single','div.sold_out_loop_wrapper'); //selects all descendants of gallery
    
    for(i=0; i.wcgallery_children.length;i++){ //looping through the descendants
            if( wcgallery_children.classList.contains() ){ 
                //if class specified in contains() is found, do addEventlistener here.
                          
    					    wcgallery.addEventListener("mouseout", function( event ) {   //hover out
            comingsoon.style.display = 'block'; //display it when not hovering
        }, false);
    
        wcgallery.addEventListener("mouseover", function( event ) {   //while hovering
            comingsoon.style.display = "none"; //remove from display on hover
        }, false);
    					
    
            } else { return } //do nothing
    }
    
    window.addEventListener('DOMContentLoaded', function(){
        coming_soon_toggle2(); //run the script after loading all elements
    });
    
    </script>
    #1583573
    Elvin
    Staff
    Customer Support

    To clarify: These 3 new classes will have the same effect as comingsoon class? meaning it will use the same element (gallery) to use as hover trigger?

    Let us know.

    #1583991
    nik9

    Yes, all of them would have the same effects.

    #1584085
    Elvin
    Staff
    Customer Support

    Try this:

    <script>
    
    function coming_soon_toggle(){
        var wcgallery = document.querySelector('figure.woocommerce-product-gallery__wrapper');
        var wcgallery_children = wcgallery.querySelectorAll('*'); //selects all descendants of gallery
        var soldout;
        var badge;
        var special;
    
        for(i=0; i.wcgallery_children.length;i++){ //looping through the descendants
            if( wcgallery_children.classList.contains('sold_out_loop_wrapper_single') ){ 
                var soldout = wcgallery.querySelector('div.sold_out_loop_wrapper');
            } if( wcgallery_children.classList.contains('badge_loop_wrapper_single') ){ 
                var badge = wcgallery.querySelector('div.sold_out_loop_wrapper');
            } if( wcgallery_children.classList.contains('special_loop_wrapper_single') ){ 
                var special = wcgallery.querySelector('div.sold_out_loop_wrapper');
            } else { return } //do nothing
        }
    
        wcgallery.addEventListener("mouseout", function( event ) {   
            if( null != soldout ){ 
                soldout.style.display = "block";
            } if( null != badge ){ 
                badge.style.display = "block";
            } if( null != special ){ 
                special.style.display = "block";
            } else { return } //do nothing
        }, false);
    
        wcgallery.addEventListener("mouseover", function( event ) {   
            if( null != soldout ){ 
                soldout.style.display = "none";
            } if( null != badge ){ 
                badge.style.display = "none";
            } if( null != special ){ 
                special.style.display = "none";
            } else { return } //do nothing
        }, false);
    }
    window.addEventListener('DOMContentLoaded', function(){
        coming_soon_toggle();
    });
    
    </script>

    I’ve significantly re-written the code to check for what is existing.

    Not sure if it will work though. The code is getting a bit more complex and its hard to tell especially when I can’t test it out completely on your setup.

    Here’s another way of doing it.

    <script>
    
    function coming_soon_toggle(){
        var wcgallery = document.querySelector('figure.woocommerce-product-gallery__wrapper');
        var wcgallery_children = wcgallery.querySelectorAll('*'); //selects all descendants of gallery
        var soldout;
        var badge;
        var special;
    
        for(i=0; i.wcgallery_children.length;i++){ //looping through the descendants
            if( wcgallery_children.classList.contains('sold_out_loop_wrapper_single') ){ 
                var soldout = wcgallery.querySelector('div.sold_out_loop_wrapper');
                wcgallery.addEventListener("mouseout", function( event ) {   
                    soldout.style.display = "block";
                }, false);
                wcgallery.addEventListener("mouseover", function( event ) {   
                    soldout.style.display = "none";
                }, false);
            } if( wcgallery_children.classList.contains('badge_loop_wrapper_single') ){ 
                var badge = wcgallery.querySelector('div.sold_out_loop_wrapper');
                wcgallery.addEventListener("mouseout", function( event ) {   
                    badge.style.display = "block";
                }, false);
                wcgallery.addEventListener("mouseover", function( event ) {   
                    badge.style.display = "none";
                }, false);
            } if( wcgallery_children.classList.contains('special_loop_wrapper_single') ){ 
                var special = wcgallery.querySelector('div.sold_out_loop_wrapper');
                wcgallery.addEventListener("mouseout", function( event ) {   
                    special.style.display = "block";
                }, false);
                wcgallery.addEventListener("mouseover", function( event ) {   
                    special.style.display = "none";
                }, false);
            } else { return } //do nothing
        }
    }
    window.addEventListener('DOMContentLoaded', function(){
        coming_soon_toggle();
    });
    
    </script>

    But again, This is also untested.

    #1585674
    nik9

    Hello Elvin,

    Na, this does not work. So I guess I go with the approach, to implement more than one scripts. Is that a problem in terms of performance?

    #1585689
    Elvin
    Staff
    Customer Support

    Na, this does not work. So I guess I go with the approach, to implement more than one scripts. Is that a problem in terms of performance?

    That’s unfortunate. But I believe I given you an idea. You’re pretty close. This is just a matter of assigning eventlisteners for mouseover/mouseout to the gallery. 🙂

    A bit more line of codes shouldn’t be that much of a hit in performance.

    But keep in mind, adding things bit by bit will eventually pile up and cause slow downs.

Viewing 12 posts - 16 through 27 (of 27 total)
  • You must be logged in to reply to this topic.