2013-08-02 13 views
9

Sto selezionando il file da openfiledialoge e visualizzandolo nella casella immagine e il suo nome nella casella di testo quando faccio clic sul pulsante delete Ricevo l'eccezione The process cannot access the file because it is being used by another process. Ho cercato molto per questa eccezione per essere risolto ma io non ha funzionato nessuno di loro lavorando, quando ho provato a chiudere il file con imagename che è in textbox cioè il file che sto visualizzando in picturebox; utilizzando IsFileLocked metodo, questo si chiude ed elimina tutti i file di particolare percorso di directory, ma come posso eliminare l'unico file mostrato in picturebox, dove sto andando maleEliminazione di file che viene visualizzato nella casella immagine

 public partial class RemoveAds : Form 
    { 
     OpenFileDialog ofd = null; 
     string path = @"C:\Users\Monika\Documents\Visual Studio 2010\Projects\OnlineExam\OnlineExam\Image\"; // this is the path that you are checking. 

     public RemoveAds() 
     { 
      InitializeComponent(); 
     } 


     private void button1_Click(object sender, EventArgs e) 
     { 
      if (System.IO.Directory.Exists(path)) 
      { 
       ofd = new OpenFileDialog(); 
       ofd.InitialDirectory = path; 
       DialogResult dr = new DialogResult(); 
       if (ofd.ShowDialog() == System.Windows.Forms.DialogResult.OK) 
       { 
        Image img = new Bitmap(ofd.FileName); 
        string imgName = ofd.SafeFileName; 
        txtImageName.Text = imgName; 
        pictureBox1.Image = img.GetThumbnailImage(350, 350, null, new IntPtr()); 
        ofd.RestoreDirectory = true; 
       } 
      } 
      else 
      { 
       return; 
      } 
     } 
private void button2_Click(object sender, EventArgs e) 
     { 
      //Image img = new Bitmap(ofd.FileName); 
      string imgName = ofd.SafeFileName; 
      if (Directory.Exists(path)) 
      { 

       var directory = new DirectoryInfo(path); 
       foreach (FileInfo file in directory.GetFiles()) 
       { if(!IsFileLocked(file)) 
        file.Delete(); 
       } 
      } 


     } 
     public static Boolean IsFileLocked(FileInfo path) 
     { 
      FileStream stream = null; 
      try 
      { //Don't change FileAccess to ReadWrite, 
       //because if a file is in readOnly, it fails. 
       stream = path.Open (FileMode.Open, FileAccess.Read, FileShare.None); 
      } 
      catch (IOException) 
      { //the file is unavailable because it is: 
       //still being written to or being processed by another thread 
       //or does not exist (has already been processed) 
       return true; 
      } 
      finally 
      { 
       if (stream != null) 
        stream.Close(); 
      } 
      //file is not locked 
      return false; 
     } 
    } 

Grazie in anticipo per qualsiasi aiuto

risposta

5

La risposta (in precedenza) ha accettato a questa domanda è pratica molto povera. Se si read the documentation su System.Drawing.Bitmap, in particolare per il sovraccarico che crea una bitmap da un file, troverete:

Il file rimane bloccato fino a quando il bitmap è disposto.

nel codice si crea la bitmap e la si memorizza in una variabile locale, ma non si dispone mai di esso quando hai finito. Ciò significa che il tuo oggetto immagine è andato fuori portata ma non ha rilasciato il blocco sul file immagine che stai tentando di eliminare. Per tutti gli oggetti che implementano IDisposable (come Bitmap), è necessario smaltirli da soli. Vedi this question per esempio (o cercane altri - questo è un concetto molto importante!).

per correggere il problema adeguatamente è sufficiente disporre dell'immagine quando si è fatto con esso:

if (ofd.ShowDialog() == System.Windows.Forms.DialogResult.OK) 
{ 
     Image img = new Bitmap(ofd.FileName); // create the bitmap 
     string imgName = ofd.SafeFileName; 
     txtImageName.Text = imgName; 
     pictureBox1.Image = img.GetThumbnailImage(350, 350, null, new IntPtr()); 
     ofd.RestoreDirectory = true; 
     img.Dispose(); // dispose the bitmap object 
} 

Si prega di non prendere il consiglio nella risposta qui sotto - si dovrebbe quasi mai bisogno di chiamare GC.Collect e se hai bisogno di farlo per far funzionare le cose, dovrebbe essere un segnale molto forte che stai facendo qualcos'altro che non va.

Inoltre, se si desidera solo eliminare il file uno (la bitmap aver visualizzato) il codice di eliminazione è sbagliato e cancellerà tutti i file nella directory e (questo è solo ripetendo il punto di Adel). Inoltre, piuttosto che tenere in vita solo per memorizzare il nome del file un OpenFileDialog oggetto globale, vorrei suggerire di sbarazzarsi di quel e salvare solo le informazioni del file:

FileInfo imageFileinfo;   //add this 
//OpenFileDialog ofd = null;  Get rid of this 

