Windows: Add filedrop class

This commit is contained in:
Jonathan Jenne 2022-02-10 16:56:12 +01:00
parent 607f7e6445
commit c39d0ea794
2 changed files with 352 additions and 0 deletions

313
Windows/FileDrop.vb Normal file
View File

@ -0,0 +1,313 @@
Imports System.Text
Imports DigitalData.Modules.Base
Imports DigitalData.Modules.Logging
Imports DigitalData.Modules.Language.Utils
Imports Microsoft.Office.Interop
Imports System.Windows
Public Class FileDrop
Inherits BaseClass
Public Enum FileFormat
OutlookAttachment
OutlookMail
ThunderbirdAttachment
ThunderbirdMail
MailWithoutAttachments
LocalFile
Unknown
End Enum
Public Enum FileSource
DragDrop
FolderWatch
Attachment
End Enum
Public Class DroppedFile
Public ReadOnly Property FilePath As String
Public Property FileFormat As FileFormat
Public Property FileSource As FileSource = FileSource.DragDrop
Public Sub New(pFilePath As String)
FilePath = pFilePath
End Sub
Public Sub New(pFilePath As String, pDropType As String)
MyClass.New(pFilePath)
Select Case pDropType
Case "LOCAL_FILE" ' "|DROPFROMFSYSTEM|"
FileFormat = FileFormat.LocalFile
Case "OUTLOOK_ATTACHMENT" ' "|OUTLOOK_ATTACHMENT|"
FileFormat = FileFormat.OutlookAttachment
Case "OUTLOOK_MAIL" ' "|OUTLOOK_MESSAGE|"
FileFormat = FileFormat.OutlookMail
Case "|MSGONLY|"
FileFormat = FileFormat.MailWithoutAttachments
Case "|FW_OUTLOOK_MESSAGE|"
FileFormat = FileFormat.OutlookMail
FileSource = FileSource.FolderWatch
Case "|FW_SIMPLEINDEXER|"
FileFormat = FileFormat.LocalFile
FileSource = FileSource.FolderWatch
Case "|ATTMNTEXTRACTED|"
FileFormat = FileFormat.LocalFile
FileSource = FileSource.Attachment
End Select
End Sub
End Class
Public Sub New(pLogConfig As LogConfig)
MyBase.New(pLogConfig)
End Sub
Public Function GetFileFormat(pEvent As DragEventArgs) As FileFormat
If IsThunderbird(pEvent) Then
If IsThunderbirdAttachment(pEvent) Then
Return FileFormat.ThunderbirdAttachment
ElseIf IsThunderbirdMail(pEvent) Then
Return FileFormat.ThunderbirdMail
Else
Return FileFormat.Unknown
End If
End If
If IsOutlook(pEvent) Then
If IsOutlookAttachment(pEvent) Then
Return FileFormat.OutlookAttachment
ElseIf IsOutlookMail(pEvent) Then
Return FileFormat.OutlookMail
Else
Return FileFormat.Unknown
End If
End If
If IsNormalFile(pEvent) Then
Return FileFormat.LocalFile
Else
Return FileFormat.Unknown
End If
End Function
Public Function GetFilePaths(pEvent As DragEventArgs) As List(Of DroppedFile)
Try
Dim oFormat = GetFileFormat(pEvent)
Dim oFiles As New List(Of DroppedFile)
Select Case oFormat
Case FileFormat.OutlookAttachment, FileFormat.OutlookMail
Dim oFilePaths = GetOutlookFilePath(pEvent)
For Each oPath In oFilePaths
oFiles.Add(New DroppedFile(oPath) With {
.FileFormat = oFormat
})
Next
Case Else
Dim oDroppedFiles As String() = GetFormat(pEvent, "FileDrop")
If oDroppedFiles IsNot Nothing Then
For Each oPath In oDroppedFiles
oFiles.Add(New DroppedFile(oPath) With {
.FileFormat = oFormat
})
Next
End If
End Select
Return oFiles
Catch ex As Exception
Logger.Error(ex)
Return Nothing
End Try
End Function
Private Function GetOutlookFilePath(pEvent As DragEventArgs) As List(Of String)
Dim oTempPath As String = IO.Path.GetTempPath()
Dim oFileName As String = GetOutlookFileName(pEvent)
Dim oFilePath As String = IO.Path.Combine(oTempPath, oFileName)
Dim oContentsList As List(Of Byte()) = GetOutlookFileContents_FromInterop(pEvent)
If oContentsList Is Nothing Then
Return Nothing
End If
Dim oPathList As New List(Of String)
For Each oContents In oContentsList
Using oFileStream As IO.FileStream = New IO.FileStream(oFilePath, IO.FileMode.Create)
oFileStream.Write(oContents, 0, oContents.Length)
oFileStream.Close()
End Using
oPathList.Add(oFilePath)
Next
Return oPathList
End Function
Private Function GetOutlookFileName(pEvent As DragEventArgs) As String
Dim oFileDescriptorSize = 512
Dim oIndex As Integer = 76
Dim oBuilder As New StringBuilder()
Using oStream As IO.MemoryStream = GetFormat(pEvent, "FileGroupDescriptor")
Dim oFileGroupDescriptor As Byte() = New Byte(oFileDescriptorSize) {}
oStream.Read(oFileGroupDescriptor, 0, oFileDescriptorSize)
While oFileGroupDescriptor(oIndex) <> 0
Dim oChar = Convert.ToChar(oFileGroupDescriptor(oIndex))
oBuilder.Append(oChar)
oIndex += 1
End While
End Using
Return oBuilder.ToString
End Function
Private Function GetOutlookFileContents_FromDragEvent(pEvent As DragEventArgs) As List(Of Byte())
Using oStream As IO.MemoryStream = pEvent.Data.GetData("FileContents", True)
If oStream Is Nothing Then
Return Nothing
End If
Dim oContentLength = Convert.ToInt32(oStream.Length)
Dim oContents As Byte() = New Byte(oContentLength) {}
oStream.Position = 0
oStream.Read(oContents, 0, Convert.ToInt32(oContentLength))
Return New List(Of Byte()) From {oContents}
End Using
End Function
Private Function GetOutlookFileContents_FromInterop(pEvent As DragEventArgs) As List(Of Byte())
Dim oApp As Outlook.Application
Try
oApp = New Outlook.Application()
Catch ex As Exception
Logger.Error(ex)
Return Nothing
End Try
Dim oResults As New List(Of Byte())
Dim oMailItem As Outlook.MailItem
For oIndex As Integer = 1 To oApp.ActiveExplorer.Selection.Count
Try
oMailItem = oApp.ActiveExplorer.Selection.Item(oIndex)
Dim oSubject As String = ConvertTextToSlug(oMailItem.Subject)
If oSubject = "" Then
oSubject = "NO_SUBJECT"
End If
Logger.Info("Subject Slug: [{0}]", oSubject)
Dim oFileName As String = $"{oSubject}.msg"
Dim oTempPath As String = IO.Path.GetTempPath()
Dim oFilePath As String = IO.Path.Combine(oTempPath, oFileName)
oMailItem.SaveAs(oFilePath)
Using oFileStream As New IO.FileStream(oFilePath, IO.FileMode.Open)
Dim oContents As Byte() = New Byte(oFileStream.Length) {}
oFileStream.Read(oContents, 0, oFileStream.Length)
oResults.Add(oContents)
End Using
Try
IO.File.Delete(oFilePath)
Catch ex As Exception
Logger.Warn("Temp file [{0}] could not be deleted!", oFilePath)
Logger.Error(ex)
End Try
Return oResults
Catch ex As Exception
Logger.Error(ex)
End Try
Next
End Function
Public Function GetFormat(pEvent As DragEventArgs, pFormat As String, pAutoConvert As Boolean) As Object
If CheckFor(pEvent, pFormat) Then
Dim oValue = pEvent.Data.GetData(pFormat, pAutoConvert)
Return oValue
Else
Return Nothing
End If
End Function
Public Function GetFormat(pEvent As DragEventArgs, pFormat As String) As Object
Return GetFormat(pEvent, pFormat, False)
End Function
Public Function CheckFor(pEvent As DragEventArgs, pFormat As String, pAutoConvert As Boolean) As Boolean
Dim oFormatExists = pEvent.Data.GetDataPresent(pFormat)
Logger.Debug("Format exists: [{0}]/[{1}]", pFormat, oFormatExists)
Return oFormatExists
End Function
Public Function CheckFor(pEvent As DragEventArgs, pFormat As String) As Boolean
Return CheckFor(pEvent, pFormat, False)
End Function
Public Function IsNormalFile(e As DragEventArgs) As Boolean
Return CheckFor(e, DataFormats.FileDrop, False)
End Function
Public Function IsOutlook(e As DragEventArgs) As Boolean
Return CheckFor(e, "FileGroupDescriptor") AndAlso CheckFor(e, "FileDrop")
End Function
Public Function IsThunderbird(e As DragEventArgs) As Boolean
Return CheckFor(e, "text/x-moz-url") AndAlso CheckFor(e, "FileDrop")
End Function
#Region "Thunderbird"
Private Function IsOutlookMail(e As DragEventArgs) As Boolean
Return Not IsOutlookAttachment(e) AndAlso CheckFor(e, "RenPrivateSourceFolder")
End Function
Private Function IsOutlookAttachment(e As DragEventArgs) As Boolean
Return IsOutlook(e) AndAlso
CheckFor(e, "RenPrivateItem") AndAlso
CheckFor(e, "ZoneIdentifier")
End Function
#End Region
#Region "Outlook"
Private Function IsThunderbirdMail(e As DragEventArgs) As Boolean
Return Not IsThunderbirdAttachment(e)
End Function
Private Function IsThunderbirdAttachment(e As DragEventArgs) As Boolean
Return IsThunderbird(e) AndAlso
CheckFor(e, "text/x-moz-url-data") AndAlso
CheckFor(e, "text/x-moz-url-desc")
End Function
#End Region
End Class

