简体   繁体   中英

Changing html tag structure on window resizing

I would like to rebuild an html tag structure to a new one on resizing the browser window. Have anyone an idea how can I get from the first structure to the second structure. I need this for an responsive personal project. Maybe with an JavaScript resize Event, I don't know...

<div class="wrapper">
    <div class="slide">
        <div class="item"></div>
        <div class="item"></div>
    </div>
    <div class="slide">
        <div class="item"></div>
        <div class="item"></div>
    </div>
</div>

<div class="wrapper">
    <div class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
</div>

You could listen to the resize event on the window and then restructure your HTML when the window is below a certain size. Moving elements from the first structure to the second isn't a big problem, however the challenge lies in reverting that again. How will you know which of the .item 's belonged to which .slide ?

One way to do this is to keep track of the parent for each .item in a separate data- attribute when you make the list:

function makeList() {
    var $slides = $('.slide'),
        $items = $();

    // For each slide set a data-attribute on all its child .item's 
    $slides.each(function(i) {
        var $item = $(this).children('.item');

        $item.attr('data-slide', i+1);
        $items = $items.add($item);
    });

    // Append all items directly to the wrapper
    $('.wrapper').html($items).attr('data-structure', 'list');
}

I set a data attribute to the .wrapper so we know that it's already converted to a list. Otherwise on every resize this would be fired, you only want it once (until it resizes back to where you want the slides).

When you want the slide again, loop through all the .item s and keep a list of slide number's. For each new data-slide number you encounter make a new slide and add that to the total list;

function makeSlides() {
    var $slides = $(),
        slideNumbers = [],
        $currentSlide = $();

    $('.item[data-slide]').each(function() {
        var $item = $(this),
            slideNumber = $item.attr('data-slide');

        // if the slide number wasn't in the array yet push the current slide into $slides and create a new one
        if(slideNumbers.indexOf(slideNumber) < 0) {
            $slides = $slides.add($currentSlide);
            $currentSlide = $('<div class="slide" />');

            slideNumbers.push(slideNumber);
        }
        $currentSlide.append($item);
    });

    // add the last currentSlide
    $slides = $slides.add($currentSlide);

    // place all slides in the wrapper
    $('.wrapper').html($slides).attr('data-structure', 'slides');
}

Then finally you bind the resize event and fire these functions when needed:

$(window).resize(function(e) {
    var currentStructure = $('.wrapper').attr('data-structure');

    if(window.innerWidth < 600) {
        if( currentStructure !== 'list') {
            makeList();
        }
    } else {
        if( currentStructure !== 'slides') {
            makeSlides();
        }
    }
});

jsFiddle demo: http://jsfiddle.net/gktLnw31/3/

I do think this could be a bit more efficient, but this is just a proof of concept. Hopefully it'll give you some insights.

我最好看一下基础,因为它已经默认包含了响应式设计,而不是尝试通过代码动态地更改它

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