ディスクの空き容量を取得(U)         <TOP>


ディスクの空き容量を取得します。VBでのCurrencyに相当する数値変数がないので、ULARGE_INTEGER構造体を用いてLowPart・HighPartに分けて計算しています。

GetLogicalDrives 使用可能ドライブの取得

GetLogicalDriveStrings 有効なドライブ名の取得

GetDiskFreeSpaceEx 指定のディレクトリを含むディスクの空き容量を調べる

 

コンボボックスには現在使用できるドライブがセットされています。目的ドライブをクリックすると容量を取得することができます。

 

WindowsXPでの結果とプロパティでの確認

 

Windows2000での結果とプロパティでの確認

 

Windows98での結果とプロパティでの確認

 

 

参考

ビット       bit(b)
バイト       byte(B)        1B = 8b
キロバイト   Kilo Byte(KB) 1KB = 1,000B
メガバイト   Mega Byte(MB) 1MB = 1,000KB
ギガバイト   Giga Byte(GB) 1GB = 1,000MB
テラバイト   Tera Byte(TB) 1TB = 1,000GB
ペタバイト   Peta Byte(PB) 1PB = 1,000TB
エクサバイト Exa Byte(EB)  1EB = 1,000PB
ゼタバイト   Zetta Byte(ZB)1ZB = 1,000EB
ヨタバイト   Yotta Byte(YB)1YB = 1,000ZB

 

'================================================================
'= ディスクの空き容量を取得(U)
'=    (GetDiskFreeSpaceEx2.bas)
'================================================================
#include "Windows.bi"

Type ULARGE_INTEGER
    lowpart As Long
    highpart As Long
End Type

' 使用可能ドライブの取得
Declare Function Api_GetLogicalDrives& Lib "kernel32" Alias "GetLogicalDrives" ()

' 有効なドライブ名の取得
Declare Function Api_GetLogicalDriveStrings& Lib "kernel32" Alias "GetLogicalDriveStringsA" (ByVal nBufferLength&, ByVal lpBuffer$)

' 指定のディレクトリを含むディスクの空き容量を調べる
Declare Function Api_GetDiskFreeSpaceEx& Lib "kernel32" Alias "GetDiskFreeSpaceExA" (ByVal lpDirectoryName$, lpFreeBytesAvailableToCaller As ULARGE_INTEGER, lpTotalNumberOfBytes As ULARGE_INTEGER, lpTotalNumberOfFreeBytes As ULARGE_INTEGER)

Var Shared Combo1 As Object
Var Shared Text(9) As Object

Combo1.Attach GetDlgItem("Combo1")
Combo1.SetFontSize 14
For i = 0 To 9
    Text(i).Attach GetDlgItem("Text" & Trim$(Str$(i + 1)))
    Text(i).SetFontSize 14
Next

'================================================================
'=
'================================================================
Declare Sub MainForm_Start edecl ()
Sub MainForm_Start()
    Var Drv As String                'ドライブ名
    Var Drives As Long               'ディスクドライブのビットマスク

    Drives = Api_GetLogicalDrives()  '利用可能なディスクドライブ取得
    If Drives = 0 Then exit Sub      '関数の失敗

    For i = 0 To 25                  'A〜Zドライブを検索する
        If (Drives and 1) = 1 Then
            Drv = Chr$(65 + i)       'ドライブ名(A〜Z)に変換
            Drv = Drv & ":\"
            Combo1.AddString Drv
        End If
        Drives = Drives \ 2          'ドライブ検索
    Next i
End Sub

'================================================================
'=
'================================================================
Declare Function LargeIntegerToDouble(LowPart As Long, HighPart As Long) As Double
Function LargeIntegerToDouble(LowPart As Long, HighPart As Long) As Double
    Var Ret As Double

    Ret = HighPart
    If HighPart < 0 Then Ret = Ret + 2 ^ 32
    Ret = Ret * 2 ^ 32

    Ret = Ret + LowPart
    If LowPart < 0 Then Ret = Ret + 2 ^ 32

    LargeIntegerToDouble = Ret
