CSS媒体查询问题(滚动条)

时间:2011-11-16 04:46:14

标签: html css browser

我在Firefox中遇到css媒体查询问题。它在Chrome中工作正常,就像我制作了两个DIV并想要一个滚动条。如果我将firefox的屏幕大小减小到800px,那么两个DIV都会崩溃,并且在某些像素媒体查询工作之后,但Chrome中不会发生这种情况。

检查这个小提琴http://jsfiddle.net/RMvqC/2/

7 个答案:

答案 0 :(得分:14)

我通过调用项目负责人中的“mqGenie”javascript解决了这个问题。

现在,我的媒体查询的宽度在Chrome,Safari,Firefox和IE上运行正常(具有相同的值),有或没有scroolbars。

此javascript在浏览器中调整CSS媒体查询,这些浏览器在视口宽度中包含滚动条宽度,以便按预期大小触发。

您可以从此网址下载:

http://stowball.github.io/mqGenie/

答案 1 :(得分:7)

Firefox& Opera遵循W3C规范,其中包括媒体查询宽度中的滚动条宽度(原因可能是避免a comment here中描述的无限循环),而Webkit没有(可能因为它们认为没有意义)

有一个解决方法(我只在FF上测试过这个),显然如果你强制滚动条一直可见,那么宽度现在将与Webkit一致。这是代码:

html
{
   overflow:hidden;
   height:100%;
}
body
{
   position:relative;
   overflow-y:scroll;
   height:100%;
   -webkit-overflow-scrolling:touch; /* So iOS Safari gets the inertia & rubber-band effect */
}

如果你想将它应用于FF&只有Opera,你可以使用CSS hacks:

/* Firefox */
@-moz-document url-prefix()
{
    html
    {
        overflow:hidden;
        height:100%;
    }
    body
    {
        position:relative;
        overflow-y:scroll;
        height:100%;
        /*-webkit-overflow-scrolling:touch;*/
    }
}

/* Opera */
x:-o-prefocus, html
{
    overflow:hidden;
    height:100%;
}
x:-o-prefocus, body
{
    position:relative;
    overflow-y:scroll;
    height:100%;
}

不言而喻,需要注意的是滚动条始终可见,这可能是一个妥协。

答案 2 :(得分:6)

Firefox&基于Webkit的浏览器以不同方式呈现滚动条。在Firefox中,MediaQuery认为滚动条的宽度与屏幕宽度相差15px,但在基于Webkit的浏览器中,它不被视为具有屏幕宽度的滚动条。所以,这就是浮动的DIV在Firefox中崩溃的原因。

我用css做了一些东西可能对你有所帮助。 (查看this fiddle

        html {
            /* force scrollbars */
            height: 101%;
        }
        body {
            margin: 0; 
            padding:0; 
            white-space:nowrap; 
        }  
        #box1,
        #box2 {
            display:inline-block;
            width: 400px;
            height: 200px;  
            vertical-align:top;
            white-space:normal;
        }
        #box1 {
            background: #ce0000;
             margin-right:-5px;
        }
        #box2 {
            background: #8e0000;
        }

        @media screen and (max-width: 799px) { 
            body { 
                white-space:normal; 
            }
            #box1,
            #box2 {
                width: 300px;
            }
        }

答案 3 :(得分:0)

您可以使用CSS-hack轻松实现Firefox的解决方案。将您的内容包装在额外的<div>之后,将这些行添加到您的CSS中:

/* Firefox-Hack */
body,  x:-moz-any-link {
    overflow-x: hidden;
}
#wrapper,  x:-moz-any-link {
    margin: 0 -7.5px;
}

检查jsbin(现在是jsfiddle)

要获得更丰富的响应体验,您可以添加其他媒体查询:another jsbin

paulirish.com

找到了CSS-hack

答案 4 :(得分:0)

这与外围有关,但我找到了一种方法来检测浏览器在任何给定时刻实际使用的媒体查询,而不必使用滚动条和主体宽度...

基本上,在你身体的某个地方定义一个绝对定位的1 x 1像素大小的列表,每个媒体查询条件都有一个列表项,你想要“可观看”。

