简体   繁体   中英

JS and CSS Centering Slideshow Images

I have a slideshow that pulls its first image from a div, then pulls the rest of the images from an array of list items. I am following a tutorial exactly from The JavaScript Pocket Guide by Burdette (2010 printing), and while everything else works I cannot get any of the pictures after the first to center or align differently. They float left and to the top of the div.

HMTL:

<!DOCTYPE html>
<hmtl class="no-js">

<head>
    <title>Slideshow</title>
    <link rel="stylesheet" href="slideshow.css" type="text/css" />

    <script type="text/javascript">
    (function(d, c) { d[c] = d[c].replace(/\bno-js\b/,"js";})(document.documentElement, "className");
    </script>

</head>


<body>
        <div id="slideshow">

            <div class="slides">
                <img src="picture01.jpg" width="450" height="336" alt="stuff" />
            </div>  

            <ul>
                <li><a href="picture02.jpg" data-size="350x263"</li>
                <li><a href="picture03.jpg" data-size="350x263"</li>
                <li><a href="picture04.jpg" data-size="350x263"</li>
            </ul>

        </div>

    <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.1/jquery.min.js" type="text/javascript">
    </script>

    <script src="slideshow.js" type="text/javascript">
    </script>


</body>

</hmtl>

CSS:

#slideshow {
    background-color: #103f1c; 
    width:500px;
    height:450px;
    margin-left: auto;
    margin-right: auto;
    top:0px;
    position: relative;
}

#slideshow .slides {
    position: relative;
    margin-left: auto;
    margin-right: auto;
    width: 450px;
}

#html.js #slideshow .slides img{
    position: absolute;
    margin-left: auto;
    margin-right: auto;
}

#slideshow .next,
#slideshow .prev {
    position: absolute;
    top: 50%;
    margin-top: -0.5em;
    width: 40px;
    font-size: 32px;
    text-decoration: none;  
}

#slideshow .next{
    right: -50px;
    padding-left:10px;
}

#slideshow .prev {
    left:-50px;
    padding-right: 10px;
    text-align: right;  
}

JS:

(function($) {

    // Include utility jQuery plug-ins

    $.fn.tallest = function(outer, margins) {
        var fn = outer ? "height" : "outerHeight";
        return Math.max.apply(Math, $.map(this, function(el) {
            return $(el)[fn](margins);
        }));
    };

    $.fn.widest = function(outer, margins) {
        var fn = outer ? "width" : "outerWidth";
        return Math.max.apply(Math, $.map(this, function(el) {
            return $(el)[fn](margins);
        }));
    };

    // Declare initial variables

    var slideshow = $("#slideshow");
    var slides = slideshow.find(".slides");
    var currentImageIndex = 0;

    // Create images from the link list

    slideshow.find("ul a").each(function() {

        var link = $(this);
        var size = link.attr("data-size").split("x");

        $("<img />").attr({
            src : link.attr("href"),
            width : size[0],
            height : size[1],
            alt : link.text()           
        }).hide().appendTo(slides);
    });

    // Collect all images in one node set and hide the list

    var images = slides.find("img");
    slideshow.find("ul").hide();

    // Resize slides <div> to hold the largest images

    var slidesWidth = images.widest();
    var slidesHeight = images.tallest();

    slides.css({
        width : slidesWidth,
        height : slidesHeight
    });

    // Center each image

    images.each(function() { 
        var image = $(this);
        image.css({
            left: slidesHeight / 2 - image.width() / 2,
            top: slidesHeight / 2 - image.height() / 2,
        });
    });

    // Save a reference to the first image

    var activeImage = images.eq(currentImageIndex);

    // The function to show the next or previous image

    function showImage(newIndex) {
        currentImageIndex = newIndex >= images.length ? 0 : newIndex;
        currentImageIndex = currentImageIndex < 0 ? images.length - 1 : currentImageIndex;
        activeImage.fadeOut(0);
        activeImage = images.eq(currentImageIndex).fadeIn(150); 

    }

    // Start timer to cycle through images

    var interval = setInterval(function() {
        showImage(currentImageIndex + 1);
    }, 5000);

    // Create next and previous controls

    $('<a href="#" class="next" style="color:white">\u232A</a>').appendTo(slides).bind("click", +1, onClick);
    $('<a href="#" class="prev" style="color:white">\u2329</a>').appendTo(slides).bind("click", -1, onClick);

    // The event handler for the controls   

    function onClick(event) {
        event.preventDefault();
        clearInterval(interval);
        showImage(currentImageIndex + event.data);  
    }

})(jQuery); // Self-invoking function executes automatically

The main problem here is in your CSS:

#html.js #slideshow .slides img{
    position: absolute;
    margin-left: auto;
    margin-right: auto;
}

Margin: auto; will only work on objects that have a defined width. Since an image is a replaced inline-block, no real width exists. This is made worse by the fact that you've positioned it absolutely, which changes the way margins will work - the item will always pick up its position relative to the determined parent, and apply margins after that outside of the flow, so auto will not be relevant.

first step is to remove the absolute positioning on the image, it's not useful here.

By default, images are a type of inline-block, so simply adding "text-align:center;" to the "#slideshow .slides" selector will center the images.

Alternately, if we just want to edit the images and force them to center themselves, change the above block to:

#html.js #slideshow .slides img{
    display:block;
    margin-left: auto;
    margin-right: auto;
}

and everything should line up like you wanted.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM