SORU
6 HAZİRAN 2010, Pazar


iPad/tarayıcı Javascript resim yüklerken kilitlenen iPhone

İPad fotoğraf uygulaması taklit eden Safari bir resim galerisi yapmaya çalışıyorum. Mükemmel, bir keresinde 6 MB veya daha fazla değer görüntülerin de DOM ekleyerek veya yeni bir Resim nesneleri, yeni görüntüler ya da durdurmak yükleme veya tarayıcı çöküyor oluşturarak yük dışında çalışır. Bu sorun, suçlu olarak Javascript kodu eledim kadar yaygındır herkes aynı sınıra karşı vuruyor.

-Tarayıcı Medya Oynatıcı ile bir öğe birkaç MB daha fazla aktarabilirsiniz verilen ya, bu sınırı gereksiz ve geçici çözüm kullanılabilir bir tür olmalı. Belki de bellek ya da başka bir şey boşaltarak.

Ben de reference for UIWebView Bu rastladı.

"JavaScript ayırmalarını da 10 MB ile sınırlıdır. Safari JavaScript için toplam bellek ayırma bu sınırı aşarsanız, bir özel durum oluşturur."

Oldukça iyi görüyorum ne de maçlar. Ayırması mümkün nesneleri Javascript içinde mi, ya da Safari/çalışan toplam tutmak ve asla bırakmaz UİWebView mu? Alternatif olarak, veri olarak başka bir şekilde yüklemek için herhangi bir çözüm bu 10MB ye değil mi?

CEVAP
16 Temmuz 2010, Cuma


Güncelleme: bunu yapmanın daha kolay bir yolu yok sanırım, uygulamanıza bağlı olarak. Yerine sahip birden fazla görüntü, Eğer sadece bir tane <img> element veya Image nesne (ya da belki iki, bir 'bu' görüntü ve bir sonraki görüntü Eğer ihtiyacınız animasyonlar veya geçişler) ve sadece update .src, .width, .height ve bu yüzden, asla elde yakın 10MB sınırı. Eğer carousel bir uygulama yapmak istersen, küçük tutucuları ilk kullanırdın. Bu tekniği uygulamak için daha kolay olabilir bulabilirsiniz.


Aslında bir iş-etrafında bu bulmuş olabilir düşünüyorum.

Temelde, biraz daha derin bir görüntü yönetimi ve açıkça ihtiyacın yok, herhangi bir resmi küçültmek gerekir. Normalde document.removeChild(divMyImageContainer) $("myimagecontainer").empty() ya da ne yaptığını, ama Mobil Safari bu kesinlikle hiçbir şey yapmaz kullanarak bunu yapmak istiyorum; tarayıcı sadece asla belleği kaldırır.

Bunun yerine, çok az bellek alır, böylece görüntü kendisini güncellemesi gerekiyor; ve src öznitelik görüntü değiştirerek bunu yapabilirsin. data URL kullanmak için bunu yapmak için bildiğim en hızlı yolu. Bu söyleyeceğim diye yerine:

myImage.src="/path/to/image.png"

onun yerine bunu söylüyorlar:

myImage.src="data:image/gif;base64,AN_ENCODED_IMAGE_DATA_STRING"

Aşağıda çalışıyor göstermek için bir test. Benim testlerde, büyük 750KB benim görüntü sonunda tarayıcı öldürmek ve tüm JS exectution durdurmak olacaktır. Ama src, sıfırlama sonra bende 170 kez resmi durumlarda yüklemek mümkün oldu. Kodu nasıl çalıştığı hakkında bir açıklama da aşağıda.

var strImagePath = "http://path/to/your/gigantic/image.jpg";
var arrImages = [];
var imgActiveImage = null
var strNullImage = "data:image/gif;base64,R0lGODlhEAAOALMAAOazToeHh0tLS/7LZv/0jvb29t/f3//Ub//ge8WSLf/rhf/3kdbW1mxsbP//mf///yH5BAAAAAAALAAAAAAQAA4AAARe8L1Ekyky67QZ1hLnjM5UUde0ECwLJoExKcppV0aCcGCmTIHEIUEqjgaORCMxIC6e0CcguWw6aFjsVMkkIr7g77ZKPJjPZqIyd7sJAgVGoEGv2xsBxqNgYPj/gAwXEQA7";
var intTimesViewed = 1;
var divCounter = document.createElement('h1');
document.body.appendChild(divCounter);

var shrinkImages = function() {
    var imgStoredImage;
    for (var i = arrImages.length - 1; i >= 0; i--) {
        imgStoredImage = arrImages[i];
        if (imgStoredImage !== imgActiveImage) {
            imgStoredImage.src = strNullImage;
        }
    }
};
var waitAndReload = function() {
    this.onload = null;
    setTimeout(loadNextImage,2500);
};
var loadNextImage = function() {
    var imgImage = new Image();
    imgImage.onload = waitAndReload;
    document.body.appendChild(imgImage);
    imgImage.src = strImagePath   "?"   (Math.random() * 9007199254740992);
    imgActiveImage = imgImage;
    shrinkImages()
    arrImages.push(imgImage);
    divCounter.innerHTML = intTimesViewed  ;
};
loadNextImage()

Bu kodu kendi kurallarını uygulamak için nasıl anlamaya gerekir, bu yüzden benim çözüm test etmek için yazılmıştır. Kodu aşağıda anlatacağım üç parça geliyor, ama gerçekten önemli tek parçası imgStoredImage.src = strNullImage;

loadNextImage() yeni bir görüntü yükler ve shrinkImages() çağırır. Bu da başka bir resim yükleme işlemini başlatmak için kullanılır (hata: daha sonra bu olay, ama değilim) takas etmeliyim ki onload bir olay atar.

waitAndReload() burada sadece görüntüsü ekran üzerinde göstermek için izin vermektir. Mobile Safari çok yavaş ve büyük bir resim görüntüleme, görüntü ekranı boyamak için yüklendikten sonra zamana ihtiyacı vardır.

shrinkImages() daha önce yüklenen tüm fotoğraflar (active hariç) geçer ve dataurl adresi .src değişiklikler.

Dataurl burada (bulabildiğim ilk dataurl görüntü için bir dosya klasörü bir görüntü kullanıyorum. Sadece senaryonun iyi görebilmeniz için kullanıyorum. Bu veriler, url dizesi kullanın böylece muhtemelen şeffaf bir gif yerine kullanmak isteyeceksiniz,: data:image/gif;base64,R0lGODlhAQABAIAAAP///wAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw==

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • efaustus9

    efaustus9

    16 HAZİRAN 2006
  • LearnKey

    LearnKey

    19 AĞUSTOS 2008