2009-10-08 13 views
7

Qualche tempo fa ho postato una domanda relativa a una perdita di memoria WriteableBitmap, e sebbene abbia ricevuto suggerimenti meravigliosi relativi al problema, continuo a pensare che ci sia un bug grave/(errore da parte mia)/(Confusione)/(qualche altra cosa) qui.Come smaltire una bitmap scrivibile? (WPF)

Così, qui è il mio problema ancora:

Supponiamo di avere un applicazione WPF con un'immagine e un pulsante. La sorgente dell'immagine è una bitmap veramente grande (3600 * 4800 px), quando viene mostrata a runtime l'applicaton consuma ~ 90 MB.

Ora supponiamo di voler istanziare un WriteableBitmap dalla sorgente dell'immagine (l'immagine veramente grande), quando ciò accade le applicazioni consumano ~ 220 MB.

Ora arriva la parte difficile, quando le modifiche all'immagine (tramite WriteableBitmap) terminano e tutti i riferimenti a WriteableBitmap (almeno quelli di cui sono a conoscenza) vengono distrutti (alla fine di un metodo oppure impostandoli su null) la memoria utilizzata da writeableBitmap dovrebbe essere liberata e l'utilizzo dell'applicazione dovrebbe tornare a ~ 90 MB. Il problema è che a volte ritorna, a volte no.

Ecco un esempio di codice:

// The Image's source whas set previous to this event 
private void buttonTest_Click(object sender, RoutedEventArgs e) 
    { 
     if (image.Source != null) 
     { 
      WriteableBitmap bitmap = new WriteableBitmap((BitmapSource)image.Source); 

      bitmap.Lock(); 

      bitmap.Unlock(); 

      //image.Source = null; 
      bitmap = null; 
     } 
    } 

Come si può vedere il riferimento è locale e la memoria dovrebbe essere rilasciato alla fine del metodo (o quando il garbage collector decide di farlo). Tuttavia, l'app potrebbe consumare ~ 224 MB fino alla fine dell'universo.

Qualsiasi aiuto sarebbe fantastico.

risposta

0

È necessario rendere l'immagine Bitmap alla stessa risoluzione e pixel? È possibile creare writeablebitmap con un numero di pixel molto più basso e chiamare il metodo di rendering. Poiché writeablebitmap contiene un riferimento agli uielementi originali quando si chiama il rendering, in questo caso si avranno 3 blocchi: 1) originale uielement, 2) pixel in writeablemapmap, 3) riferimento all'originale copiato.

Ho avuto un problema simile con il WriteableBitmap in termini di perdite di memoria ed ho riparato a check-out questo link: http://www.wintellect.com/CS/blogs/jprosise/archive/2009/12/17/silverlight-s-big-image-problem-and-what-you-can-do-about-it.aspx

Se si crea un altro WriteableBitmap e copiare i pixel sopra, quindi smaltire il primo WriteableBitmap dovresti vedere qualche rilascio di memoria, almeno lo ho fatto nel mio scenario.