End Function

'================================================================
'=
'================================================================
Declare Function ThreeNonZeroDigits(Value As Double) As String
Function ThreeNonZeroDigits(Value As Double) As String
    If Value >= 100 Then

        '小数無し
        ThreeNonZeroDigits = Format$(Int(Value),"### ")
    Else If Value >= 10 Then

        '小数点以下1桁
        ThreeNonZeroDigits = Format$(Value, "###.# ")
    Else

        '小数点以下2桁
        ThreeNonZeroDigits = Format$(Value, "###.##")
    End If
End Function

'================================================================
'=
'================================================================
Declare Function FormatBytes(bNum As Double) As String
Function FormatBytes(bNum As Double) As String
    Static ONE_KB As Double : ONE_KB = 1024
    Static ONE_MB As Double : ONE_MB = ONE_KB * 1024
    Static ONE_GB As Double : ONE_GB = ONE_MB * 1024
    Static ONE_TB As Double : ONE_TB = ONE_GB * 1024
    Static ONE_PB As Double : ONE_PB = ONE_TB * 1024
    Static ONE_EB As Double : ONE_EB = ONE_PB * 1024
    Static ONE_ZB As Double : ONE_ZB = ONE_EB * 1024
    Static ONE_YB As Double : ONE_YB = ONE_ZB * 1024

    Var Value As Double

    If bNum <= 999 Then

        'bytesフォーマット
        FormatBytes = Format$(bNum, "### ") & "B"
    Else If bNum <= ONE_KB * 999 Then

        'KBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_KB) & "KB"
    Else If bNum <= ONE_MB * 999 Then

        'MBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_MB) & "MB"
    Else If bNum <= ONE_GB * 999 Then

        'GBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_GB) & "GB"
    Else If bNum <= ONE_TB * 999 Then

        'TBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_TB) & "TB"
    Else If bNum <= ONE_PB * 999 Then

        'PBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_PB) & "PB"
    Else If bNum <= ONE_EB * 999 Then

        'EBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_EB) & "EB"
    Else If bNum <= ONE_ZB * 999 Then

        'ZBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_ZB) & "ZB"
    Else

        'YBフォーマット
        FormatBytes = ThreeNonZeroDigits(bNum / ONE_YB) & "YB"
    End If
End Function

'================================================================
'=
'================================================================
Declare Sub Combo1_Change edecl ()
Sub Combo1_Change()
    Var bAvail As ULARGE_INTEGER
    Var bTotal As ULARGE_INTEGER
    Var bFree As ULARGE_INTEGER
    Var dTotal As Double
    Var dFree As Double
    Var Ret As Long

    Ret = Api_GetDiskFreeSpaceEx(GetDlgItemText("Combo1"), bAvail, bTotal, bFree)

    dTotal = LargeIntegerToDouble(bTotal.lowpart, bTotal.highpart)

    If dTotal = 0 Then
        For i = 0 To 5 : Text(i).SetWindowText "" : Next
            Res = MessageBox("", "取得できません!", 0, 2)
            Exit Sub
    End If

    dFree = LargeIntegerToDouble(bFree.lowpart, bFree.highpart)

    Text(0).SetWindowText FormatBytes(dTotal)
    Text(1).SetWindowText FormatBytes(dFree)
    Text(2).SetWindowText FormatBytes(dTotal - dFree)
    Text(3).SetWindowText Format$(100, "###.##%")
    Text(4).SetWindowText Format$(dFree / dTotal * 100, "###.##%")
    Text(5).SetWindowText Format$((dTotal - dFree) / dTotal * 100, "###.##%")
End Sub

'================================================================
'=
'================================================================
While 1
    WaitEvent
Wend
Stop
End