Differenze tra le versioni di "Eseguire un file WAV mediante le funzioni esterne del API di PulseAudio"
Da Gambas-it.org - Wikipedia.
(11 versioni intermedie di uno stesso utente non sono mostrate) | |||
Riga 1: | Riga 1: | ||
Per la esigua quantità di funzioni necessarie e la loro semplicità d'uso mostreremo di seguito direttamente un codice esemplificativo, ma debitamente spiegato, con il quale eseguire un file WAV. | Per la esigua quantità di funzioni necessarie e la loro semplicità d'uso mostreremo di seguito direttamente un codice esemplificativo, ma debitamente spiegato, con il quale eseguire un file WAV. | ||
− | Library "libpulse-simple:0. | + | |
+ | E' necessario avere installata nel sistema e richiamare in Gambas la libreria condivisa: "''libpulse-simple.so.0.1.1''". | ||
+ | Library "libpulse-simple:0.1.1" | ||
<FONT color=gray>' ''Dichiariamo una "Struttura" per passare i valori dei campioni audio necessari per l'esecuzione dei dati audio del file WAV:''</font> | <FONT color=gray>' ''Dichiariamo una "Struttura" per passare i valori dei campioni audio necessari per l'esecuzione dei dati audio del file WAV:''</font> | ||
Riga 12: | Riga 14: | ||
Private Const PA_SAMPLE_S16LE As Byte = 3 <FONT color=gray>' ''Signed 16 Bit PCM, little endian (PC)''</font> | Private Const PA_SAMPLE_S16LE As Byte = 3 <FONT color=gray>' ''Signed 16 Bit PCM, little endian (PC)''</font> | ||
− | <FONT color=gray size=1>' ''pa_simple* pa_simple_new (const char *server, const char *name, pa_stream_direction_t dir, const char *dev, const char *stream_name, const pa_sample_spec *ss, const pa_channel_map *map, const pa_buffer_attr *attr, int *error)'' | + | <FONT color=gray size=1>' ''pa_simple* pa_simple_new (const char *server, const char *name, pa_stream_direction_t dir, const char *dev, const char *stream_name, const pa_sample_spec *ss, const pa_channel_map *map, const pa_buffer_attr *attr, int *error)''</font> |
− | ' ''Crea una connessione col server sonoro.''</font> | + | <FONT color=gray size=2>' ''Crea una connessione col server sonoro.''</font> |
− | <FONT size= | + | <FONT size=2>Private Extern pa_simple_new(server$ As String, name As String, direct As Byte, dev As String, stream_name As String, ss As Pa_sample_spec, map As Pointer, attr As Pointer, err As Pointer) As Pointer</font> |
<FONT color=gray>' ''int pa_simple_write (pa_simple *s, const void *data, size_t bytes, int *error)'' | <FONT color=gray>' ''int pa_simple_write (pa_simple *s, const void *data, size_t bytes, int *error)'' | ||
' ''Scrive una certa quantità di dati nel server sonoro.''</font> | ' ''Scrive una certa quantità di dati nel server sonoro.''</font> | ||
− | Private Extern pa_simple_write(sP As Pointer, | + | Private Extern pa_simple_write(sP As Pointer, data As Pointer, bytes As Integer, err As Pointer) As Integer |
<FONT color=gray>' ''int pa_simple_drain (pa_simple *s, int *error)'' | <FONT color=gray>' ''int pa_simple_drain (pa_simple *s, int *error)'' | ||
Riga 29: | Riga 31: | ||
− | + | Public Sub Main() | |
Dim pss As New Pa_sample_spec | Dim pss As New Pa_sample_spec | ||
Riga 40: | Riga 42: | ||
Dim fl As File | Dim fl As File | ||
− | + | fileWAV = "<FONT color=darkgreen>>''/percorso/del/file.wav''</font>" | |
− | + | fl = Open fileWAV For Read | |
− | + | dimensione = Lof(fl) | |
<FONT color=gray>' ''Vengono assegnati ai rispettivi membri della "Struttura" i necessari valori per l'esecuzione del file wav.'' | <FONT color=gray>' ''Vengono assegnati ai rispettivi membri della "Struttura" i necessari valori per l'esecuzione del file wav.'' | ||
' ''Vengono, altresì, mostrate alcune informazioni sul file wav:''</font> | ' ''Vengono, altresì, mostrate alcune informazioni sul file wav:''</font> | ||
− | + | With pss | |
− | + | .formato = PA_SAMPLE_S16LE | |
− | + | Seek #fl, 22 | |
− | + | .channels = Read #fl As Short | |
− | + | .rate = Read #fl As Integer | |
− | + | Print "File wav: "; fileWAV | |
− | + | Print "Canali: "; .channels | |
− | + | Print "Frequenza: "; .rate; " hertz" | |
− | + | Seek #fl, 34 | |
− | + | bit = Read #fl As Short | |
− | + | Print "Risoluzione: "; bit; " bit" | |
− | + | obr = .rate * bit * .channels | |
− | + | Print "Durata: "; Time(0, 0, 0, ((dimensione * 8) / obr) * 1000) | |
− | + | End With | |
+ | Print | ||
<FONT color=gray>' ''Viene quindi creata una connessione con il server sonoro per il flusso di dati audio da eseguire.'' | <FONT color=gray>' ''Viene quindi creata una connessione con il server sonoro per il flusso di dati audio da eseguire.'' | ||
Riga 74: | Riga 77: | ||
' ''- Null: vengono usati attributi di buffering di default;'' | ' ''- Null: vengono usati attributi di buffering di default;'' | ||
' ''- Null: vengono ignorati i codici di errore sollevati.''</font> | ' ''- Null: vengono ignorati i codici di errore sollevati.''</font> | ||
− | + | p = pa_simple_new(Null, "nome qualsiasi", PA_STREAM_PLAYBACK, Null, "testo qualsiasi", pss, 0, 0, 0) | |
− | + | If p == 0 Then Error.Raise("Impossible inizializzare la libreria 'Pulseaudio' !") | |
− | + | ||
+ | Seek #fl, 0 | ||
− | + | buf = New Byte[DimBuffer] | |
<FONT color=gray>' ''Viene eseguito un ciclo per la lettura dei dati audio dal file, e per la successiva scrittura nel server sonoro:''</font> | <FONT color=gray>' ''Viene eseguito un ciclo per la lettura dei dati audio dal file, e per la successiva scrittura nel server sonoro:''</font> | ||
− | + | Repeat | |
− | + | ||
<FONT color=gray>' ''Viene evitato l'errore di "Out of bound" nel vettore "buf[]":''</font> | <FONT color=gray>' ''Viene evitato l'errore di "Out of bound" nel vettore "buf[]":''</font> | ||
− | + | If dimensione - Seek(fl) < DimBuffer Then DimBuffer = dimensione - Seek(fl) | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | <FONT color=gray>' ''Usa un vettore di tipo "Byte[]", che viene ad ogni ciclo riempito da una quantità di dati pari al valore stabilito:''</font> | |
− | + | buf.Read(fl, 0, DimBuffer) | |
− | <FONT color=gray>' '' | + | <FONT color=gray>' ''La funzione "pa_simple_write" prevede un ''Puntatore'' al buffer contenente i dati da scrivere:''</font> |
− | + | pa_simple_write(p, buf.Data, DimBuffer, 0) | |
− | ' '' | ||
− | |||
<FONT color=gray>' ''Mostra il tempo trascorso dall'inizio dell'esecuzione del file audio:''</font> | <FONT color=gray>' ''Mostra il tempo trascorso dall'inizio dell'esecuzione del file audio:''</font> | ||
− | + | Write "\r" & CStr(Time(0, 0, 0, ((Seek(fl) * 8) / obr) * 1000)) | |
− | + | Until Seek(fl) >= dimensione | |
− | + | ||
− | + | pa_simple_drain(p, 0) | |
− | + | ||
− | |||
<FONT color=gray>' ''Va in Chiusura:''</font> | <FONT color=gray>' ''Va in Chiusura:''</font> | ||
− | + | Print "Esecuzione terminata !" | |
− | + | fl.Close | |
− | + | pa_simple_free(p) | |
− | + | ||
− | + | End | |
Versione attuale delle 10:35, 26 nov 2023
Per la esigua quantità di funzioni necessarie e la loro semplicità d'uso mostreremo di seguito direttamente un codice esemplificativo, ma debitamente spiegato, con il quale eseguire un file WAV.
E' necessario avere installata nel sistema e richiamare in Gambas la libreria condivisa: "libpulse-simple.so.0.1.1".
Library "libpulse-simple:0.1.1" ' Dichiariamo una "Struttura" per passare i valori dei campioni audio necessari per l'esecuzione dei dati audio del file WAV: Public Struct pa_sample_spec formato As Integer rate As Integer channels As Byte End Struct Private Const PA_STREAM_PLAYBACK As Byte = 1 Private Const PA_SAMPLE_S16LE As Byte = 3 ' Signed 16 Bit PCM, little endian (PC) ' pa_simple* pa_simple_new (const char *server, const char *name, pa_stream_direction_t dir, const char *dev, const char *stream_name, const pa_sample_spec *ss, const pa_channel_map *map, const pa_buffer_attr *attr, int *error) ' Crea una connessione col server sonoro. Private Extern pa_simple_new(server$ As String, name As String, direct As Byte, dev As String, stream_name As String, ss As Pa_sample_spec, map As Pointer, attr As Pointer, err As Pointer) As Pointer ' int pa_simple_write (pa_simple *s, const void *data, size_t bytes, int *error) ' Scrive una certa quantità di dati nel server sonoro. Private Extern pa_simple_write(sP As Pointer, data As Pointer, bytes As Integer, err As Pointer) As Integer ' int pa_simple_drain (pa_simple *s, int *error) ' Attende sino a quando tutti i dati scritti nel server sonoro vengono eseguiti. Private Extern pa_simple_drain(sP As Pointer, err As Pointer) As Integer ' void pa_simple_free (pa_simple *s) ' Chiude e libera la connessione con il server sonoro. Private Extern pa_simple_free(sP As Pointer) Public Sub Main() Dim pss As New Pa_sample_spec Dim DimBuffer As Short = 1024 Dim bit As Short Dim fileWAV As String Dim p As Pointer Dim dimensione, obr As Integer Dim buf As Byte[] Dim fl As File fileWAV = ">/percorso/del/file.wav" fl = Open fileWAV For Read dimensione = Lof(fl) ' Vengono assegnati ai rispettivi membri della "Struttura" i necessari valori per l'esecuzione del file wav. ' Vengono, altresì, mostrate alcune informazioni sul file wav: With pss .formato = PA_SAMPLE_S16LE Seek #fl, 22 .channels = Read #fl As Short .rate = Read #fl As Integer Print "File wav: "; fileWAV Print "Canali: "; .channels Print "Frequenza: "; .rate; " hertz" Seek #fl, 34 bit = Read #fl As Short Print "Risoluzione: "; bit; " bit" obr = .rate * bit * .channels Print "Durata: "; Time(0, 0, 0, ((dimensione * 8) / obr) * 1000) End With Print ' Viene quindi creata una connessione con il server sonoro per il flusso di dati audio da eseguire. ' Riguardo ai parametri impostati nella seguente funzione si precisa che: ' - NUll: viene usato il server sonoro di default; ' - "nome qualsiasi": il nome dell'applicazione; ' - PA_STREAM_PLAYBACK: stabilisce che il flusso sarà in uscita, ossia in esecuzione di un file WAV; ' - Null: viene usato il dispositivo sonoro di default; ' - "testo qualsiasi": una testo descrittivo del flusso dati audio del file; ' - pss: le caratteristiche dei campioni audio del flusso di dati; ' - Null: viene usata la mappatura dei canali di default; ' - Null: vengono usati attributi di buffering di default; ' - Null: vengono ignorati i codici di errore sollevati. p = pa_simple_new(Null, "nome qualsiasi", PA_STREAM_PLAYBACK, Null, "testo qualsiasi", pss, 0, 0, 0) If p == 0 Then Error.Raise("Impossible inizializzare la libreria 'Pulseaudio' !") Seek #fl, 0 buf = New Byte[DimBuffer] ' Viene eseguito un ciclo per la lettura dei dati audio dal file, e per la successiva scrittura nel server sonoro: Repeat ' Viene evitato l'errore di "Out of bound" nel vettore "buf[]": If dimensione - Seek(fl) < DimBuffer Then DimBuffer = dimensione - Seek(fl) ' Usa un vettore di tipo "Byte[]", che viene ad ogni ciclo riempito da una quantità di dati pari al valore stabilito: buf.Read(fl, 0, DimBuffer) ' La funzione "pa_simple_write" prevede un Puntatore al buffer contenente i dati da scrivere: pa_simple_write(p, buf.Data, DimBuffer, 0) ' Mostra il tempo trascorso dall'inizio dell'esecuzione del file audio: Write "\r" & CStr(Time(0, 0, 0, ((Seek(fl) * 8) / obr) * 1000)) Until Seek(fl) >= dimensione pa_simple_drain(p, 0) ' Va in Chiusura: Print "Esecuzione terminata !" fl.Close pa_simple_free(p) End