/// <summary> /// Adds a new ReceivedFile to the list box data context /// </summary> /// <param name="file"></param> private void AddNewReceivedItem(ReceivedFile file) { //Use dispatcher incase method is not called from GUI thread lbReceivedFiles.Dispatcher.BeginInvoke(new Action(() => { receivedFiles.Add(file); })); }
/// <summary> /// Save the selected file to disk /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void SaveFile_Clicked(object sender, RoutedEventArgs e) { Button cmd = (Button)sender; if (cmd.DataContext is ReceivedFile) { //Use a SaveFileDialog to request the save location ReceivedFile fileToSave = (ReceivedFile)cmd.DataContext; SaveFileDialog saveDialog = new SaveFileDialog(); saveDialog.FileName = fileToSave.Filename; //If the user selected to save the file we write it to disk if (saveDialog.ShowDialog() == true) { fileToSave.SaveFileToDisk(saveDialog.FileName); AddLineToLog("Saved file '" + fileToSave.Filename + "' from '" + fileToSave.SourceInfoStr + "'"); } } }
/// <summary> /// Delete the selected ReceivedFile from the application /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void DeleteFile_Clicked(object sender, RoutedEventArgs e) { Button cmd = (Button)sender; if (cmd.DataContext is ReceivedFile) { ReceivedFile fileToDelete = (ReceivedFile)cmd.DataContext; lock (syncRoot) { //Delete the ReceivedFile from the listbox data context receivedFiles.Remove(fileToDelete); //Delete the ReceivedFile from the internal cache if (receivedFilesDict.ContainsKey(fileToDelete.SourceInfo)) { receivedFilesDict[fileToDelete.SourceInfo].Remove(fileToDelete.Filename); } fileToDelete.Close(); } AddLineToLog("Deleted file '" + fileToDelete.Filename + "' from '" + fileToDelete.SourceInfoStr + "'"); } }
/// <summary> /// Handles an incoming packet of type 'PartialFileDataInfo' /// </summary> /// <param name="header">Header associated with incoming packet</param> /// <param name="connection">The connection associated with incoming packet</param> /// <param name="data">The incoming data automatically converted to a SendInfo object</param> private void IncomingPartialFileDataInfo(PacketHeader header, Connection connection, SendInfo info) { try { byte[] data = null; ReceivedFile file = null; //Perform this in a thread safe way lock (syncRoot) { //Extract the packet sequence number from the header //The header can also user defined parameters long sequenceNumber = info.PacketSequenceNumber; if (incomingDataCache.ContainsKey(connection.ConnectionInfo) && incomingDataCache[connection.ConnectionInfo].ContainsKey(sequenceNumber)) { //We already have the associated data in the cache data = incomingDataCache[connection.ConnectionInfo][sequenceNumber]; incomingDataCache[connection.ConnectionInfo].Remove(sequenceNumber); //Check to see if we have already received any files from this location if (!receivedFilesDict.ContainsKey(connection.ConnectionInfo)) { receivedFilesDict.Add(connection.ConnectionInfo, new Dictionary <string, ReceivedFile>()); } //Check to see if we have already initialised this file if (!receivedFilesDict[connection.ConnectionInfo].ContainsKey(info.Filename)) { receivedFilesDict[connection.ConnectionInfo].Add(info.Filename, new ReceivedFile(info.Filename, connection.ConnectionInfo, info.TotalBytes)); AddNewReceivedItem(receivedFilesDict[connection.ConnectionInfo][info.Filename]); } file = receivedFilesDict[connection.ConnectionInfo][info.Filename]; } else { //We do not yet have the necessary data corresponding with this SendInfo so we add the //info to the cache if (!incomingDataInfoCache.ContainsKey(connection.ConnectionInfo)) { incomingDataInfoCache.Add(connection.ConnectionInfo, new Dictionary <long, SendInfo>()); } incomingDataInfoCache[connection.ConnectionInfo].Add(sequenceNumber, info); } } //If we have everything we need we can add data to the ReceivedFile if (data != null && file != null && !file.IsCompleted) { file.AddData(info.BytesStart, 0, data.Length, data); //Perform a little clean-up file = null; data = null; GC.Collect(); } else if (data == null ^ file == null) { throw new Exception("Either both are null or both are set. Data is " + (data == null ? "null." : "set.") + " File is " + (file == null ? "null." : "set.") + " File is " + (file.IsCompleted ? "completed." : "not completed.")); } } catch (Exception ex) { //If an exception occurs we write to the log window and also create an error file AddLineToLog("Exception - " + ex.ToString()); LogTools.LogException(ex, "IncomingPartialFileDataInfo"); } }