Python, eine beliebte Web-Trinkparty, erkennt einen stillen Zustand und spielt eine Stimme.

Vorwort

Web-Trinkparty, die beliebt ist, weil die Welt die Welt ist.

Nach einer bestimmten Anzahl von Besprechungen wird es jedoch immer einen Zeitpunkt geben, an dem niemand spricht. Erstens bleibt jeder die ganze Zeit zu Hause, daher wird nicht viel darüber gesprochen. Ich bin sicher, einige Leute denken, dass sie nicht an einer solchen Trinkparty teilnehmen sollten, aber es ist schwierig, weil es keinen Grund gibt, dies abzulehnen.

01.png

Egal wie nah Sie sind, die Trinkparty wird still sein, wenn es keinen Inhalt mehr gibt, über den Sie sprechen können.

Die Trinkparty selbst wird faul fortgesetzt. Wenn Sie sich also unwohl fühlen, machen Sie sich keine Sorgen. Eine solche Situation ist aus irgendeinem Grund die schlimmste.

Daher möchte ich dieses Mal, um den stillen Zustand ** (unangenehmer Zustand aufgrund von) ** in der Web-Trinkparty zu vermeiden, ein Programm in Python erstellen, das den stillen Zustand erkennt und eine Stimme spielt. (Es ist eine Erleichterung)

Ziel

Normalerweise verwende ich Zoom für Besprechungen wie Webbesprechungen, daher möchte ich es mit ** Zoom ** verwenden.

In der Realität wird jedoch der Sound des gesamten Systems überwacht, sodass wahrscheinlich jede Software damit umgehen kann.

Ziel ist es, den Audioeingang von Zoom 10 Sekunden lang zu überwachen. Wenn festgestellt wird, dass kein Eingang = kein Ton vorhanden ist, wird die Musikdatei zufällig aus dem angegebenen Ordner abgespielt.

Umgebung

Ich habe mit einer Idee angefangen, also benutze ich ** Python ** als Programmiersprache, aber es hat nichts zu bedeuten. Die Betriebsumgebung ist wie folgt.

■Windows10 ■Python3.7

Die verwendeten Bibliotheken sind wie folgt.


import pyaudio
import numpy as np
import wave
import math

from mutagen.mp3 import MP3 as mp3
import pygame
import time

import glob
import random
import sys

Ich persönlich wollte Zoom mit der bestmöglichen Klangqualität verwenden, daher habe ich ein separates Audio-Interface und ein Mikrofon (wahrscheinlich ist der Ton auf der Zoom-Seite ziemlich stark abgeschnitten, daher macht es nicht viel Sinn, ich bin autark). ..

03.jpg

■marantz / AUDIO SCOPE SG-5BC ■CREATIVE / SB X-Fi Surround 5.1

Jetzt schreiben wir das Programm.

Quellcode

audio = pyaudio.PyAudio()

def system(FORMAT, CHANNELS, RATE, CHUNK):

    stream = audio.open(format=FORMAT,
                        channels=CHANNELS,
                        rate=RATE,
                        input=True,
                        output=True,
                        input_device_index=1,#← Bitte wechseln Sie zu einem geeigneten Index.
                        output_device_index=7,#← Bitte wechseln Sie zu einem geeigneten Index.
                        frames_per_buffer=CHUNK)

    return stream

Zuerst instanziieren wir und verwenden pyaudio.PyAudio (), um den Audioeingang durch das Mikrofon zu überwachen.

Die zu überwachende Eingangsstimme wird aus dem numerischen Wert von "input_device_index" angegeben. Wenn Sie den Wert des Geräteindex nicht kennen, können Sie ihn mit dem folgenden Code nachschlagen.

for index in range(0, p.get_device_count()):
    print(p. get_device_info_by_index(index))

Am Beispiel meiner Umgebung lautet die Ausgabe wie folgt.