View File

@ -83,8 +83,10 @@
<Compile Include="Animator\frmPopup.vb">
<SubType>Form</SubType>
</Compile>
<Compile Include="DigitalData\Modules\Language.vb" />
<Compile Include="Drawing.vb" />
<Compile Include="File.vb" />
<Compile Include="FileDrop.vb" />
<Compile Include="Hotkey.vb" />
<Compile Include="NativeMethods.vb" />
<Compile Include="Screen.vb" />
@ -129,10 +131,47 @@
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\Modules.Base\Base\Base.vbproj">
<Project>{6ea0c51f-c2b1-4462-8198-3de0b32b74f8}</Project>
<Name>Base</Name>
</ProjectReference>
<ProjectReference Include="..\Modules.Language\Language.vbproj">
<Project>{d3c8cfed-d6f6-43a8-9bdf-454145d0352f}</Project>
<Name>Language</Name>
</ProjectReference>
<ProjectReference Include="..\Modules.Logging\Logging.vbproj">
<Project>{903B2D7D-3B80-4BE9-8713-7447B704E1B0}</Project>
<Name>Logging</Name>
</ProjectReference>
</ItemGroup>
<ItemGroup>
<COMReference Include="Microsoft.Office.Core">
<Guid>{2DF8D04C-5BFA-101B-BDE5-00AA0044DE52}</Guid>
<VersionMajor>2</VersionMajor>
<VersionMinor>8</VersionMinor>
<Lcid>0</Lcid>
<WrapperTool>primary</WrapperTool>
<Isolated>False</Isolated>
<EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference>
<COMReference Include="Microsoft.Office.Interop.Outlook">
<Guid>{00062FFF-0000-0000-C000-000000000046}</Guid>
<VersionMajor>9</VersionMajor>
<VersionMinor>6</VersionMinor>
<Lcid>0</Lcid>
<WrapperTool>primary</WrapperTool>
<Isolated>False</Isolated>
<EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference>
<COMReference Include="stdole">
<Guid>{00020430-0000-0000-C000-000000000046}</Guid>
<VersionMajor>2</VersionMajor>
<VersionMinor>0</VersionMinor>
<Lcid>0</Lcid>
<WrapperTool>primary</WrapperTool>
<Isolated>False</Isolated>
<EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference>
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.VisualBasic.targets" />
</Project>