窗口大小调整时的Vanilla Javascript操作元素

山姆·奥尔金(Sam Holguin)

我在玩Javascript标签系统。

当窗口宽度降到某个断点以下时,选项卡内容将插入到手风琴布局的链接之后,并且随着窗口宽度的增加,该过程将反向进行。

减小窗口大小时,一切都会按预期工作,但是随着增大窗口宽度,一切都会中断。以下代码导致了此问题tabBody.appendChild( tabBodyItems[k] );

3个.c-Tabs_BodyItem元素中只有2个附加???

的HTML

<div class="c-Tabs" id="js-Tabs">
    <div class="o-Container">
        <div class="o-Row c-Tabs_Head">
            <div class="o-Col-sm-4 c-Tabs_HeadItem">
                <a href="" class="c-Tabs_Link">Link 1</a>
            </div>
            <div class="o-Col-sm-4 c-Tabs_HeadItem is-active">
                <a href="" class="c-Tabs_Link">Link 2</a>
            </div>
            <div class="o-Col-sm-4 c-Tabs_HeadItem">
                <a href="" class="c-Tabs_Link">Link 3</a>
            </div>
        </div>
        <div class="c-Tabs_Body">
            <div class="c-Tabs_BodyItem">
                <ul>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                </ul>
            </div>
            <div class="c-Tabs_BodyItem is-active">
                <ul>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                </ul>
            </div>
            <div class="c-Tabs_BodyItem">
                <ul>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                </ul>
            </div>
        </div>
    </div>
</div>

Java脚本

我不会显示实际制表系统的Javascript;这不是引起问题的原因。

function insertAfter( el, referenceNode )
{
    referenceNode.parentNode.insertBefore( el, referenceNode.nextSibling );
}

function debounce( func, wait, immediate )
{
    var timeout;

    return function() {
        var context = this, args = arguments;
        var later = function() {
            timeout = null;
            if (!immediate) func.apply(context, args);
        };
        var callNow = immediate && !timeout;
        clearTimeout(timeout);
        timeout = setTimeout(later, wait);
        if (callNow) func.apply(context, args);
    };
}

var tabHeadItems = document.getElementsByClassName( 'c-Tabs_HeadItem' );
var tabBody = document.querySelector( '.c-Tabs_Body' );
var tabBodyItems = document.getElementsByClassName( 'c-Tabs_BodyItem' );
var isTabs = true;

function setTab()
{
    if ( window.matchMedia( '(min-width: 768px)' ).matches && isTabs === false )
    {
        for( var k = 0, lenK = tabBodyItems.length; k < lenK; k++ )
        {
            tabBody.appendChild( tabBodyItems[k] );
        }

        isTabs = true;
    }
    else if ( window.matchMedia( '(max-width: 767px)' ).matches && isTabs === true )
    {
        for( var l = 0, lenL = tabBodyItems.length; l < lenL; l++ )
        {
            insertAfter( tabBodyItems[l], tabHeadItems[l] );
        }

        isTabs = false;
    }
}

setTab();

var debounceSetTab = debounce(function() {
    setTab();
}, 250 );

window.addEventListener( 'resize', debounceSetTab );
巴尔玛

其原因是,getElementsByClassName返回现场 NodeList这意味着随着DOM的更改,更改的内容NodeList会反映出来。元素的顺序tabBodyItems基于它们在DOM中的位置,因此,当您在DOM中四处移动元素时,它们的索引会tabBodyItems发生变化以反映这一点。这是在循环遍历集合时发生的for,因此您跳过了元素,因为它们被重新编号了。

最简单的解决方法是使用document.querySelectorAll而不是document.getElementsByClassName这将返回一个static NodeList

function insertAfter( el, referenceNode )
{
    referenceNode.parentNode.insertBefore( el, referenceNode.nextSibling );
}

function debounce( func, wait, immediate )
{
    var timeout;

    return function() {
        var context = this, args = arguments;
        var later = function() {
            timeout = null;
            if (!immediate) func.apply(context, args);
        };
        var callNow = immediate && !timeout;
        clearTimeout(timeout);
        timeout = setTimeout(later, wait);
        if (callNow) func.apply(context, args);
    };
}