{'index': 0, 'structVersion': 2, 'name': 'Microsoft Sound Mapper- Input', 'hostApi': 0, 'maxInputChannels': 2, 'maxOutputChannels': 0, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 1, 'structVersion': 2, 'name': 'Wiedergabe-Weiterleitung(SB X-Fi Surround 5.1)', 'hostApi': 0, 'maxInputChannels': 2, 'maxOutputChannels': 0, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 2, 'structVersion': 2, 'name': 'Linie(USB2.0 High-Speed True HD ', 'hostApi': 0, 'maxInputChannels': 2, 'maxOutputChannels': 0, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 3, 'structVersion': 2, 'name': 'Linie/Mikrofoneingang(SB X-Fi Surround 5.1', 'hostApi': 0, 'maxInputChannels': 2, 'maxOutputChannels': 0, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 4, 'structVersion': 2, 'name': 'SPDIF In (USB2.0 High-Speed Tru', 'hostApi': 0, 'maxInputChannels': 2, 'maxOutputChannels': 0, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 5, 'structVersion': 2, 'name': 'Mikrofon(USB2.0 High-Speed True HD ', 'hostApi': 0, 'maxInputChannels': 2, 'maxOutputChannels': 0, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 6, 'structVersion': 2, 'name': 'Microsoft Sound Mapper- Output', 'hostApi': 0, 'maxInputChannels': 0, 'maxOutputChannels': 2, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 7, 'structVersion': 2, 'name': 'Lautsprecher(SB X-Fi Surround 5.1)', 'hostApi': 0, 'maxInputChannels': 0, 'maxOutputChannels': 6, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 8, 'structVersion': 2, 'name': 'SPDIF-Ausgabe(SB X-Fi Surround 5.1)', 'hostApi': 0, 'maxInputChannels': 0, 'maxOutputChannels': 6, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 9, 'structVersion': 2, 'name': 'SPDIF Out (USB2.0 High-Speed Tr', 'hostApi': 0, 'maxInputChannels': 0, 'maxOutputChannels': 2, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}
{'index': 10, 'structVersion': 2, 'name': 'Lautsprecher(USB2.0 High-Speed True H', 'hostApi': 0, 'maxInputChannels': 0, 'maxOutputChannels': 8, 'defaultLowInputLatency': 0.09, 'defaultLowOutputLatency': 0.09, 'defaultHighInputLatency': 0.18, 'defaultHighOutputLatency': 0.18, 'defaultSampleRate': 44100.0}

In meiner Umgebung sind mehrere Audio-Interfaces verbunden, daher gibt es viele solche Indizes.

Dieses Mal muss nicht nur die Eingabestimme gelesen werden, sondern auch der Status der anderen sprechenden Partei und der Status des freigegebenen Bildschirms mit Zoom.

Daher wird in diesem Fall als Index die Wiedergabeumleitung 1 verwendet, um das gesamte System zu überwachen. Überprüfen Sie diesen Wert selbst und ersetzen Sie ihn durch einen geeigneten Wert.

Es gibt ein Element, das "output_device_index" angibt. Dies wird jedoch angegeben, weil Sie eine Audiodatei im "wav" -Format abspielen möchten. Dieser Punkt ist nicht erforderlich, insbesondere wenn Sie nicht vorhaben, die wav-Datei abzuspielen. Erstens wird es absichtlich zu einer Funktion gemacht. Wenn Sie also keinen Plan haben, können Sie "FORMAT, CHANNELS, RATE, CHUNK" angeben, ohne es zu einer Funktion zu machen.

frames = []

def surveillance():

    print("Under surveillance...")

    FORMAT = pyaudio.paInt16
    CHANNELS = 1  #monaural
    RATE = 44100  #Beispielrate
    CHUNK = 2 ** 11  #Datenbewertung
    RECORD_SECONDS = 10  #Aufnahmedauer

    stream = system(FORMAT, CHANNELS, RATE, CHUNK)

    for i in range(0, int(RATE / CHUNK * RECORD_SECONDS)):
        buf = stream.read(CHUNK)
        data = np.frombuffer(buf, dtype="int16")
        frames.append(max(data))

    stream.stop_stream()

    calculation()

Der Funktionsname lautet "monitor".

Hier wird die Stimme 10 Sekunden lang in Python eingegeben, und der ** maximale positive Wert ** der Sprachwellenform pro Sekunde wird extrahiert und zu "Frames" hinzugefügt.

Um es ein wenig zu erklären, in diesem Fall "RATE = 44100", also beträgt die Abtastfrequenz 44,1 kHz. Dies bedeutet, dass wir 44100 Lautstärkepegel pro Sekunde erhalten. Ein Klang ist eine Welle, und solange es sich um eine Welle handelt, sind natürlich negative Werte enthalten. Wenn Sie alle 1 / 44,1 Sekunden den genauen Pegel ermitteln möchten, müssen Sie den absoluten Wert ermitteln. Diesmal wird jedoch nur der Maximalwert gespeichert, da es ausreicht, innerhalb von 10 Sekunden zu beurteilen, ob ein Ton zu hören ist.

Der erfasste Wert wird durch "np.frombuffer" in 2 ** 16 Schritte mit einem Dynamikbereich von 16 Bit umgewandelt. Wie bereits erwähnt, hat es jedoch positive und negative Werte, sodass der Maximalwert 32767 beträgt.

