From 5e0ba19538763e77c6638175d981e4c0b38e2d1d Mon Sep 17 00:00:00 2001 From: Martin Kaistra Date: Mon, 2 Mar 2015 22:47:52 +0100 Subject: first commit --- core.py | 135 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 135 insertions(+) create mode 100644 core.py (limited to 'core.py') diff --git a/core.py b/core.py new file mode 100644 index 0000000..ac957e7 --- /dev/null +++ b/core.py @@ -0,0 +1,135 @@ +import sys, io +from PyQt4 import QtCore, QtGui, uic +from PyQt4.QtGui import QPainter, QColor +from os.path import expanduser +import subprocess as sp +import numpy +from PIL import Image, ImageDraw, ImageFont +from PIL.ImageQt import ImageQt + +class Core(): + + def __init__(self): + self.lastBackgroundImage = "" + self._image = None + + if sys.platform == "win32": + self.FFMPEG_BIN = "ffmpeg.exe" + else: + self.FFMPEG_BIN = "ffmpeg" # on Linux and Mac OS + + def drawBaseImage(self, backgroundImage, titleText, titleFont): + + if self._image == None or not self.lastBackgroundImage == backgroundImage: + self.lastBackgroundImage = backgroundImage + + if backgroundImage == "": + im = Image.new("RGB", (1280, 720), "black") + else: + im = Image.open(backgroundImage) + + # resize if necessary + if not im.size == (1280, 720): + im = im.resize((1280, 720), Image.ANTIALIAS) + + self._image = ImageQt(im) + + self._image1 = QtGui.QImage(self._image) + painter = QPainter(self._image1) + font = titleFont + font.setPointSizeF(35) + painter.setFont(font) + painter.setPen(QColor(255, 255, 255)) + + painter.drawText(70, 375, titleText) + painter.end() + + buffer = QtCore.QBuffer() + buffer.open(QtCore.QIODevice.ReadWrite) + self._image1.save(buffer, "PNG") + + strio = io.BytesIO() + strio.write(buffer.data()) + buffer.close() + strio.seek(0) + return Image.open(strio) + + def drawBars(self, spectrum, image): + + imTop = Image.new("RGBA", (1280, 360)) + draw = ImageDraw.Draw(imTop) + for j in range(0, 63): + draw.rectangle((10 + j * 20, 325, 10 + j * 20 + 20, 325 - spectrum[j * 4] * 1 - 10), fill=(255, 255, 255, 50)) + draw.rectangle((15 + j * 20, 320, 15 + j * 20 + 10, 320 - spectrum[j * 4] * 1), fill="white") + + + imBottom = imTop.transpose(Image.FLIP_TOP_BOTTOM) + + im = Image.new("RGB", (1280, 720), "black") + + im.paste(image, (0, 0)) + im.paste(imTop, (0, 0), mask=imTop) + im.paste(imBottom, (0, 360), mask=imBottom) + + return im + + def readAudioFile(self, filename): + command = [ self.FFMPEG_BIN, + '-i', filename, + '-f', 's16le', + '-acodec', 'pcm_s16le', + '-ar', '44100', # ouput will have 44100 Hz + '-ac', '1', # mono (set to '2' for stereo) + '-'] + in_pipe = sp.Popen(command, stdout=sp.PIPE, stderr=sp.DEVNULL, bufsize=10**8) + + completeAudioArray = numpy.empty(0, dtype="int16") + + while True: + # read 2 seconds of audio + raw_audio = in_pipe.stdout.read(88200*4) + if len(raw_audio) == 0: + break + audio_array = numpy.fromstring(raw_audio, dtype="int16") + completeAudioArray = numpy.append(completeAudioArray, audio_array) + # print(audio_array) + + in_pipe.kill() + in_pipe.wait() + + # add 0s the end + completeAudioArrayCopy = numpy.zeros(len(completeAudioArray) + 44100, dtype="int16") + completeAudioArrayCopy[:len(completeAudioArray)] = completeAudioArray + completeAudioArray = completeAudioArrayCopy + + return completeAudioArray + + def transformData(self, i, completeAudioArray, sampleSize, smoothConstantDown, smoothConstantUp, lastSpectrum): + if len(completeAudioArray) < (i + sampleSize): + sampleSize = len(completeAudioArray) - i + + window = numpy.hanning(sampleSize) + data = completeAudioArray[i:i+sampleSize][::1] * window + paddedSampleSize = 2048 + paddedData = numpy.pad(data, (0, paddedSampleSize - sampleSize), 'constant') + spectrum = numpy.fft.fft(paddedData) + sample_rate = 44100 + frequencies = numpy.fft.fftfreq(len(spectrum), 1./sample_rate) + + y = abs(spectrum[0:paddedSampleSize/2 - 1]) + + # filter the noise away + # y[y<80] = 0 + + y = 20 * numpy.log10(y) + y[numpy.isinf(y)] = 0 + + if lastSpectrum is not None: + lastSpectrum[y < lastSpectrum] = y[y < lastSpectrum] * smoothConstantDown + lastSpectrum[y < lastSpectrum] * (1 - smoothConstantDown) + lastSpectrum[y >= lastSpectrum] = y[y >= lastSpectrum] * smoothConstantUp + lastSpectrum[y >= lastSpectrum] * (1 - smoothConstantUp) + else: + lastSpectrum = y + + x = frequencies[0:paddedSampleSize/2 - 1] + + return lastSpectrum \ No newline at end of file -- cgit v1.2.3