private void button1_Click(object sender, EventArgs e) 
{ 
    if (System.IO.Directory.Exists(path)) 
    { 
     OpenFileDialog ofd = new OpenFileDialog(); //make ofd local 
     ofd.InitialDirectory = path; 
     DialogResult dr = new DialogResult(); 
     if (ofd.ShowDialog() == System.Windows.Forms.DialogResult.OK) 
     { 
       Image img = new Bitmap(ofd.FileName); 
       imageFileinfo = new FileInfo(ofd.FileName); // save the file name 
       string imgName = ofd.SafeFileName; 
       txtImageName.Text = imgName; 
       pictureBox1.Image = img.GetThumbnailImage(350, 350, null, new IntPtr()); 
       ofd.RestoreDirectory = true; 
       img.Dispose(); 
     } 
     ofd.Dispose(); //don't forget to dispose it! 
    } 
    else 
    { 
     return; 
    } 
} 

Poi, nel tuo gestore secondo pulsante è possibile eliminare solo quello file che ti interessa.

 private void button2_Click(object sender, EventArgs e) 
     {     
      if (!IsFileLocked(imageFileinfo)) 
      {     
       imageFileinfo.Delete(); 
      } 
     } 
+0

Sto salvando l'immagine utilizzando un altro modulo, quindi è necessario disporre l'immagine dopo averla salvata anche o solo al momento del recupero e dell'eliminazione? – Durga

+0

@Durga Non capisco cosa intendi. Se hai un'altra domanda, pubblicare un'altra domanda è l'opzione migliore: mostra il codice di cui stai parlando. In questo caso (sopra) viene collocata la variabile locale 'img' - l'istanza dell'oggetto' Bitmap', non il file da cui è stato creato. Non lo usi più tardi perché è una variabile locale e non rientra nell'ambito. –

+0

ho capito quello che lei ha spiegato, è la risposta molto pulito e ben spiegato, ottenuto esattamente come lo shold faccio in modo corretto Grazie mille – Durga

-1

uso questo codice

string imgName = ofd.SafeFileName; 
      if (Directory.Exists(path)) 
      { 

       var directory = new DirectoryInfo(path); 
       foreach (FileInfo file in directory.GetFiles()) 
       { 
        GC.Collect(); 
        GC.WaitForPendingFinalizers(); 
         file.Delete(); 
       } 
      } 
+0

ho provato la chiusura utilizzando questo IsFileLocked (percorso FileInfo) '', ma non funziona, si può suggerire qualsiasi altro modo con cui posso chiuderlo – Durga

+0

Try This Aggiungi queste righe nel vostro codice GC .Raccogliere(); GC.WaitForPendingFinalizers(); –

+0

dopo di che la linea dovrebbe aggiungo questo nel mio codice, in modo che possa lavorare – Durga

0

vostro gestore di eventi button2_Click è il ciclismo attraverso tutti i file all'interno della cartella & fare le eliminazioni.

è necessario modificare il codice come il seguente:

public partial class RemoveAds : Form 
{ 
    OpenFileDialog ofd = null; 
    string path = @"C:\Users\Monika\Documents\Visual Studio 2010\Projects\OnlineExam\OnlineExam\Image\"; // this is the path that you are checking. 
    string fullFilePath; 

    public RemoveAds() 
    { 
     InitializeComponent(); 
    } 


    private void button1_Click(object sender, EventArgs e) 
    { 
     if (System.IO.Directory.Exists(path)) 
     { 
      ofd = new OpenFileDialog(); 
      ofd.InitialDirectory = path; 
      DialogResult dr = new DialogResult(); 
      if (ofd.ShowDialog() == System.Windows.Forms.DialogResult.OK) 
      { 
       Image img = new Bitmap(ofd.FileName); 
       string imgName = ofd.SafeFileName; 
       txtImageName.Text = imgName; 
       pictureBox1.Image = img.GetThumbnailImage(350, 350, null, new IntPtr()); 
       fullFilePath = ofd.FilePath; 
       ofd.RestoreDirectory = true; 
      } 
     } 
     else 
     { 
      return; 
     } 
    } 

    private void button2_Click(object sender, EventArgs e) 
     { 
      FileInfo file = new FileInfo(fullFilePath); 

      if(!IsFileLocked(file)) 
       file.Delete(); 
     } 


    } 

    public static Boolean IsFileLocked(FileInfo path) 
    { 
     FileStream stream = null; 
     try 
     { //Don't change FileAccess to ReadWrite, 
      //because if a file is in readOnly, it fails. 
      stream = path.Open (FileMode.Open, FileAccess.Read, FileShare.None); 
     } 
     catch (IOException) 
     { //the file is unavailable because it is: 
      //still being written to or being processed by another thread 
      //or does not exist (has already been processed) 
      return true; 
     } 
     finally 
     { 
      if (stream != null) 
       stream.Close(); 
     } 
     //file is not locked 
     return false; 
    } 
} 
+0

sì Si sta verificando per il file che è in picturebox ma ancora non sta ottenendo cancellato – Durga

+0

C'era qualche mistypes nel mio codice, si prega di controllare di nuovo il mio codice. –

0

Utilizzando GetThumnailImage devi specificare la larghezza e l'altezza che è statica. Utilizzare invece il metodo di caricamento. es .: pictureBox1.Carico (percorso dell'immagine); usando questo non avrai problemi a cancellare l'immagine o la cartella prima di chiudere l'app. non è necessario creare altri metodi. Spero che questo aiuti

Problemi correlati