[ 初めての方へ | 一覧(最新更新順) | 全文検索 | 過去ログ ]
『動画ファイルのビットレート』(動画ファン)
動画ファイルのビットレートをセルに書き出すVBAのコードがあれば教えてください。
ネット情報で以下のマクロを考えてみました。
Sub GetVideoFile()
Dim fso As Object Dim folder As Object Dim file As Object Dim shell As Object Dim size As Long Dim bitrate As Long Dim row As Long
Dim folderPath As String
With Application.FileDialog(msoFileDialogFolderPicker) .Title = "調査する動画フォルダーを選択してください" .Show If .SelectedItems.Count = 0 Then MsgBox "キャンセルされました。", vbInformation Exit Sub End If folderPath = .SelectedItems(1) End With
Set fso = CreateObject("Scripting.FileSystemObject") Set folder = fso.GetFolder(folderPath) Set shell = CreateObject("Shell.Application")
row = 1
For Each file In folder.Files If LCase(fso.GetExtensionName(file.Path)) Like "mp4" Or LCase(fso.GetExtensionName(file.Path)) Like "mp4" Then size = file.size / 1024 / 1024 Cells(row, 1) = file.Name Cells(row, 2) = size 'Cells(row, 3) = -----------> ここにビットレートを書き出す row = row + 1 End If Next file End Sub
< 使用 Excel:Excel2021、使用 OS:Windows11 >
Dim objFle As Object
Set objFle = objFld.Items.Item(file.name)
bitrate = objFld.GetDetailesOf(objFle , 28)
Cells(row, 3) = bitrate
↑'Cells(row, 3) = の箇所を上記4行に変更
(ufj) 2023/09/14(木) 15:38:31
>bitrate = objFld.GetDetailesOf(objFle , 28) たぶん、28のビットレートじゃなくて、 320 の 総ビット レート だと思います。
Sub sample() Debug.Print CallFFProbe("D:\Video\TEST.MP4") ' ffmpegをつかう End Sub Function CallFFProbe(filepath As String) As String ' ffmpeg をインストールしてPathを通しておく または ffprobe.exe をフルパスで指定 With CreateObject("Wscript.Shell") CallFFProbe = .Exec("cmd /c ffprobe.exe -hide_banner """ & filepath & """").StdErr.ReadAll End With End Function (´・ω・`) 2023/09/14(木) 15:46:40
早速、試してみましたが
CallFFProbeの行でエラーがでました。
CallFFProbe = .Exec("cmd /c C:\Program Files (x86)\Digiarty\VideoProc Converter\ffprobe.exe -hide_banner """ & filepath & """").StdErr.ReadAll
最初、
Windowsセキュリティ
このコンテンツはブロックされています。
CMD.EXEからのコンテンツへのアクセスは管理者によって
許可されていません。
と表示されたので「ブロック解除」を選択して「OK」をクリック
2回目の起動では、Windowsセキュリティーのエラーは出ませんでしたが
イミディエイト画面に以下の表示が出て上手く処理できませんでした。
'C:\Program' は、内部コマンドまたは外部コマンド、
操作可能なプログラムまたはバッチ ファイルとして認識されていません。
これはffprobe.exeの指定が間違っているためですか?
私の環境では、チェックすると
ffprobe.exe が4か所で保存されていました。
サイズが、183kb、171kb、192kb、128360kb とそれぞれ違っています。
(動画ファン) 2023/09/14(木) 18:37:47
Sub 総ビットレート取得() Dim sPath, fName As String Dim TotalBitrate As Long
sPath = Application.GetOpenFilename("MP4ビデオ,*.mp4") If sPath = False Then Exit Sub fName = Split(sPath, "\")(UBound(Split(sPath, "\"))) sPath = Replace(sPath, fName, "")
On Error Resume Next With CreateObject("Shell.Application") With .Namespace(sPath) 'sPathはレイトバイディングの為variant指定のこと TotalBitrate = .ParseName(fName).ExtendedProperty("System.Video.TotalBitrate") End With End With End Sub
win10(64)
(kazuo) 2023/09/14(木) 20:17:46
総ビットレート取得()を紹介いただきましたので試してみました。
上手くビットレート(TotalBitrate)が入手できました。
総ビットレート取得()は、単一ファイルを選択する仕様ですが
これをディレクトリーを指定してディレクトリー内の複数ファイルを対象にして
ビットレート取得後にセル(c列)に書き出すようにコードを変更したいです。
現在、開発途中のコードは下記ですが
これに希望に合うようにコードを修正して頂けないでしょうか
お願いします。
Sub GetVideoProperties()
Dim fso As Object Dim folder As Object Dim file As Object Dim shell As Object Dim size As Long Dim Target As String, Cnt As Long Dim row As Long Dim folderPath As Variant
With Application.FileDialog(msoFileDialogFolderPicker) .Title = "調査する動画フォルダーを選択してください" .Show If .SelectedItems.Count = 0 Then MsgBox "キャンセルされました。", vbInformation Exit Sub End If folderPath = .SelectedItems(1)
End With
Set fso = CreateObject("Scripting.FileSystemObject") Set folder = fso.GetFolder(folderPath) Set shell = CreateObject("Shell.Application")
ActiveSheet.Columns("A:F").Clear
Range("A1") = "ファイル名" Range("B1") = "ファイルサイズ(MB)" Range("C1") = "ビットレート"
Dim varFolPath As Variant Dim objFld As Variant Dim bitrate As Long varFolPath = folderPath Set objFld = shell.Namespace(varFolPath)
row = 2
For Each file In folder.Files If LCase(fso.GetExtensionName(file.Path)) Like "mp4" Or LCase(fso.GetExtensionName(file.Path)) Like "mp4" Then size = file.size / 1024 / 1024 'bitrate = shell.Namespace(file.Path).Self.ExtendedProperty("System.Video.Bitrate")
Cells(row, 1) = file.Name Cells(row, 2) = size
row = row + 1 End If Next file Cells(row, 2) = "合計 / " & Application.WorksheetFunction.Sum(Range("B2:B" & row - 1)) Cells(row + 1, 2) = "平均 / " & Round(Application.WorksheetFunction.Sum(Range("B2:B" & row - 1)) / (row - 2), 1)
End Sub
(動画ファン) 2023/09/15(金) 08:19:15
(余談) Win7(x86)では「総ビット レート」が320じゃなかったりするんですね... ^^;
Rem =================================================== Rem 参照設定: Microsoft Shell Controls And Automation Rem =================================================== Private Function test(argFolder, argFile) As String Dim fo As Shell32.folder, i As Shell32.FolderItem Dim v(), r As Long, c As Long, p With New Shell32.shell Set fo = .Namespace(argFolder) End With Set i = fo.Items.Item(argFile) ReDim v(0 To 500) For r = 0 To 500 If fo.GetDetailsOf(Nothing, r) Like "*ビット*" Then p = fo.GetDetailsOf(i, r) If Len(p) Then v(c) = "[" & r & ":" & fo.GetDetailsOf(Nothing, r) & "]:" & fo.GetDetailsOf(i, r) c = c + 1 End If End If Next If c = 0 Then Exit Function ReDim Preserve v(0 To c - 1) test = Join(v, ",") End Function
↓組み込み例
Cells(row, 3) = test(folderPath, file.Name)
(白茶) 2023/09/15(金) 08:57:00
あ。 GetDetailsOfで取れた値の先頭に U+200E(Left-To-Right Mark)が含まれている様です。(今気付いた)
(白茶) 2023/09/15(金) 09:03:49
> Set fso = CreateObject("Scripting.FileSystemObject") から > Next file まで
Set fso = CreateObject("Scripting.FileSystemObject") Set folder = fso.GetFolder(folderPath) Set shell = CreateObject("Shell.Application") Dim irow As Long With ActiveSheet .Columns("A:F").Clear .Range("A1:C1").Value = Split("ファイル名 ファイルサイズ(MB) ビットレート") irow = 2 For Each file In folder.Files If LCase(fso.GetExtensionName(file.Path)) = "mp4" Then size = file.size / 1024 / 1024 .Cells(irow, 1).Value = file.Name .Cells(irow, 2).Value = size .Cells(irow, 3).Value = CLng(shell.Namespace(folderPath).ParseName(file.Name) _ .ExtendedProperty("System.Video.TotalBitrate")) irow = irow + 1 End If Next file End With
(kazuo) 2023/09/15(金) 10:07:21
頂いたファンクションで音声ビットレートと総ビットレートが出力されるようになりました。
ファイルサイズが991MBで再生時間が50:09の動画(固定ビットレートの動画)でチェックしたら
以下の「動画ファイル ビットレート計算機」で計算される値と
私が常用している「MediaInfo」で表示される動画の総ビットレート値は2763で同じでした。
(たまたま一致しただけかも?)
Private Function test(argFolder, argFile)で計算された値は2754で若干異なるのですが
気にしないことにしました。
Sub GetVideoProperties() Dim fso As Object Dim folder As Object Dim file As Object Dim shell As Object Dim size As Long Dim Target As String, Cnt As Long Dim row As Long Dim folderPath As Variant
With Application.FileDialog(msoFileDialogFolderPicker) .Title = "調査する動画フォルダーを選択してください" .Show If .SelectedItems.Count = 0 Then MsgBox "キャンセルされました。", vbInformation Exit Sub End If folderPath = .SelectedItems(1)
End With
Set fso = CreateObject("Scripting.FileSystemObject") Set folder = fso.GetFolder(folderPath) Set shell = CreateObject("Shell.Application")
ActiveSheet.Columns("A:D").Clear
Range("A1") = "ファイル名" Range("B1") = "ファイルサイズ(MB)" Range("C1") = "音声ビットレート" Range("D1") = "総ビットレート"
Application.ScreenUpdating = False
Dim varFolPath As Variant Dim objFld As Variant Dim bitrate As Long varFolPath = folderPath Set objFld = shell.Namespace(varFolPath)
row = 2
Dim VBR As String Dim MBR As String
For Each file In folder.Files If LCase(fso.GetExtensionName(file.Path)) Like "mp4" Or LCase(fso.GetExtensionName(file.Path)) Like "mp4" Then size = file.size / 1024 / 1024 'bitrate = shell.Namespace(file.Path).Self.ExtendedProperty("System.Video.Bitrate")
Cells(row, 1) = file.Name Cells(row, 2) = size
VBR = Mid(TBRT(folderPath, file.Name), 15, 2) MBR = Mid(TBRT(folderPath, file.Name), 38, 4) Cells(row, 3) = VBR Cells(row, 4) = MBR
row = row + 1 End If Next file Cells(row, 2) = "合計 / " & Application.WorksheetFunction.Sum(Range("B2:B" & row - 1)) Cells(row + 1, 2) = "平均 / " & Round(Application.WorksheetFunction.Sum(Range("B2:B" & row - 1)) / (row - 2), 1)
Application.ScreenUpdating = True
End Sub
Rem =================================================== Rem 参照設定: Microsoft Shell Controls And Automation Rem ===================================================
Private Function TBRT(argFolder, argFile) As String Dim fo As Shell32.folder, i As Shell32.FolderItem Dim v(), r As Long, c As Long, p With New Shell32.shell Set fo = .Namespace(argFolder) End With Set i = fo.Items.Item(argFile) ReDim v(0 To 500) For r = 0 To 500 If fo.GetDetailsOf(Nothing, r) Like "*ビット*" Then p = fo.GetDetailsOf(i, r) If Len(p) Then v(c) = "[" & r & ":" & fo.GetDetailsOf(Nothing, r) & "]:" & fo.GetDetailsOf(i, r) c = c + 1 End If End If Next If c = 0 Then Exit Function ReDim Preserve v(0 To c - 1) TBRT = Join(v, ",") End Function (動画ファン) 2023/09/15(金) 10:47:05
当たり前でしょうが、
白茶さんからいただいたコードから産出される値と同じでした。
’-------------------------------
ufjからのアドバイスは、´・ω・`さんの以下の書き込みから判断して間違いだと判断して
手を付けずにスルーしました。
>>28のビットレートじゃなくて、320 の 総ビット レート だと思います。
結果的にUFJさんが、不快な思いをされたのであればお許しください。
お詫びいたします。
(動画ファン) 2023/09/15(金) 11:37:01
https://www.excel.studio-kazu.jp/kw/20230501124500.html
以下のコードを追加しましたが
Cells(row, 5) = objFld.GetDetailsOf(objFld.ParseName(file), 27)
エラーにはならずに「長さ」と文字が表示されます。
コードの訂正をお願いできないでしょうか。
(動画ファン) 2023/09/15(金) 12:18:37
挙動としては、 objFld.GetDetailsOf(objFld.ParseName(file), 27) ~~~~~~~~~~~~~~~~~~~~~~この部分の結果が Nothing だとそうなりますね。 この file は > For Each file In folder.Files の file だと思いますけど、 だったらfsoのFileでしょうから既定のプロパティはPathです。 .Nameを指定してやらねばイカンのではないでしょうか?
(白茶) 2023/09/15(金) 13:22:30
objFld.ParseName(file.Name)に変更して上手く処理できたと思ったので
チェックのためターゲットのフォルダーを他のフォルダーで試してみたら
総ビットレート(kbps)と再生時間が計算されない事例が出てきました。
総ビットレート(kbps) は何も書き出されない
再生時間 はゼロ(0:00:00)と表示される
(コード的には、以下の2つが相当します)
.Cells(irow, 3).Value = Round(CLng(shell.Namespace(folderPath).ParseName(file.Name) _ .ExtendedProperty("System.Video.TotalBitrate")) / 1000, 0) '総ビットレート
.Cells(irow, 4) = objFld.GetDetailsOf(objFld.ParseName(file.Name), 27) '再生時間
変名前のファイル名は正常に表示されているのでファイル名が問題になることは無いと思いますが
ファイル名が「EXCELで使用できない文字列なのかな」と思ってAAA.mp4と問題になる事が無いであろう
ファイル名に変換してみましたが状況に変化ありません。
この不具合は、どのような問題の為か判りますか?
Sub GetVideoProperties_2()
Dim fso As Object Dim folder As Object Dim file As Object Dim shell As Object Dim size As Long Dim Target As String, Cnt As Long Dim row As Long Dim folderPath As Variant
With Application.FileDialog(msoFileDialogFolderPicker) .Title = "調査する動画フォルダーを選択してください" .Show If .SelectedItems.Count = 0 Then MsgBox "キャンセルされました。", vbInformation Exit Sub End If folderPath = .SelectedItems(1)
End With
Set fso = CreateObject("Scripting.FileSystemObject") Set folder = fso.GetFolder(folderPath) Set shell = CreateObject("Shell.Application")
Dim irow As Long
Application.ScreenUpdating = False
Dim varFolPath As Variant Dim objFld As Variant Dim bitrate As Long varFolPath = folderPath Set objFld = shell.Namespace(varFolPath)
With ActiveSheet .Columns("A:F").Clear .Range("A1:E1").Value = Split("ファイル名 ファイルサイズ(MB) 総ビットレート(kbps) 再生時間") irow = 2 For Each file In folder.Files If LCase(fso.GetExtensionName(file.Path)) = "mp4" Then size = file.size / 1024 / 1024
.Cells(irow, 1).Value = file.Name .Cells(irow, 2).Value = size .Cells(irow, 3).Value = Round(CLng(shell.Namespace(folderPath).ParseName(file.Name) _ .ExtendedProperty("System.Video.TotalBitrate")) / 1000, 0) .Cells(irow, 4) = objFld.GetDetailsOf(objFld.ParseName(file.Name), 27) '再生時間
irow = irow + 1
End If
Next file End With
Cells(irow, 2) = "合計 / " & Application.WorksheetFunction.Sum(Range("B2:B" & irow - 1)) Cells(irow + 1, 2) = "平均 / " & Round(Application.WorksheetFunction.Sum(Range("B2:B" & irow - 1)) / (irow - 2), 1) Cells(irow, 4).NumberFormatLocal = "hh:mm:ss" Cells(irow, 4) = Application.WorksheetFunction.Sum(Range("D2:D" & irow - 1)) Cells(irow, 4).Offset(0, 1) = " <--- 合計"
Columns("A:F").AutoFit
Application.ScreenUpdating = True
End Sub
(動画ファン) 2023/09/15(金) 15:32:17
>動画ファンさん
ということで、僕のことはお気になさらず。解決するといいね
(ufj) 2023/09/15(金) 16:44:40
ExtendedProperty("System.Video.TotalBitrate") という良い方法を教えて持ったんだから、応用すればいいじゃないですかね
Sub sample() Debug.Print ビットレートを取得("D:\Video\test.MP4") End Sub
Function ビットレートを取得(filepath As String) Dim sh As Shell32.Shell, FSO As FileSystemObject, f As File Dim folder As Shell32.Folder3, objItem As Shell32.FolderItem2 Set sh = CreateObject("Shell.Application") Set FSO = CreateObject("Scripting.FileSystemObject") Set f = FSO.GetFile(filepath) Set folder = sh.Namespace(f.ParentFolder.Path) Set objItem = folder.ParseName(f.Name)
Debug.Print objItem.ExtendedProperty("System.Video.TotalBitrate") Debug.Print Format(CDate(CDbl(objItem.ExtendedProperty("Duration")) / 10000000 / 60 / 60 / 24), "h:mm:ss")
End Function (´・ω・`) 2023/09/15(金) 16:45:38
ExtendedProperty("Duration")は ExtendedProperty("System.Media.Duration") の方がピンと来ますね ちなみに単位は 100ナノ秒 だそうです (´・ω・`) 2023/09/15(金) 17:10:02
問題のmp4のフルパスを指定でアドバイスいただいたコードを試してみました。
結果「0:00:00」と同じ結果が表示されます。
Function名は、ビットレートを取得となっていますが
結果は、再生時間だと思いますが?
なお、イミディエイト画面に
? objItem.ExtendedProperty("System.Video.TotalBitrate")
を書き込んでチェックしても何も表示されません。
この結果は、2023/09/15(金) 15:32:17の下記の書き込み結果と同じです。
総ビットレート(kbps) は何も書き出されない
再生時間 はゼロ(0:00:00)と表示される
どこか間違いがあるのでしょうか ?
’------------------------------------
>僕のことはお気になさらず。解決するといいね
Ufjさん、了解です。
お手数をおかけしました。
(動画ファン) 2023/09/15(金) 17:36:33
そうですか 残念ですが力及ばす申し訳ありません (´・ω・`) 2023/09/16(土) 00:39:45
白茶さんのGetVideoProperties()を利用した場合でも問題の動画ファイルでは
ビットレートと再生時間が表示できませんでした。
結果は同じで
総ビットレート(kbps) は何も書き出されない
再生時間 はゼロ(0:00:00)と表示される
です。
結果が表示される場合とされない場合の動画(MP4)のどこが違うのかが現在判明できていません。
何か違いを探す手段はありませんか?
結果が表示されない動画でも私が利用している「MediaInfo」では問題なく
ビットレート(kbps) も再生時間も表示されるので何か違いを探す事はできそうに思えます。
参考 : MediaInfo
https://forest.watch.impress.co.jp/library/software/mediainfo/
(動画ファン) 2023/09/16(土) 06:05:57
参考:
https://excel-ubara.com/excelvba4/EXCEL_VBA_426.html
Sub sample2()
Dim rtnAry() As Variant rtnAry = getExtendedProperty("G:\test.aaa.mp4")
With ActiveSheet .Cells.Clear .Cells(2, "A") = rtnAry(27, 0) '長さ .Cells(2, "B") = rtnAry(27, 1) '再生時間 hh:mm:ss
End With End Sub
Function getExtendedProperty(ByVal aFilePath As String) As Variant()
Dim rtnAry() As Variant ReDim rtnAry(50, 1)
Dim fso As Object Set fso = CreateObject("Scripting.FileSystemObject")
Dim sh As Object Set sh = CreateObject("Shell.Application") Dim shFolder As Object Dim shFile As Object Set shFolder = sh.Namespace(fso.GetParentFolderName(aFilePath))
Dim i As Long Set shFile = shFolder.ParseName(fso.GetFileName(aFilePath))
'以下でも良い 'Set shFile = shFolder.Items.Item(fso.GetFileName(aFilePath))
For i = 0 To 30 rtnAry(i, 0) = shFolder.GetDetailsOf(Nothing, i) rtnAry(i, 1) = shFolder.GetDetailsOf(shFile, i) Next
getExtendedProperty = rtnAry
End Function
(動画ファン) 2023/09/16(土) 07:39:18
下記に変更します。
Sub sample3() Dim rtnAry() As Variant
rtnAry = getExtendedProperty("G:\test\AAA.mp4")
With ActiveSheet .Cells.Clear .Cells(1, "A") = rtnAry(0, 0) 'ファイル名 .Cells(1, "B") = rtnAry(0, 1)
.Cells(2, "A") = rtnAry(1, 0) 'サイズ .Cells(2, "B") = rtnAry(1, 1)
.Cells(3, "A") = rtnAry(27, 0) '再生時間 .Cells(3, "B") = rtnAry(27, 1)
.Cells(4, "A") = rtnAry(28, 0) '音声ビットレート .Cells(4, "B") = rtnAry(28, 1)
.Cells(5, "A") = rtnAry(320, 0) '総ビットレ−ト .Cells(5, "B") = rtnAry(320, 1) End With
End Sub
Function getExtendedProperty(ByVal aFilePath As String) As Variant() Dim rtnAry() As Variant ReDim rtnAry(500, 1)
Dim fso As Object Set fso = CreateObject("Scripting.FileSystemObject")
Dim sh As Object Set sh = CreateObject("Shell.Application")
Dim shFolder As Object Dim shFile As Object Set shFolder = sh.Namespace(fso.GetParentFolderName(aFilePath))
Dim i As Long
Set shFile = shFolder.ParseName(fso.GetFileName(aFilePath)) '以下でも良い 'Set shFile = shFolder.Items.Item(fso.GetFileName(aFilePath)) For i = 0 To 500 rtnAry(i, 0) = shFolder.GetDetailsOf(Nothing, i) rtnAry(i, 1) = shFolder.GetDetailsOf(shFile, i) Next
getExtendedProperty = rtnAry
End Function
(動画ファン) 2023/09/16(土) 08:56:11
[ 一覧(最新更新順) ]
YukiWiki 1.6.7 Copyright (C) 2000,2001 by Hiroshi Yuki.
Modified by kazu.