[英]Rendering a float array to 24-bit RGB image (using PIL for example)
x
is a numpy.float32
array, with values from -200
to 0
. x
是一个numpy.float32
数组,值从-200
到0
。 These are dB (decibel) values. 这些是dB(分贝)值。
When I do (as recommended here ): 当我这样做(如建议在这里 ):
Image.fromarray(x, mode='F')
I get a greyscale or sometimes nearly black image. 我得到灰度或有时接近黑色的图像。
How to map a float in [-200, 0] to a 24-bit RGB byte array (using a colormap) that can be read with the Python module PIL with Image.fromarray(x, mode='RGB')
? 如何将[-200,0]中的float映射到24位RGB字节数组(使用颜色图),可以使用Python模块PIL的
Image.fromarray(x, mode='RGB')
读取该数组?
The required .wav audio file is here , for which we want to plot the spectrogram . 所需的.wav音频文件在这里 ,我们要为其绘制频谱图 。
Here is some code to test: 这是一些代码要测试:
import scipy, numpy as np
import scipy.io.wavfile as wavfile
import numpy as np
from PIL import Image
def stft(x, fftsize=1024, overlap=4):
hop = fftsize / overlap
w = scipy.hanning(fftsize+1)[:-1]
return np.array([np.fft.rfft(w*x[i:i+fftsize]) for i in range(0, len(x)-fftsize, hop)])
def dB(ratio):
return 20 * np.log10(ratio+1e-10)
def magnitudedB(frame, fftsize=1024):
w = scipy.hanning(fftsize+1)[:-1]
ref = np.sum(w) / 2
return dB(np.abs(frame) / ref)
sr, x = wavfile.read('test.wav')
x = np.float32(x) / 2**15
s = magnitudedB(stft(x)).astype(np.float32).transpose()[::-1,]
print "Max %.1f dB, Min %.1f dB" % (np.max(s), np.min(s))
im = Image.fromarray(s+200, mode='F')
im.show()
Notes: 笔记:
The colormap is greyscale, how to get another colormap? 颜色图是灰度的,如何获得另一个颜色图? like this one
喜欢这个
My only requirement is that the output image can be read into a Tkinter frame / canvas (it works well with PIL's im = Image.fromarray(...)
then ImageTk.PhotoImage(image=im)
) or wxPython frame / canvas. 我唯一的要求是可以将输出图像读入Tkinter框架/画布(与PIL的
im = Image.fromarray(...)
然后ImageTk.PhotoImage(image=im)
)或wxPython框架/画布。
Based on the answer here , you can use matplotlib colormaps to transform the numpy array before converting to an image. 根据此处的答案,您可以在转换为图像之前使用matplotlib 颜色图转换numpy数组。
#im = Image.fromarray(s+200, mode='F')
from matplotlib import cm
s = (s + 200)/200.0 # input data should range from 0-1
im = Image.fromarray(cm.jet(s, bytes=True))
im.show()
You should probably set the scaling appropriately based on your min/max values. 您可能应该根据最小/最大值适当地设置缩放比例。
Sample output: 样本输出:
To plot images using colormaps I'd suggest you to use matplotlib.pyplot.imshow . 要使用颜色图绘制图像,建议您使用matplotlib.pyplot.imshow 。
The result of doing so with your test.wav
file would be something like this: 使用
test.wav
文件执行此操作的结果将是这样的:
For more detailed information about creating audio spectrograms using python you can read more about it here 有关使用python创建音频频谱图的更多详细信息,您可以在此处了解更多信息
I can't find any details on mode='F' in the documentation, but I would expect it to take pixel values in a range like 0.0 - 1.0. 我在文档中找不到有关mode ='F'的任何详细信息,但是我希望它采用0.0-1.0之类的像素值。 Your values are entirely below that range, thus the black image;
您的值完全低于该范围,因此是黑色图像; you will need to transform them.
您将需要对其进行转换。
Getting a colormapped image (instead of grayscale) would require mode='P', which would require that you transform your data into an array of bytes. 要获取带有颜色映射的图像(而不是灰度图像),需要使用mode ='P',这将需要将数据转换为字节数组。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.