var tabHeadItems = document.querySelectorAll( '.c-Tabs_HeadItem' );
var tabBody = document.querySelector( '.c-Tabs_Body' );
var tabBodyItems = document.querySelectorAll( '.c-Tabs_BodyItem' );
var isTabs = true;

function setTab()
{
    if ( window.matchMedia( '(min-width: 768px)' ).matches && isTabs === false )
    {
        for( var k = 0, lenK = tabBodyItems.length; k < lenK; k++ )
        {
            tabBody.appendChild( tabBodyItems[k] );
        }

        isTabs = true;
    }
    else if ( window.matchMedia( '(max-width: 767px)' ).matches && isTabs === true )
    {
        for( var l = 0, lenL = tabBodyItems.length; l < lenL; l++ )
        {
            insertAfter( tabBodyItems[l], tabHeadItems[l] );
        }

        isTabs = false;
    }
}

setTab();

var debounceSetTab = debounce(function() {
    setTab();
}, 250 );

window.addEventListener( 'resize', debounceSetTab );
<div class="c-Tabs" id="js-Tabs">
    <div class="o-Container">
        <div class="o-Row c-Tabs_Head">
            <div class="o-Col-sm-4 c-Tabs_HeadItem">
                <a href="" class="c-Tabs_Link">Link 1</a>
            </div>
            <div class="o-Col-sm-4 c-Tabs_HeadItem is-active">
                <a href="" class="c-Tabs_Link">Link 2</a>
            </div>
            <div class="o-Col-sm-4 c-Tabs_HeadItem">
                <a href="" class="c-Tabs_Link">Link 3</a>
            </div>
        </div>
        <div class="c-Tabs_Body">
            <div class="c-Tabs_BodyItem" id="body1">
                <ul>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                </ul>
            </div>
            <div class="c-Tabs_BodyItem is-active" id="body2">
                <ul>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                </ul>
            </div>
            <div class="c-Tabs_BodyItem"id="body3">
                <ul>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                    <li>Lorem ipsum dolor sit amet, consectetur adipisicing elit.</li>
                </ul>
            </div>
        </div>
    </div>
</div>

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

Javascript滚动和窗口大小调整

来自分类Dev

如何控制表格内元素在窗口大小调整时浮动的顺序

来自分类Dev

窗口大小调整以准确的大小执行操作

来自分类Dev

如何根据窗口大小调整元素大小

来自分类Dev

在窗口大小调整中向元素添加类

来自分类Dev

窗口大小调整后,可可旋转元素消失

来自分类Dev

C程序的窗口大小调整会影响元素位置

来自分类Dev

窗口大小调整后,可可旋转元素消失

来自分类Dev

如何使用香草JavaScript触发窗口大小调整事件?

来自分类Dev

对象标签上的窗口大小调整事件javascript

来自分类Dev

WPF ItemsControl元素-根据窗口大小调整内容大小(锚定)

来自分类Dev

窗口大小调整时的jQuery函数

来自分类Dev

javascript图像地图大小调整问题

来自分类Dev

屏幕大小调整和元素位置调整

来自分类Dev

计算窗口大小调整时的圆圈大小

来自分类Dev

使用表单大小调整GUI元素的大小

来自分类Dev

使用表单大小调整元素宿主的子内容大小

来自分类Dev

窗口大小调整时右上浮动的Div

来自分类Dev

窗口大小调整时的开火功能

来自分类Dev

高图-窗口大小调整时边距更新

来自分类Dev

窗口右侧的元素与窗口调整大小重叠

来自分类Dev

将SVG元素的大小调整为其内容

来自分类Dev

将<video>元素的大小调整为父div

来自分类Dev

ResizeObserver:如何获取大小调整后的元素的ID?

来自分类Dev

在添加新数据后停止元素大小调整吗?

来自分类Dev

调整javaScript中的窗口大小?

来自分类Dev

JavaScript调整大小并加载,根据窗口宽度移动元素

来自分类Dev

在调整大小窗口上调整元素大小

来自分类Dev

使用“vanilla”javascript 操作动态添加的 HTML 元素

Related 相关文章

热门标签

归档