원저자: Thijs van der Vossen
이 글은 2010년 10월 25일에 작성된 "모바일 사파리 이미지 리소스 제한을 해결하는 방법"을 번역한 것입니다. 일부 제한사항이 더 이상 적용되지 않을 수 있습니다.
이 글을 번역한 목적은 "Zepto 소스 코드 자산 모듈 읽기"의 부록입니다. Zepto 소스 코드를 읽는 일련의 글이 github에 올려져 있습니다. Welcome to star: reading-zepto
텍스트 시작:
Ipad
및 Iphone
의 사용 가능한 메모리로 제한되는 Safari
브라우저의 모바일 버전은 데스크톱 버전보다 리소스 사용 제한이 더 엄격합니다Ipad
和 Iphone
的可用内存,Safari
浏览器的移动端会比桌面端有着更严格的资源使用限制
其中之一是每个 HTML
页面的图片数据总量。当移动端的 Safari
浏览器加载了 8
到 10MB
的图片数据后,就会停止加载其他图片,甚至浏览器还会崩溃。
大多数网站都不会受到这条限制的影响,因为保持页面合理的大小通常是一种很聪明的做法。
但是,在下面的场景中,你可能会遇到麻烦,如大型的图片画廊和幻灯片,或者是异步加载新数据的 web
应用,例如模拟不同版块切换时的原生动画(是的,你可以用移动端 Safari
模拟 Flipboard
的切换效果 )。
我们有充足的理由相信,只通过删除不再需要的图片元素,就可以不受这条限制的影响:
var img = document.getElementById('previous'); img.parentNode.removeChild(img);
但是然并卵,因为某些原因,将图片从 DOM
(或者一个包含图片的元素)中删除时,图片的真实数据并没有释放。真是头大啊!
而将图片的 src
属性设置为其他的(更小的)图片链接,却起到了作用。
var img = document.getElementById('previous'); img.src = 'images/empty.gif';
替换掉 src
属性后,旧的图片数据最终得到了释放。
我已经彻底测试过这种方法,下面几个方面是需要注意的:
将 src
属性设置为其他图片后,图片数据不会立即释放,需要一段时间让垃圾回收器来真正地释放内存。这意味着,如果你太块地插入图片,依旧可能会陷入麻烦中。
在移动端 Safari
触发限制后,即便删除一部分或者全部已经加载的数据,Safari
也不会再加载额外的图片,这种情况即便在切换到其他页面时也继续存在。这意味着在测试这项技术时,你需要经常重启 Safari
(这差点把我逼疯了)。
如果你想将图片元素从 DOM
中删除,你还必须确保在更改 src
前,元素不能为垃圾回收掉,否则,旧图片数据不会被释放。下面这个是最好的解决方案:
var img = document.getElementById('previous'); img.parentNode.removeChild(img); img.src = 'data:image/gif;base64,' + 'R0lGODlhAQABAAD/ACwAAAAAAQABAAACADs='; window.timeout(function() {img = null; }, 60000);
你可以看到,我使用了 data URI
作为替换图片。
(如果你只是删除图片元素, iPad
在加载8张图片后会停止继续加载,如果用 Zepto
的 assets
插件,会持续加载。)
在上周我和 Thomas Fuchs
解释了这项技术后,他立即将它加入了 Zepto
HTML
페이지에 있는 이미지 데이터의 총량입니다. 모바일 Safari
브라우저가 8
에서 10MB
범위의 이미지 데이터를 로드하면 다른 이미지 로드가 중지되고 브라우저가 충돌할 수도 있습니다. 🎜🎜대부분의 웹사이트는 이 제한의 영향을 받지 않습니다. 일반적으로 페이지 크기를 합리적으로 유지하는 것이 현명하기 때문입니다. 🎜🎜그러나 대규모 이미지 갤러리 및 슬라이드쇼나 다른 섹션 간 전환 시뮬레이션과 같이 새 데이터를 비동기적으로 로드하는 웹
애플리케이션과 같은 다음 시나리오에서는 문제가 발생할 수 있습니다(예, 모바일 Safari
를 사용하여 Flipboard
의 전환 효과를 시뮬레이션할 수 있습니다. 🎜🎜🎜🎜더 이상 필요하지 않은 이미지 요소를 삭제하는 것만으로도 다음을 수행할 수 있다고 믿을 만한 충분한 이유가 있습니다. 이 제한의 영향을 받습니다: 🎜rrreee🎜 그러나 어떤 이유로 DOM
(또는 이미지가 포함된 요소)에서 이미지가 삭제되면 이미지의 실제 데이터가 공개되지 않습니다. 머리가 정말 크네요! 🎜🎜이미지의 src
속성을 다른(더 작은) 이미지 링크로 설정하면 작동했습니다. 🎜rrreee🎜src
속성을 교체한 후 드디어 예전 이미지 데이터가 공개되었습니다. 🎜🎜이 방법을 철저히 테스트했으며 다음 측면에 유의해야 합니다. 🎜src
속성을 other로 설정합니다. 이미지가 촬영되면 이미지 데이터가 즉시 해제되지 않으며, 가비지 컬렉터가 실제로 메모리를 해제하는 데 시간이 걸립니다. 즉, 이미지를 너무 광범위하게 삽입하면 여전히 문제가 발생할 수 있습니다. 🎜Safari
가 제한을 실행한 후에는 로드된 데이터의 일부 또는 전체가 삭제되더라도 Safari
에서 추가 이미지를 로드하지 않습니다. , 다른 페이지로 전환해도 이 상황이 계속됩니다. 이는 이 기술을 테스트할 때 Safari
를 자주 다시 시작해야 함을 의미합니다(이것은 나를 거의 미치게 만듭니다). 🎜DOM
에서 이미지 요소를 제거하려면 src
를 변경하기 전에 해당 요소가 가비지 수집될 수 없는지 확인해야 합니다. , 이전 이미지 데이터는 공개되지 않습니다. 가장 좋은 해결책은 다음과 같습니다. 🎜data URI
를 대체 이미지로 사용했습니다. 🎜🎜🎜🎜(그림 요소만 삭제하면 iPad
는 8을 로드합니다. Pictures 이미지 로드가 중단됩니다. Zepto
의 assets
플러그인을 사용하면 계속 로드됩니다. ) 🎜🎜 Thomas Fuchs는 지난 주에 이 기술을 발견한 후 즉시 <code>Zepto
에 통합했습니다. 이번 주말에 저는 여러분이 자신을 테스트하는 데 사용할 수 있는 테스트 기능을 기고했습니다. 🎜위 내용은 Safari 모바일 단말기에서 이미지 리소스 제한을 처리하는 방법의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!