it-swarm-id.com

Bagaimana saya bisa menentukan panjang (mis. Durasi) file .wav di C #?

Dalam situasi terkompresi saya tahu saya perlu membaca header wav, mencabut jumlah saluran, bit, dan laju sampel dan menyelesaikannya dari sana: (saluran) * (bit) * (sampel/s) * (detik) = (filesize)

Apakah ada cara yang lebih sederhana - perpustakaan gratis, atau sesuatu dalam kerangka .net mungkin?

Bagaimana saya melakukan ini jika file .wav dikompresi (dengan codec mpeg misalnya)?

26
John Sibly

Anda dapat mempertimbangkan menggunakan fungsi mciSendString (...) (pengecekan kesalahan dihilangkan untuk kejelasan):

using System;
using System.Text;
using System.Runtime.InteropServices;

namespace Sound
{
    public static class SoundInfo
    {
        [DllImport("winmm.dll")]
        private static extern uint mciSendString(
            string command,
            StringBuilder returnValue,
            int returnLength,
            IntPtr winHandle);

        public static int GetSoundLength(string fileName)
        {
            StringBuilder lengthBuf = new StringBuilder(32);

            mciSendString(string.Format("open \"{0}\" type waveaudio alias wave", fileName), null, 0, IntPtr.Zero);
            mciSendString("status wave length", lengthBuf, lengthBuf.Capacity, IntPtr.Zero);
            mciSendString("close wave", null, 0, IntPtr.Zero);

            int length = 0;
            int.TryParse(lengthBuf.ToString(), out length);

            return length;
        }
    }
}
18
Jan Zich

Unduh NAudio.dll dari tautan http://naudio.codeplex.com/

dan kemudian gunakan fungsi ini

public static TimeSpan GetWavFileDuration(string fileName)       
{     
    WaveFileReader wf = new WaveFileReader(fileName);
    return wf.TotalTime; 
}

anda akan mendapatkan Durasi

29
Monti Pal

Tidak mengambil apa pun dari jawaban yang sudah diterima, tetapi saya bisa mendapatkan durasi file audio (beberapa format berbeda, termasuk AC3, yang saya butuhkan saat itu) menggunakan namespace Microsoft.DirectX.AudioVideoPlayBack. Ini adalah bagian dari DirectX 9.0 untuk Kode yang Dikelola . Menambahkan referensi ke yang membuat kode saya sesederhana ini ...

Public Shared Function GetDuration(ByVal Path As String) As Integer
    If File.Exists(Path) Then
        Return CInt(New Audio(Path, False).Duration)
    Else
        Throw New FileNotFoundException("Audio File Not Found: " & Path)
    End If
End Function

Dan itu juga cukup cepat! Berikut referensi untuk Audio kelas.

5
Josh Stodola
3
Cetra

Ya, Ada perpustakaan gratis yang dapat digunakan untuk mendapatkan durasi waktu file Audio. Perpustakaan ini juga menyediakan lebih banyak fungsi.

TagLib

TagLib didistribusikan di bawah GNU Lisensi Publik Rendah (LGPL) dan Lisensi Publik Mozilla (MPL).

Saya menerapkan kode di bawah ini yang mengembalikan durasi waktu dalam hitungan detik.

using TagLib.Mpeg;

public static double GetSoundLength(string FilePath)
{
    AudioFile ObjAF = new AudioFile(FilePath);
    return ObjAF.Properties.Duration.TotalSeconds;
}
2
Manish Nayak

Saya mengalami kesulitan dengan contoh kelas MediaPlayer di atas. Ini bisa memakan waktu, sebelum pemain membuka file. Di "dunia nyata" Anda harus mendaftar untuk acara MediaOpened, setelah itu dipecat, NaturalDuration valid. Dalam aplikasi konsol, Anda hanya perlu menunggu beberapa detik setelah pembukaan.

using System;
using System.Text;
using System.Windows.Media;
using System.Windows;

namespace ConsoleApplication2
{
  class Program
  {
    static void Main(string[] args)
    {
      if (args.Length == 0)
        return;
      Console.Write(args[0] + ": ");
      MediaPlayer player = new MediaPlayer();
      Uri path = new Uri(args[0]);
      player.Open(path);
      TimeSpan maxWaitTime = TimeSpan.FromSeconds(10);
      DateTime end = DateTime.Now + maxWaitTime;
      while (DateTime.Now < end)
      {
        System.Threading.Thread.Sleep(100);
        Duration duration = player.NaturalDuration;
        if (duration.HasTimeSpan)
        {
          Console.WriteLine(duration.TimeSpan.ToString());
          break;
        }
      }
      player.Close();
    }
  }
}
2
Lars

