Trascina i file in WPF


106

Devo rilasciare un file immagine nella mia applicazione WPF. Al momento ho un evento che si attiva quando inserisco i file, ma non so come fare dopo. Come ottengo l'immagine? L' senderoggetto è l'immagine o il controllo?

private void ImagePanel_Drop(object sender, DragEventArgs e)
{
    //what next, dont know how to get the image object, can I get the file path here?
}

Risposte:


211

Questo è fondamentalmente quello che vuoi fare.

private void ImagePanel_Drop(object sender, DragEventArgs e)
{

  if (e.Data.GetDataPresent(DataFormats.FileDrop))
  {
    // Note that you can have more than one file.
    string[] files = (string[])e.Data.GetData(DataFormats.FileDrop);

    // Assuming you have one file that you care about, pass it off to whatever
    // handling code you have defined.
    HandleFileOpen(files[0]);
  }
}

Inoltre, non dimenticare di collegare effettivamente l'evento in XAML, oltre a impostare l' AllowDropattributo.

<StackPanel Name="ImagePanel" Drop="ImagePanel_Drop" AllowDrop="true">
    ...
</StackPanel>

awesome funziona un fascino, basta scambiare "HandleFileOpen (files [0]);" a "foreach (string file in files) {Openfile (file);}" - Grazie :)
Eamonn McEvoy

1
Scusa :) Voglio dire che il drag & drop non funziona. AllowDropè impostato su True ma il Dropgestore eventi non viene mai chiamato. Quando trascino un file sulla finestra, vedo un simbolo circolare "negato"
mcont

4
Ho usato un Gridelemento come radice, con un Borderinterno con la Backgroundproprietà impostata su qualcosa (il bianco va bene, ma non trasparente). All'interno Borderho inserito il contenuto effettivo.
mcont

1
L'impostazione dello sfondo su trasparente ha funzionato bene per me quando ho provato a rilasciare su una griglia. Apparentemente hai bisogno di uno sfondo in modo che l'hit test avvenga. Grazie a questo post del blog: codeinreview.com/136/enabling-drag-and-drop-over-a-grid-in-wpf
DustinA

1
Un vero problema è che se esegui VisualStudio come amministratore, esegui il debug della tua app e trascini da FileExplorer come non amministratore, il contesto di sicurezza è diverso e non si attiverà alcun evento di trascinamento. Mi è costato 30 minuti di vita.
Hans Karlsen,

35

Il file immagine è contenuto nel eparametro, che è un'istanza della DragEventArgsclasse .
(Il senderparametro contiene un riferimento all'oggetto che ha generato l'evento.)

In particolare, controlla il e.Datamembro ; come spiega la documentazione, questo restituisce un riferimento all'oggetto dati ( IDataObject) che contiene i dati dall'evento di trascinamento.

L' IDataObjectinterfaccia fornisce una serie di metodi per recuperare l'oggetto dati che stai cercando. Probabilmente vorrai iniziare chiamando il GetFormatsmetodo per scoprire il formato dei dati con cui stai lavorando. (Ad esempio, è un'immagine reale o semplicemente il percorso di un file immagine?)

Quindi, una volta identificato il formato del file trascinato, chiamerai uno degli overload specifici del GetDatametodo per recuperare effettivamente l'oggetto dati in un formato particolare.


12

Oltre alla risposta di AR, tieni presente che se vuoi usare il TextBoxdrop devi sapere quanto segue.

TextBoxsembra avere già una gestione predefinita per DragAndDrop. Se il tuo oggetto dati è un String, funziona semplicemente. Altri tipi non vengono gestiti e ottieni l' effetto del mouse Proibito e il tuo gestore di Drop non viene mai chiamato.

Sembra che tu possa abilitare la tua gestione con e.Handleda true in un PreviewDragOvergestore di eventi.

XAML

<TextBox AllowDrop="True"    x:Name="RtbInputFile"      HorizontalAlignment="Stretch"   HorizontalScrollBarVisibility="Visible"  VerticalScrollBarVisibility="Visible" />

C #

RtbInputFile.Drop += RtbInputFile_Drop;            
RtbInputFile.PreviewDragOver += RtbInputFile_PreviewDragOver;

private void RtbInputFile_PreviewDragOver(object sender, DragEventArgs e)
{
    e.Handled = true;
}

private void RtbInputFile_Drop(object sender, DragEventArgs e)
{
     if (e.Data.GetDataPresent(DataFormats.FileDrop))
     {
                // Note that you can have more than one file.
                string[] files = (string[])e.Data.GetData(DataFormats.FileDrop);
                var file = files[0];                
                HandleFile(file);  
     }
}

1
Nell'esempio di AR manca il gestore PreviewDragOver, che è piuttosto importante per far sì che tutto si unisca. Complimenti.
Greg Vogel
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.