def calculation():

    print("Calculation")

    rms = (max(frames))

    db = 20 * math.log10(rms) if rms > 0.0 else -math.inf
    print(f"RMS:{format(db, '3.1f')}[dB]")

    if (db<=65):#← Bitte passen Sie die Anzahl an die Umgebung an
        random_music()
        #disc_jockey()

    else:
        pass

    frames.clear()

Als nächstes folgt die Funktion, die den Ruhezustand bestimmt.

Protokollieren Sie die erfassten Werte, um das Verständnis der Pegeländerungen zu erleichtern. Bestimmen Sie den Schwellenwert und verzweigen Sie mit if. In meiner Umgebung scheinen ungefähr 65 dB ein guter Wert zu sein. Ändern Sie diesen Wert entsprechend Ihrer eigenen Umgebung.

def random_music():

    print("Random music")

    files = [r.split('/')[-1] for r in glob.glob('./data/*.mp3')]
    filename = random.choice(files)  #Die MP3-Datei, die Sie abspielen möchten
    print(filename)

    pygame.mixer.init()
    pygame.mixer.music.load(filename)  #Laden Sie die Tonquelle
    mp3_length = mp3(filename).info.length  #Holen Sie sich die Länge der Tonquelle
    pygame.mixer.music.play(1)  #Die Wiedergabe beginnt. Spielen Sie n Mal, wenn Teil 1 geändert wird(In diesem Fall auch xn die Anzahl der Sekunden in der nächsten Zeile.)
    time.sleep(mp3_length + 0.25)  #Warten Sie nach dem Start der Wiedergabe auf die Länge der Tonquelle(0.Warten auf 25 ist Fehlerbehebung)
    pygame.mixer.music.stop()  #Die Wiedergabe stoppt, nachdem auf die Länge der Tonquelle gewartet wurde

Schließlich ist es ein Programm, das zufällig MP3-Dateien aus beliebigen Ordnern extrahiert und wiedergibt. In meinem Fall habe ich es in "Daten" direkt unter dem Quellcode-Verzeichnis abgelegt.

try:
    while True:
        surveillance()

except KeyboardInterrupt:
    print("Emergency stop")
    sys.exit(0)

stream.close()
audio.terminate()

Danach wird das Programm geloopt und überwacht.

Wenn die Stille dringend unterbrochen wird, endet sie mit "Strg + C".

def disc_jockey():

    print("Play...")

    filename = "./disc_jockey.wav"
    wf = wave.open(filename, "rb")

    FORMAT = audio.get_format_from_width(wf.getsampwidth())
    CHANNELS = wf.getnchannels()
    RATE = wf.getframerate()
    CHUNK = wf.getnframes()

    stream = system(FORMAT, CHANNELS, RATE, CHUNK)

    data = wf.readframes(CHUNK)
    stream.write(data)

    stream.start_stream()
    stream.stop_stream()
    stream.close()

    random_music()

Übrigens habe ich am Anfang erwähnt, dass ich auch "wav" spielen möchte, also werde ich beschreiben, wie es geht.

Es ist im Grunde dasselbe wie die Aufzeichnungsmethode, aber in diesem Fall ist es notwendig, den Wert gemäß dem Status der Datei zu bestimmen, so dass jeder Wert durch "Welle" erfasst und ersetzt wird.

Der Grund, warum der Funktionsname DJ lautet, ist, dass ** selbst wenn die Musik plötzlich abgespielt wird, die andere Partei unklar ist. ** Ich habe sie hier mit der Absicht erstellt, eine Song-Einführungsstimme einzufügen.

Und die Daten, die ich hatte, waren ** Chris 〇Puller ** 's "Lass uns hier zum Lied gehen" und ** Ioin Hikaru **' s Voice wav Datei. Jetzt das.

02.png

Ich weiß nicht warum.

Zusammenfassung

Ich konnte wegen eines bestimmten Virus nicht nach draußen gehen, und die stille Web-Trinkparty findet immer noch statt, aber lassen Sie uns alle unser Bestes geben.

Recommended Posts

Python, eine beliebte Web-Trinkparty, erkennt einen stillen Zustand und spielt eine Stimme.
Erstellen Sie eine Webmap mit Python und GDAL
Starten Sie einen Webserver mit Python und Flask
Holen Sie sich Python-Webseite, Zeichenkodierung und Anzeige
Erstellen einer Web-App für die Sprachtranskription
[Python] gibt A [oder / und] B zurück
Lassen Sie uns JavaScript wegwerfen und ein Web-Frontend in Python schreiben!
Ich möchte eine Webanwendung mit React und Python Flask erstellen