2

我想要做的是:创建一个 MIDI 文件,但只在内存中,并将其输入pygame.mixer.music.load(). 这是我一直在尝试的(我从这里使用 MidiFile ):

import pygame.mixer
import MidiFile3
import io

pygame.mixer.init()

midi = MidiFile3.MIDIFile(1) # midi file with one track
midi.addTrackName(0,0,"Track 1") #Track Name on track 0, position 0
midi.addTempo(0,0,120) #Tempo to 120 bpm on track 0, position 0

for i in range(8):
    midi.addNote(0,0,60,i,1,100) #add 8 c1-notes to the track

bytestream = io.BytesIO()
midi.writeFile(bytestream)
pygame.mixer.music.load(bytestream.getvalue())

在这里我收到错误消息

pygame.error: File path 'MThd' contains null characters

当我做

bytestream = open('file.mid','wb')
midi.writeFile(bytestream)
bytestream.close()
pygame.mixer.music.load('file.mid')

它按预期工作。

当然,我知道包含文件名的字符串和包含文件内容的字节字符串之间是有区别的。但我在 Daniweb 上找到了这篇使用字节流的帖子,这个例子对我有用。

我只是不知道如何让我的例子起作用。

4

3 回答 3

1

music.load()函数需要一个文件名或文件对象。

bytestream.getvalue()是字节流的内容,看起来像一个文件名。

您必须使用文件/BytesIO对象本身:

pygame.mixer.music.load(bytestream)
于 2015-06-07T09:49:47.610 回答
1

我将问题修复如下:

bytestream = io.BytesIO()
midi.writeFile(bytestream)
temp = io.BytesIO(bytestream.getvalue())
pygame.mixer.music.load(temp)

看起来,该writeFile()操作以某种方式使 BytesIO 对象对该pygame.mixer.music.load()方法无效。通过使用正确创建的字节流再次使用 BytesIO 的构造函数,我们神奇地获得了可以传递给的有效字节流pygame.mixer.music.load()

于 2015-06-07T19:26:25.367 回答
0

公认的答案虽然有效,但不是正确的解决方案。写入字节流后,您需要做的就是将指针重置为开头。正确的代码(部分)如下:

bytestream = io.BytesIO()
midi.writeFile(bytestream)
bytestream.seek(0)
pygame.mixer.music.load(bytestream)

我实际上在这里回答了一个类似的问题。

于 2017-04-21T00:32:24.977 回答