然后在每个媒体查询定义中,显示/隐藏相应的列表项,然后只需检查该项是否在脚本中可见。

示例:

<body>
    ...
    <ul id="mediaQueryHelper">
        <li id="desktop"></li>
    </ul>
</body>

<style type="text/less">
    #mediaQueryHelper {
        position: absolute;
        height: 1px;
        width: 1px;
        visibility: hidden;
        top: -999px;
        left: -999px;
    }

    @media screen and (min-width: 481px)
    {
       #desktop { display: inline; }
    }

    @media screen and (min-width: 320px) and (max-width: 480px)
    {
       #desktop{ display: none; }
    }

</style>

<script type="text/javascript">
    $(document).ready(function()
    {
        var _desktop = $("#desktop");

        $(window).resize(function() {
            console.log("media-query mode: " + _desktop.is(":visible") ? "DESKTOP" : "MOBILE");
        });
    });
</script>

答案 5 :(得分:0)

安全玩!

我的最终策略是向媒体查询添加20px,这是我在版式上的默认空白。

一个例外:parseString(data, { explicitArray: false }, (error, result) => { if (error) { throw new Error(error); } else { res = result; console.log(result); } }); ,在这种尺寸下,请不要离开20px的空白,并再添加一条规则来解决较小的背景问题:

@media (min-width: 320px)

20px是滚动条的默认宽度大小。

仅供参考:example

答案 6 :(得分:0)

简短答案

如果您不想一直显示滚动条,请将内容包装到<div>元素等中。可以在显示滚动条时使用JavaScript向所有媒体查询添加特定值。

// check whether scrollbar is visible
var isScrollbarVisible = window.innerWidth > document.documentElement.clientWidth;

// search for media rule
var mediaRule = document.styleSheets[i].cssRules[j];

// update media rule
mediaRule.media.mediaText = '..'


长答案

我写了一个小脚本,您可以将其包含在页面中。它检测何时调整窗口大小,并在需要时更改所有媒体查询。 css变量--replace-media-scrollbar的值用作滚动条的宽度;如果找不到值,则使用15px。这适用于媒体查询withmin-widthmax-widthheightmin-heightmax-height,即使它们使用{{1 }}。

JavaScript:

and

可选CSS:

function* visitCssRule(cssRule) {
    // visit imported stylesheet
    if (cssRule.type == cssRule.IMPORT_RULE)
        yield* visitStyleSheet(cssRule.styleSheet);

    // yield media rule
    if (cssRule.type == cssRule.MEDIA_RULE)
        yield cssRule;
}

function* visitStyleSheet(styleSheet) {
    try {
        // visit every rule in the stylesheet
        var cssRules = styleSheet.cssRules;
        for (var i = 0, cssRule; cssRule = cssRules[i]; i++)
            yield* visitCssRule(cssRule);
    } catch (ignored) {}
}

function* findAllMediaRules() {
    // visit all stylesheets
    var styleSheets = document.styleSheets;
    for (var i = 0, styleSheet; styleSheet = styleSheets[i]; i++)
        yield* visitStyleSheet(styleSheet);
}

// collect all media rules
const mediaRules = Array.from(findAllMediaRules());

// read scrollbar width
var style = getComputedStyle(document.documentElement);
var scrollbar = style.getPropertyValue('--replace-media-scrollbar') || '15px';

// update media rules
if (scrollbar != '0px') {
    var oldValue = '0px';
    function updateMediaRulesScrollbar() {
        var newValue = window.innerWidth > document.documentElement.clientWidth ? scrollbar : '0px';
        // if value changed
        if (oldValue != newValue) {
            for (var i = 0, mediaRule; mediaRule = mediaRules[i]; i++) {
                var regex = RegExp('\\((width|min-width|max-width|height|min-height|max-height): (calc\\([^)]*\\)|[^)]*)\\)', 'g');
                var replacement = '($1: calc($2 - ' + oldValue + ' + ' + newValue + '))';
                mediaRule.media.mediaText = mediaRule.media.mediaText.replace(regex, replacement);
                console.log(mediaRule);
            }
        }
        oldValue = newValue;
    }
    updateMediaRulesScrollbar();
    window.onresize = updateMediaRulesScrollbar;
}