我有以下示例html,有一个DIV,宽度为100% . 它包含一些元素 . 在执行窗口重新调整大小时,可以重新定位内部元素,并且div的尺寸可以改变 . 我问是否有可能挂钩div的尺寸变化事件?以及如何做到这一点?我目前将回调函数绑定到目标DIV上的jQuery resize事件,但是,没有输出控制台日志,请参见下文:
<html>
<head>
<script type="text/javascript" language="javascript" src="http://code.jquery.com/jquery-1.6.1.min.js"></script>
<script type="text/javascript" language="javascript">
$('#test_div').bind('resize', function(){
console.log('resized');
});
</script>
</head>
<body>
<div id="test_div" style="width: 100%; min-height: 30px; border: 1px dashed pink;">
<input type="button" value="button 1" />
<input type="button" value="button 2" />
<input type="button" value="button 3" />
</div>
</body>
</html>
21 回答
有一种非常有效的方法可以确定元素的大小是否已更改 .
http://marcj.github.io/css-element-queries/
该库有一个 ResizeSensor 类,可用于调整大小 .
它使用基于事件的方法,因此它会浪费CPU时间 .
例:
请不要使用jQuery onresize插件,因为它使用
setTimeout()
循环来检查更改 .THIS IS INCREDIBLY SLOW AND NOT ACCURATE .
披露:我直接与此库相关联 .
一个新标准是Resize Observer api,可在Chrome 64中使用 .
调整观察者大小
规格:https://wicg.github.io/ResizeObserver
Polyfills:https://github.com/WICG/ResizeObserver/issues/3
Firefox问题:https://bugzil.la/1272409
Safari问题:http://wkb.ug/157743
目前的支持:http://caniuse.com/#feat=resizeobserver
您必须在
window
对象上绑定resize
事件,而不是在通用html元素上绑定 .然后你可以使用这个:
在回调函数中,您可以检查
div
调用的新宽度所以,你的问题的答案是 no ,你不能将
resize
事件绑定到div .从长远来看,您将能够使用ResizeObserver .
不幸的是,许多浏览器目前默认不支持它 .
同时,您可以使用如下功能 . 因为,大多数元素大小的更改将来自窗口大小调整或来自DOM中的更改 . 您可以使用窗口的resize事件监听窗口大小调整,并且可以使用MutationObserver监听DOM更改 .
下面是一个函数的示例,当提供的元素的大小因这些事件中的任何一个而发生更改时,它将回调您:
看看这个http://benalman.com/code/projects/jquery-resize/examples/resize/
它有各种例子 . 尝试调整窗口大小,看看容器元素中的元素是如何调整的 .
Example with js fiddle to explain how to get it work.
看看这个小提琴http://jsfiddle.net/sgsqJ/4/
因为resize()事件绑定到具有类“test”的元素以及窗口对象和窗口对象$(' . test')的resize回调中 . 调用resize() .
例如
最好的解决方案是使用所谓的 Element Queries . 但是,它们不是标准的,没有规范存在 - 唯一的选择是使用其中一个可用的polyfill /库,如果你想这样做的话 .
元素查询背后的想法是允许页面上的某个容器响应提供给它的空间 . 这将允许编写一次组件,然后将其放在页面的任何位置,同时将其内容调整为当前大小 . No matter what the Window size is. 这是我们在元素查询和媒体查询之间看到的第一个区别 . 每个人都希望在某些时候创建一个规范来标准化元素查询(或实现相同目标的东西),并使它们本机,干净,简单和健壮 . 大多数人都认为媒体查询非常有限,无法帮助进行模块化设计和真正的响应 .
有一些polyfill /库以不同的方式解决问题(虽然可以称为解决方法而不是解决方案):
CSS元素查询 - https://github.com/marcj/css-element-queries
BoomQueries - https://github.com/BoomTownROI/boomqueries
eq.js - https://github.com/Snugug/eq.js
ElementQuery - https://github.com/tysonmatanich/elementQuery
还有一些,我可以自由搜索 . 我不能说哪个当前可用的选项是最好的 . 你必须尝试一些并做出决定 .
我已经看到了提出类似问题的其他解决方案 . 通常他们使用计时器或窗口/视口大小,这不是一个真正的解决方案 . 此外,我认为理想情况下这应该主要在CSS中解决,而不是在javascript或html中 .
当MarcJ的解决方案没有找到时,我发现这个库可以工作:
https://github.com/sdecima/javascript-detect-element-resize
它非常轻巧,可以通过CSS或简单的HTML加载/渲染来检测自然调整大小 .
代码示例(取自链接):
ResizeSensor.js是一个巨大的库,但我把它减少到 THIS .
泡泡袖:
如何使用它:
我不建议使用setTimeout()hack,因为它会降低性能!相反,您可以使用DOM mutation observers来收听Div大小更改 .
JS:
HTML:
这是小提琴https://jsfiddle.net/JerryGoyal/uep7nse1/
尝试更改div大小 .
您可以在debounce方法中进一步包装您的方法以提高效率 .
debounce
将每x毫秒触发您的方法,而不是每毫秒触发DIV正在调整大小 .只有window对象生成“resize”事件 . 唯一的方法我知道要做你想做的是运行一个定期检查大小的间隔计时器 .
您可以在调整大小时使用
iframe
或object
使用contentWindow
或contentDocument
. 没有setInterval
或setTimeout
步骤:
将元素位置设置为
relative
在透明的绝对隐藏IFRAME中添加
收听
IFRAME.contentWindow
-onresize
事件HTML的一个例子:
The Javascript:
运行示例
JsFiddle:https://jsfiddle.net/qq8p470d/
查看更多:
Clay - 它基于
element-resize-event
element-resize-event
这篇博文有助于我有效地检测DOM元素的大小变化 .
http://www.backalleycoder.com/2013/03/18/cross-browser-event-based-element-resize-detection/
如何使用此代码...
示例使用的打包代码......
注意:AppConfig是我用于组织可重用函数的命名空间/对象 . 您可以随意搜索并替换您想要的任何名称 .
我的jQuery插件在所有元素上启用"resize"事件而不仅仅是
window
.https://github.com/dustinpoissant/ResizeTriggering
使用Clay.js(https://github.com/zzarcon/clay),检测元素大小的变化非常简单:
您可以尝试以下代码段中的代码,它使用普通的javascript来满足您的需求 . (运行代码段并单击整页链接以触发警告,如果要测试div,则调整div的大小 . ) .
你也可以查看fiddle
UPDATE
更新Fiddle
这几乎是最佳答案的精确副本,但它不是链接,而是代码中重要的部分,转换为IMO更易读,更易于理解 . 其他一些小改动包括使用cloneNode(),而不是将html放入js字符串 . 小东西,但你可以按原样复制和粘贴它,它会工作 .
它的工作方式是让两个不可见的div填充你正在观看的元素,然后在每个元素中放置一个触发器,并设置一个滚动位置,如果大小改变,将导致触发滚动更改 .
所有真正的功劳都归功于Marc J,但如果你只是在寻找相关的代码,那么它是:
使用 Bharat Patil 回答只需在绑定回调中返回false以防止最大堆栈错误,请参阅下面的示例:
规范中仅存在
Window.onResize
,但您始终可以使用IFrame
在DIV中生成新的Window
对象 .请检查answer . 有一个新的小jquery plugin,便携且易于使用 . 您可以随时查看源代码以了解它是如何完成的 .
我认为它无法在高度和宽度上工作 . 只有5行纯javascript(确定它甚至可以更短)http://codepen.io/anon/pen/eNyyVN