• 检测CD / DVD插入/弹出


    下载源码- 15.05 KB 介绍 您是否想知道如何检测在您的ROM中插入CD / DVD磁盘时发生的事件,或在弹出ROM时发生的事件?在插入磁盘时,您是否曾经需要获取插入到ROM中的CD / DVD内容的类型?如果上述情况是真的,下面这篇文章是为你写的。 背景 使用Win32 API,您可以跟踪许多Windows消息。当你插入/弹出一个CD /DVD,一个WM_DEVICECHANGE消息发生在Windows,你可以跟踪在一个子类的应用程序。使用该技术和其他一些技术,您可以编写一个库,在CD / DVD内容到达时触发事件并删除。此外,您还可以在媒体到达时获得内容的类型。 使用的代码 我已经创建了一个ActiveX DLL项目在VB6。有一个名为clsROMMonitor的类,它是负责子类化和事件触发的主类。一个名为modROMMonitor的通用模块拥有一些用于子类化的有用方法和库所需的Win32 API。图书馆需要一个外部的“形式”才能工作。它有两个事件命名为OnMediaInsert和OnMediaEject,它们将在到达和删除媒体的名称暗示。您还可以了解媒体内容的类型。实现了音频ocd检测和DVD视频检测逻辑。类的IsMediaAudioCD和IsMediaDVDVideo属性将帮助您解决这个问题。它可以扩展到您所能想到的任何特定类型。记住一件事,从VB IDE调试代码可能会遇到问题,因为这使用的是子类化。但是,下面是主类clsROMMonitor的代码: 隐藏,收缩,复制Code

    Option Explicit
      
    ' Original Window Proc Address
    Private mlngWinProcOld              As Long
      
    ' Subclassed hWnd
    Private mlngHwnd                    As Long
    Private mlngHandle                  As Long
    
    Private mstrDriveLetter             As String
    Private mblnMediaAudioCD            As Boolean
    Private mblnMediaDVDVideo           As Boolean
    
    'Events
    Public Event OnMediaInsert(DriveLetter As String)
    Public Event OnMediaEject(DriveLetter As String)
    
    Public Property Get hwnd() As Long
        hwnd = mlngHandle
    End Property
    
    Public Property Let hwnd(lngHwnd As Long)
        mlngHandle = lngHwnd
        SubClass mlngHandle
    End Property
    
    Public Property Get IsMediaAudioCD() As Boolean
        IsMediaAudioCD = mblnMediaAudioCD
    End Property
    
    Public Property Get IsMediaDVDVideo() As Boolean
        IsMediaDVDVideo = mblnMediaDVDVideo
    End Property
    
    Private Sub SubClass(ByVal hwnd&)
        If IsWindow(hwnd) Then
            If GetProp(hwnd, "ROMMonitor") Then
                Exit Sub
            End If
            
            If SetProp(hwnd, ByVal "ROMMonitor", ObjPtr(Me)) Then
                mlngWinProcOld = SetWindowLong_
    		(hwnd, GWL_WNDPROC, AddressOf modROMMonitor.WindProc)
                mlngHwnd = hwnd
            End If
        End If
    End Sub
    
    Private Sub UnSubClass()
        If IsWindow(mlngHwnd) Then
            If mlngWinProcOld Then
                SetWindowLong mlngHwnd, GWL_WNDPROC, mlngWinProcOld
                ' remove the added property
                RemoveProp mlngHwnd, "ROMMonitor"
                ' set the variables to zero to avoid any mishaps
                mlngWinProcOld = 0
                mlngHwnd = 0
            End If
        End If
    End Sub
    
    Private Sub Class_Terminate()
      UnSubClass
    End Sub
    
    Private Function GetDriveFromMask(unitmask As Integer) As String
    '      Finds the first valid drive letter from a mask of drive letters. The
    '      mask must be in the format 1 = A, 2 = B, 4 = C, 8 = D, 16 = E etc.
        GetDriveFromMask = Chr(65 + (Log(unitmask) / Log(2)))
    End Function
    
    Private Function pIsMediaAudioCD(ByVal strPath As String) As Boolean
        Dim strFileName     As String   ' Walking filename variable.
        
        On Error Resume Next
            
        strFileName = Dir(strPath & ":" & "*.cda", _
    		vbNormal Or vbHidden Or vbSystem Or vbReadOnly)
        
        If Len(strFileName) <> 0 Then
            pIsMediaAudioCD = True
        Else
            pIsMediaAudioCD = False
        End If
    End Function
    
    Private Function pIsMediaDVDVideo(ByVal strPath As String) As Boolean
        Dim strFileName     As String   ' Walking filename variable.
        Dim lngFileCount    As Integer
        
        On Error Resume Next
        lngFileCount = 0
            
        strFileName = Dir(strPath & ":" & "video_ts", _
    		vbNormal Or vbHidden Or vbSystem Or vbReadOnly Or vbDirectory)
        
        If Len(strFileName) <> 0 Then
            strFileName = Dir(strPath & ":video_ts*.vob", _
    		vbNormal Or vbHidden Or vbSystem Or vbReadOnly)
            While Len(strFileName) <> 0
                lngFileCount = lngFileCount + 1
                DoEvents
                strFileName = Dir()  ' Get next file.
            Wend
            
            If lngFileCount > 0 Then
                pIsMediaDVDVideo = True
            Else
                pIsMediaDVDVideo = False
            End If
        Else
            pIsMediaDVDVideo = False
        End If
    End Function
    
    Friend Function WindowProc(ByVal hWindow&, ByVal uMsg&, _
    		ByVal wParam&, ByVal lParam&) As Long
        ' this function is called from the modCDMonitor BAS module.  all messages are for
        ' the subclasses hWnd are passed here to be processed before passing them on to VB
        
        Select Case uMsg
            ' catch the device changed message
            Case WM_DEVICECHANGE
                Dim dbHdr As DEV_BROADCAST_HDR, dbVol As DEV_BROADCAST_VOLUME
                
                ' see if the wParam is what we are looking for
                Select Case wParam
                    Case DBT_DEVICEARRIVAL, DBT_DEVICEREMOVECOMPLETE
                        ' if the wParam is one of the values we are looking for, copy the
                        ' data pointed to by the lParam into the local 
                        ' DEV_BROADCAST_HDR struct
                        CopyMemory ByVal VarPtr(dbHdr), ByVal lParam, Len(dbHdr)
                        
                        ' if the dbch_devicetype member of the DEV_BROADCAST_HDR 
                        ' struct is equal to DBT_DEVTYP_VOLUME, 
                        ' copy the data pointed to by the lParam into the local
                        ' DEV_BROADCAST_VOLUME struct
                        If dbHdr.dbch_devicetype = DBT_DEVTYP_VOLUME Then
                            CopyMemory ByVal VarPtr(dbVol), ByVal lParam, Len(dbVol)
                            'if the dbcv_flags member includes the DBTF_MEDIA value, 
                            'raise the correct event....
                            If dbVol.dbcv_flags And DBTF_MEDIA Then
                                mstrDriveLetter = GetDriveFromMask(CInt(dbVol.dbcv_unitmask))
                                Select Case wParam
                                    Case DBT_DEVICEARRIVAL
                                        mblnMediaAudioCD = pIsMediaAudioCD(mstrDriveLetter)
                                        mblnMediaDVDVideo = pIsMediaDVDVideo(mstrDriveLetter)
                                        RaiseEvent OnMediaInsert(mstrDriveLetter)
                                    Case DBT_DEVICEREMOVECOMPLETE
                                        RaiseEvent OnMediaEject(mstrDriveLetter)
                                End Select
                            End If
                        End If
                    Case Else
                        ' do nothing
                End Select
            Case Else
                ' do nothing
        End Select
        
        ' pass the messages on to VB
        WindowProc = CallWindowProc(mlngWinProcOld, hWindow, uMsg, wParam, lParam)
    End Function

    通用模块modROMMonitor的代码如下: 隐藏,收缩,复制Code

    Option Explicit
    
    Option Private Module
    
    Public Type DEV_BROADCAST_HDR
        dbch_size As Long
        dbch_devicetype As Long
        dbch_reserved As Long
    End Type
    
    Public Type DEV_BROADCAST_VOLUME
        dbcv_size As Long
        dbcv_devicetype As Long
        dbcv_reserved As Long
        dbcv_unitmask As Long
        dbcv_flags As Long
    End Type
    
    Public Const DBTF_MEDIA  As Long = &H1&
    Public Const DBTF_NET = &H2&
    Public Const DBT_DEVTYP_VOLUME  As Long = &H2&
    Public Const WM_DEVICECHANGE  As Long = &H219&
    Public Const DBT_DEVICEARRIVAL  As Long = &H8000&
    Public Const DBT_DEVICEREMOVECOMPLETE  As Long = &H8004&
    
    Public Const GWL_WNDPROC As Long = (-4&)
    
    Public Declare Function IsWindow Lib "user32" (ByVal hwnd&) As Long
    
    Public Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" _
    	(lpDest As Any, lpSource As Any, ByVal cBytes&)
    
    Public Declare Function SetProp Lib "user32" Alias "SetPropA" _
    	(ByVal hwnd As Long, ByVal lpString As String, ByVal hData As Long) As Long
    Public Declare Function GetProp Lib "user32" Alias "GetPropA" _
    	(ByVal hwnd As Long, ByVal lpString As String) As Long
    Public Declare Function RemoveProp Lib "user32" Alias "RemovePropA" _
    	(ByVal hwnd&, ByVal lpString$) As Long
    
    Public Declare Function SetWindowLong Lib "user32" Alias "SetWindowLongA" _
    	(ByVal hwnd&, ByVal nIndex&, ByVal dwNewLong&) As Long
    
    Public Declare Function CallWindowProc Lib "user32" Alias "CallWindowProcA" _
      (ByVal lpPrevWndFunc&, ByVal hwnd&, ByVal Msg&, ByVal wParam&, ByVal lParam&) As Long
    
    Public Function WindProc(ByVal hwnd&, ByVal uMsg&, ByVal wParam&, ByVal lParam&) As Long
        WindProc = ROMMonitorFromHwnd(hwnd).WindowProc(hwnd, uMsg, wParam, lParam)
    End Function
    
    Private Function ROMMonitorFromHwnd(ByVal hwnd As Long) As clsROMMonitor
        ' resolve a dumb pointer into a referenced object....
        
        Dim ROMMonitorEx        As clsROMMonitor
        Dim lngptrObj           As Long
          
        ' retrieve the pointer from the property we set in the subclass routine
        lngptrObj = GetProp(hwnd, ByVal "ROMMonitor")
        
        ' copy the pointer into the local variable.  if you end your app during this
        ' process, VB will crash when it tries to destroy the extra object reference
        ' so don't end your app now.
        CopyMemory ROMMonitorEx, lngptrObj, 4&
        
        ' set a reference to the object
        Set ROMMonitorFromHwnd = ROMMonitorEx
        
        ' clear the object variable so VB won't try to
        ' decrement the reference count on the object
        CopyMemory ROMMonitorEx, 0&, 4&
    End Function

    使用图书馆 您可以从任何COM兼容语言使用此库。我使用了一个示例VB6标准EXE应用程序来使用这个。您已经拥有了在代码中使用WinthEvents使用clsROMMonitor所需的一切,以便您可以跟踪事件。您必须将表单的hWnd传递给类的hWnd属性,然后跟踪事件并获取媒体的内容。请看下面示例应用程序的代码: 隐藏,收缩,复制Code

    '********************************************************
    '* WARNING!!!!
    '* THIS IS A CLIENT OF A SUBCLASSED LIBRARY PROJECT
    '* DO NOT PRESS THE STOP BUTTON OF VB IDE WHILE THE APPLICATION
    '* IS RUNNING, OR YOUR APPLICATION WILL CRASH. MAKE SURE YOU CLOSE
    '* YOUR APPLICATION WHEN NEEDED BY CLICKING THE CROSS ICON OF THE
    '* WINDOW.
    '********************************************************
    
    Option Explicit
    ' the subclass procedure is in the clsCDMonitor class module
    Private WithEvents MyROMMonitor As clsROMMonitor
    
    Private Sub Form_Load()
      ' create an instance of the clsCDMonitor object and call it's
      Set MyROMMonitor = New clsROMMonitor
      MyROMMonitor.hWnd = Me.hWnd
     
    End Sub
    
    Private Sub Form_Unload(Cancel As Integer)
      ' destroy the object so we don't crash since the
      ' subclass is terminated in the Class_Terminate event
      Set MyROMMonitor = Nothing
    End Sub
    
    Private Sub MyROMMonitor_OnMediaEject(DriveLetter As String)
        MsgBox "Media Ejected"
    End Sub
    
    Private Sub MyROMMonitor_OnMediaInsert(DriveLetter As String)
        If MyROMMonitor.IsMediaAudioCD Then
            MsgBox "Media is Audio CD"
        ElseIf MyROMMonitor.IsMediaDVDVideo Then
            MsgBox "Media is DVD Video"
        Else
            MsgBox "Mixed media instered"
        End If
    End Sub
    
    '* ENJOY!!!

    结论 该库使用了Win32API和子类化技术。在调试库时要小心。希望你会喜欢! 历史 2008年9月20日:初任 本文转载于:http://www.diyabc.com/frontweb/news2300.html

  • 相关阅读:
    jira 解决结果配置
    .net core ef mysql in 参数化写法
    CentOS安装破解版Jira 亲测有效(附带破解包)
    实现js读取Excel数据
    android权限(permission)大全
    如何搭建Nuget服务器
    WebApi配置Swagger
    Aps.Net WebApi依赖注入
    解决.Net Core跨域问题
    一篇关于Asp.Net Model验证响应消息的问题处理
  • 原文地址:https://www.cnblogs.com/Dincat/p/13457466.html
Copyright © 2020-2023  润新知