Coba kode di bawah ini dari Cara menentukan panjang file .wav di C #

    string path = @"c:\test.wav";
    WaveReader wr = new WaveReader(File.OpenRead(path));
    int durationInMS = wr.GetDurationInMS();
    wr.Close();
2
Aleks

Saya harus mengatakan MediaInfo , saya telah menggunakannya selama lebih dari setahun dengan aplikasi pengkodean audio/video yang sedang saya kerjakan. Ini memberikan semua informasi untuk file wav bersama dengan hampir setiap format lainnya.

MediaInfoDll Dilengkapi dengan kode sampel C # tentang cara membuatnya bekerja.

1
sieben

Anda mungkin menemukan bahwa perpustakaan XNA memiliki beberapa dukungan untuk bekerja dengan WAV dll. Jika Anda bersedia untuk turun rute itu. Ini dirancang untuk bekerja dengan C # untuk pemrograman game, jadi mungkin hanya mengurus apa yang Anda butuhkan.

1
xan

Ada sedikit tutorial (dengan - mungkin - kode kerja yang dapat Anda manfaatkan) di CodeProject .

Satu-satunya hal yang Anda harus sedikit berhati-hati adalah bahwa itu "normal" untuk file WAV yang terdiri dari beberapa potongan - jadi Anda harus menggeser seluruh file untuk memastikan bahwa semua potongan diperhitungkan.

1
moobaa

Apa sebenarnya aplikasi Anda lakukan dengan WAV terkompresi? File WAV terkompresi selalu rumit - Saya selalu mencoba dan menggunakan format wadah alternatif dalam kasus ini seperti file OGG atau WMA. Pustaka XNA cenderung dirancang untuk bekerja dengan format tertentu - meskipun mungkin dalam XACT Anda akan menemukan metode pemutaran wav yang lebih umum. Alternatif yang mungkin adalah melihat ke port SDL C #, meskipun saya hanya pernah menggunakannya untuk memainkan WAV terkompresi - setelah dibuka Anda dapat meminta jumlah sampel untuk menentukan panjangnya.

1
Bubba

saya telah menguji kode gagal akan gagal, format file seperti "\\ ip\dir\*. wav '

 public static class SoundInfo
   {
     [DllImport("winmm.dll")]
     private static extern uint mciSendString
     (
        string command,
        StringBuilder returnValue,
        int returnLength,
        IntPtr winHandle
     );

     public static int GetSoundLength(string fileName)
      {
        StringBuilder lengthBuf = new StringBuilder(32);

        mciSendString(string.Format("open \"{0}\" type waveaudio alias wave", fileName), null, 0, IntPtr.Zero);
        mciSendString("status wave length", lengthBuf, lengthBuf.Capacity, IntPtr.Zero);
        mciSendString("close wave", null, 0, IntPtr.Zero);

        int length = 0;
        int.TryParse(lengthBuf.ToString(), out length);

        return length;
    }
}

saat naudio bekerja

    public static int GetSoundLength(string fileName)
     {
        using (WaveFileReader wf = new WaveFileReader(fileName))
        {
            return (int)wf.TotalTime.TotalMilliseconds;
        }
     }`
0
item.wu

Saya akan berasumsi bahwa Anda agak terbiasa dengan struktur file .WAV: berisi struktur header WAVEFORMATEX, diikuti oleh sejumlah struct lainnya (atau "potongan") yang berisi berbagai jenis informasi. Lihat Wikipedia untuk info lebih lanjut tentang format file.

Pertama, beralihlah ke file .wav dan tambahkan panjang potongan "data" yang tidak murni (potongan "data" berisi data audio untuk file; biasanya hanya ada satu di antaranya, tetapi mungkin saja ada lebih dari satu). Anda sekarang memiliki ukuran total, dalam byte, dari data audio.

Selanjutnya, dapatkan anggota "rata-rata byte per detik" dari struct header WAVEFORMATEX file tersebut.

Terakhir, bagi ukuran total data audio dengan rata-rata byte per detik - ini akan memberi Anda durasi file, dalam detik.

Ini berfungsi cukup baik untuk file yang tidak dikompresi dan dikompresi.

0
GogglesPisano

waktu = FileLength/(Tingkat Sampel * Saluran * Bit per sampel/8)

0
Martin Abilev