This serie mainly tackles the playback of wave tracks with loops. Current code had to be improved as: - loop playback doesn't require setting the loop start/end points: leaving them at 0 mean playing the whole segment, - moreover, the length (at least for wave tracks) of the segment is not used. Instead, the duration of stamped/posted tracks is used instead. - even forcing a length on segment isn't taken into account (tested locally, but not included in the current tests). - implemented it by creating the graph internal to segment state and gathering relevant information on the fly. There's no indication it's done this exact way on native, but at least tests for time of track playback are identical.
Notes: - only changed the track waves, future work will require equivalent testings at least on MIDI sequences.
From: Eric Pouech epouech@codeweavers.com
Signed-off-by: Eric Pouech epouech@codeweavers.com --- dlls/dmime/segmentstate.c | 10 ++++++---- dlls/dmime/tests/dmime.c | 3 --- 2 files changed, 6 insertions(+), 7 deletions(-)
diff --git a/dlls/dmime/segmentstate.c b/dlls/dmime/segmentstate.c index 3b939bc95ca..38ff9185534 100644 --- a/dlls/dmime/segmentstate.c +++ b/dlls/dmime/segmentstate.c @@ -53,7 +53,7 @@ struct segment_state MUSIC_TIME end_point; MUSIC_TIME played; BOOL auto_download; - DWORD repeats; + DWORD repeats, actual_repeats;
struct list tracks; }; @@ -117,7 +117,8 @@ static ULONG WINAPI segment_state_Release(IDirectMusicSegmentState8 *iface) static HRESULT WINAPI segment_state_GetRepeats(IDirectMusicSegmentState8 *iface, DWORD *repeats) { struct segment_state *This = impl_from_IDirectMusicSegmentState8(iface); - FIXME("(%p, %p): semi-stub\n", This, repeats); + TRACE("(%p, %p)\n", This, repeats); + *repeats = This->repeats; return S_OK; }
@@ -236,6 +237,7 @@ HRESULT segment_state_create(IDirectMusicSegment *segment, MUSIC_TIME start_time if (SUCCEEDED(hr)) hr = IDirectMusicSegment_GetStartPoint(segment, &This->start_point); if (SUCCEEDED(hr)) hr = IDirectMusicSegment_GetLength(segment, &This->end_point); if (SUCCEEDED(hr)) hr = IDirectMusicSegment_GetRepeats(segment, &This->repeats); + if (SUCCEEDED(hr)) This->actual_repeats = This->repeats;
for (i = 0; SUCCEEDED(hr); i++) { @@ -315,7 +317,7 @@ static HRESULT segment_state_play_chunk(struct segment_state *This, IDirectMusic
while ((hr = segment_state_play_until(This, performance, next_time, track_flags)) == S_FALSE) { - if (!This->repeats) + if (!This->actual_repeats) { MUSIC_TIME end_time = This->start_time + This->played;
@@ -332,7 +334,7 @@ static HRESULT segment_state_play_chunk(struct segment_state *This, IDirectMusic &This->end_point))) break; This->start_time += This->end_point - This->start_point; - This->repeats--; + This->actual_repeats--;
if (next_time <= This->start_time || This->end_point <= This->start_point) break; } diff --git a/dlls/dmime/tests/dmime.c b/dlls/dmime/tests/dmime.c index 26fdf3ef2a5..f6f34915547 100644 --- a/dlls/dmime/tests/dmime.c +++ b/dlls/dmime/tests/dmime.c @@ -4540,7 +4540,6 @@ static void test_segment_state(void) value = 0xdeadbeef; hr = IDirectMusicSegmentState_GetRepeats(state, &value); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(value == 0, "got %#lx\n", value); time = 0xdeadbeef; hr = IDirectMusicSegmentState_GetStartTime(state, &time); @@ -4624,7 +4623,6 @@ static void test_segment_state(void) value = 0xdeadbeef; hr = IDirectMusicSegmentState_GetRepeats(state, &value); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(value == 0, "got %#lx\n", value); time = 0xdeadbeef; hr = IDirectMusicSegmentState_GetStartTime(state, &time); @@ -4655,7 +4653,6 @@ static void test_segment_state(void) value = 0xdeadbeef; hr = IDirectMusicSegmentState_GetRepeats(state, &value); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(value == 0, "got %#lx\n", value); time = 0xdeadbeef; hr = IDirectMusicSegmentState_GetStartTime(state, &time);
From: Eric Pouech epouech@codeweavers.com
Signed-off-by: Eric Pouech epouech@codeweavers.com --- dlls/dmime/tests/dmime.c | 14 ++++++++++++++ 1 file changed, 14 insertions(+)
diff --git a/dlls/dmime/tests/dmime.c b/dlls/dmime/tests/dmime.c index f6f34915547..cb4a58d4403 100644 --- a/dlls/dmime/tests/dmime.c +++ b/dlls/dmime/tests/dmime.c @@ -4575,6 +4575,20 @@ static void test_segment_state(void) ok(state != tmp_state, "got %p\n", state); IDirectMusicSegmentState_Release(tmp_state);
+ graph = (void *)0xdeadbeef; + hr = IDirectMusicSegmentState_QueryInterface(state, &IID_IDirectMusicGraph, (void **)&graph); + todo_wine + ok(hr == S_OK, "got %#lx\n", hr); + if (hr == S_OK) + { + IDirectMusicTool *segment_state_tool; + + hr = IDirectMusicGraph_GetTool(graph, 0, &segment_state_tool); + ok(hr == E_NOTIMPL, "got %#lx\n", hr); + if (SUCCEEDED(hr)) IDirectMusicTool_Release(segment_state_tool); + IDirectMusicGraph_Release(graph); + } + tmp_state = (void *)0xdeadbeef; hr = IDirectMusicPerformance_GetSegmentState(performance, &tmp_state, 0); ok(hr == S_OK || broken(hr == DMUS_E_NOT_FOUND) /* sometimes on Windows */, "got %#lx\n", hr);
From: Eric Pouech epouech@codeweavers.com
Signed-off-by: Eric Pouech epouech@codeweavers.com --- dlls/dmime/segmentstate.c | 97 +++++++++++++++++++++++++++++++++++++-- dlls/dmime/tests/dmime.c | 1 - 2 files changed, 93 insertions(+), 5 deletions(-)
diff --git a/dlls/dmime/segmentstate.c b/dlls/dmime/segmentstate.c index 38ff9185534..51067d21d3d 100644 --- a/dlls/dmime/segmentstate.c +++ b/dlls/dmime/segmentstate.c @@ -45,8 +45,10 @@ static void track_entry_destroy(struct track_entry *entry) struct segment_state { IDirectMusicSegmentState8 IDirectMusicSegmentState8_iface; + IDirectMusicGraph IDirectMusicGraph_iface; LONG ref;
+ IDirectMusicGraph *parent_graph; IDirectMusicSegment *segment; MUSIC_TIME start_time; MUSIC_TIME start_point; @@ -82,7 +84,12 @@ static HRESULT WINAPI segment_state_QueryInterface(IDirectMusicSegmentState8 *if *ppobj = &This->IDirectMusicSegmentState8_iface; return S_OK; } - + if (IsEqualIID(riid, &IID_IDirectMusicGraph)) + { + IDirectMusicSegmentState8_AddRef(iface); + *ppobj = &This->IDirectMusicGraph_iface; + return S_OK; + } WARN("(%p, %s, %p): not found\n", This, debugstr_dmguid(riid), ppobj); return E_NOINTERFACE; } @@ -108,6 +115,7 @@ static ULONG WINAPI segment_state_Release(IDirectMusicSegmentState8 *iface) { segment_state_end_play((IDirectMusicSegmentState *)iface, NULL); if (This->segment) IDirectMusicSegment_Release(This->segment); + if (This->parent_graph) IDirectMusicGraph_Release(This->parent_graph); free(This); }
@@ -192,6 +200,73 @@ static const IDirectMusicSegmentState8Vtbl segment_state_vtbl = segment_state_GetObjectInPath, };
+static inline struct segment_state *impl_from_IDirectMusicGraph(IDirectMusicGraph *iface) +{ + return CONTAINING_RECORD(iface, struct segment_state, IDirectMusicGraph_iface); +} + +static HRESULT WINAPI segment_state_graph_QueryInterface(IDirectMusicGraph *iface, REFIID riid, void **ret_iface) +{ + struct segment_state *This = impl_from_IDirectMusicGraph(iface); + return IDirectMusicSegmentState8_QueryInterface(&This->IDirectMusicSegmentState8_iface, riid, ret_iface); +} + +static ULONG WINAPI segment_state_graph_AddRef(IDirectMusicGraph *iface) +{ + struct segment_state *This = impl_from_IDirectMusicGraph(iface); + return IDirectMusicSegmentState8_AddRef(&This->IDirectMusicSegmentState8_iface); +} + +static ULONG WINAPI segment_state_graph_Release(IDirectMusicGraph *iface) +{ + struct segment_state *This = impl_from_IDirectMusicGraph(iface); + return IDirectMusicSegmentState8_Release(&This->IDirectMusicSegmentState8_iface); +} + +static HRESULT WINAPI segment_state_graph_StampPMsg(IDirectMusicGraph *iface, DMUS_PMSG *msg) +{ + struct segment_state *This = impl_from_IDirectMusicGraph(iface); + + TRACE("(%p, %p)\n", This, msg); + + if (!msg) return E_POINTER; + + return IDirectMusicGraph_StampPMsg(This->parent_graph, msg); +} + +static HRESULT WINAPI segment_state_graph_InsertTool(IDirectMusicGraph *iface, IDirectMusicTool *tool, + DWORD *channels, DWORD channels_count, LONG index) +{ + struct segment_state *This = impl_from_IDirectMusicGraph(iface); + TRACE("(%p, %p, %p, %lu, %ld)\n", This, tool, channels, channels_count, index); + return E_NOTIMPL; +} + +static HRESULT WINAPI segment_state_graph_GetTool(IDirectMusicGraph *iface, DWORD index, IDirectMusicTool **tool) +{ + struct segment_state *This = impl_from_IDirectMusicGraph(iface); + TRACE("(%p, %lu, %p)\n", This, index, tool); + return E_NOTIMPL; +} + +static HRESULT WINAPI segment_state_graph_RemoveTool(IDirectMusicGraph *iface, IDirectMusicTool *tool) +{ + struct segment_state *This = impl_from_IDirectMusicGraph(iface); + TRACE("(%p, %p)\n", This, tool); + return E_NOTIMPL; +} + +static const IDirectMusicGraphVtbl segment_state_graph_vtbl = +{ + segment_state_graph_QueryInterface, + segment_state_graph_AddRef, + segment_state_graph_Release, + segment_state_graph_StampPMsg, + segment_state_graph_InsertTool, + segment_state_graph_GetTool, + segment_state_graph_RemoveTool, +}; + /* for ClassFactory */ HRESULT create_dmsegmentstate(REFIID riid, void **ret_iface) { @@ -201,6 +276,7 @@ HRESULT create_dmsegmentstate(REFIID riid, void **ret_iface) *ret_iface = NULL; if (!(obj = calloc(1, sizeof(*obj)))) return E_OUTOFMEMORY; obj->IDirectMusicSegmentState8_iface.lpVtbl = &segment_state_vtbl; + obj->IDirectMusicGraph_iface.lpVtbl = &segment_state_graph_vtbl; obj->ref = 1; obj->start_time = -1; list_init(&obj->tracks); @@ -216,6 +292,7 @@ HRESULT segment_state_create(IDirectMusicSegment *segment, MUSIC_TIME start_time { IDirectMusicSegmentState *iface; struct segment_state *This; + IDirectMusicGraph *graph; IDirectMusicTrack *track; HRESULT hr; UINT i; @@ -228,7 +305,10 @@ HRESULT segment_state_create(IDirectMusicSegment *segment, MUSIC_TIME start_time This->segment = segment; IDirectMusicSegment_AddRef(This->segment);
- if (SUCCEEDED(hr = IDirectMusicPerformance8_GetGlobalParam(performance, &GUID_PerfAutoDownload, + hr = IDirectMusicPerformance8_QueryInterface(performance, &IID_IDirectMusicGraph, (void **)&graph); + + if (SUCCEEDED(hr) && + SUCCEEDED(hr = IDirectMusicPerformance8_GetGlobalParam(performance, &GUID_PerfAutoDownload, &This->auto_download, sizeof(This->auto_download))) && This->auto_download) hr = IDirectMusicSegment_SetParam(segment, &GUID_DownloadToAudioPath, -1, DMUS_SEG_ALLTRACKS, 0, performance); @@ -268,8 +348,17 @@ HRESULT segment_state_create(IDirectMusicSegment *segment, MUSIC_TIME start_time } }
- if (SUCCEEDED(hr)) *ret_iface = iface; - else IDirectMusicSegmentState_Release(iface); + if (SUCCEEDED(hr)) + { + *ret_iface = iface; + This->parent_graph = graph; + } + else + { + IDirectMusicSegmentState_Release(iface); + IDirectMusicGraph_Release(graph); + } + return hr; }
diff --git a/dlls/dmime/tests/dmime.c b/dlls/dmime/tests/dmime.c index cb4a58d4403..8ae62b38670 100644 --- a/dlls/dmime/tests/dmime.c +++ b/dlls/dmime/tests/dmime.c @@ -4577,7 +4577,6 @@ static void test_segment_state(void)
graph = (void *)0xdeadbeef; hr = IDirectMusicSegmentState_QueryInterface(state, &IID_IDirectMusicGraph, (void **)&graph); - todo_wine ok(hr == S_OK, "got %#lx\n", hr); if (hr == S_OK) {
From: Eric Pouech epouech@codeweavers.com
Now storing track_flags inside segment state so that they can be reused in subsequent calls. The start/seek/loop flags are now properly set when calling IDirectMusicTrack_Play().
Signed-off-by: Eric Pouech epouech@codeweavers.com --- dlls/dmime/segmentstate.c | 13 ++++++++----- dlls/dmime/wavetrack.c | 7 +++++-- 2 files changed, 13 insertions(+), 7 deletions(-)
diff --git a/dlls/dmime/segmentstate.c b/dlls/dmime/segmentstate.c index 51067d21d3d..0deb396d384 100644 --- a/dlls/dmime/segmentstate.c +++ b/dlls/dmime/segmentstate.c @@ -56,6 +56,7 @@ struct segment_state MUSIC_TIME played; BOOL auto_download; DWORD repeats, actual_repeats; + DWORD track_flags;
struct list tracks; }; @@ -385,12 +386,13 @@ static HRESULT segment_state_play_until(struct segment_state *This, IDirectMusic }
This->played = played; + This->track_flags &= ~(DMUS_TRACKF_START|DMUS_TRACKF_DIRTY); if (This->start_point + This->played >= This->end_point) return S_FALSE; return S_OK; }
static HRESULT segment_state_play_chunk(struct segment_state *This, IDirectMusicPerformance8 *performance, - REFERENCE_TIME duration, DWORD track_flags) + REFERENCE_TIME duration) { IDirectMusicSegmentState *iface = (IDirectMusicSegmentState *)&This->IDirectMusicSegmentState8_iface; MUSIC_TIME next_time; @@ -404,7 +406,7 @@ static HRESULT segment_state_play_chunk(struct segment_state *This, IDirectMusic time + duration, &next_time))) return hr;
- while ((hr = segment_state_play_until(This, performance, next_time, track_flags)) == S_FALSE) + while ((hr = segment_state_play_until(This, performance, next_time, This->track_flags)) == S_FALSE) { if (!This->actual_repeats) { @@ -424,6 +426,7 @@ static HRESULT segment_state_play_chunk(struct segment_state *This, IDirectMusic break; This->start_time += This->end_point - This->start_point; This->actual_repeats--; + This->track_flags |= DMUS_TRACKF_LOOP | DMUS_TRACKF_SEEK;
if (next_time <= This->start_time || This->end_point <= This->start_point) break; } @@ -444,8 +447,8 @@ HRESULT segment_state_play(IDirectMusicSegmentState *iface, IDirectMusicPerforma return hr; }
- if (FAILED(hr = segment_state_play_chunk(This, performance, 10000000, - DMUS_TRACKF_START | DMUS_TRACKF_SEEK | DMUS_TRACKF_DIRTY))) + This->track_flags = DMUS_TRACKF_START | DMUS_TRACKF_SEEK | DMUS_TRACKF_DIRTY; + if (FAILED(hr = segment_state_play_chunk(This, performance, 10000000))) return hr;
if (hr == S_FALSE) return S_OK; @@ -458,7 +461,7 @@ HRESULT segment_state_tick(IDirectMusicSegmentState *iface, IDirectMusicPerforma
TRACE("%p %p\n", iface, performance);
- return segment_state_play_chunk(This, performance, 10000000, 0); + return segment_state_play_chunk(This, performance, 10000000); }
HRESULT segment_state_stop(IDirectMusicSegmentState *iface, IDirectMusicPerformance8 *performance) diff --git a/dlls/dmime/wavetrack.c b/dlls/dmime/wavetrack.c index 7f2fe4a8e5f..3d64e6e84c5 100644 --- a/dlls/dmime/wavetrack.c +++ b/dlls/dmime/wavetrack.c @@ -147,6 +147,7 @@ static HRESULT WINAPI wave_track_Play(IDirectMusicTrack8 *iface, void *state_dat MUSIC_TIME start_time, MUSIC_TIME end_time, MUSIC_TIME time_offset, DWORD track_flags, IDirectMusicPerformance *performance, IDirectMusicSegmentState *segment_state, DWORD track_id) { + static const DWORD handled_track_flags = DMUS_TRACKF_START | DMUS_TRACKF_SEEK | DMUS_TRACKF_DIRTY | DMUS_TRACKF_LOOP; struct wave_track *This = impl_from_IDirectMusicTrack8(iface); LONG volume = This->header.lVolume; IDirectMusicGraph *graph; @@ -157,9 +158,11 @@ static HRESULT WINAPI wave_track_Play(IDirectMusicTrack8 *iface, void *state_dat TRACE("(%p, %p, %ld, %ld, %ld, %#lx, %p, %p, %ld)\n", This, state_data, start_time, end_time, time_offset, track_flags, performance, segment_state, track_id);
- if (track_flags) FIXME("track_flags %#lx not implemented\n", track_flags); + if (track_flags & ~handled_track_flags) + FIXME("track_flags %#lx not implemented\n", track_flags & ~handled_track_flags); if (segment_state) FIXME("segment_state %p not implemented\n", segment_state); - if (!(track_flags & DMUS_TRACKF_START)) return S_OK; + + if (!(track_flags & (DMUS_TRACKF_START | DMUS_TRACKF_LOOP))) return S_OK;
if (FAILED(hr = IDirectMusicPerformance_QueryInterface(performance, &IID_IDirectMusicGraph, (void **)&graph)))
From: Eric Pouech epouech@codeweavers.com
When playing a loop, and if no end of loop point has been defined (meaning = play whole segment), don't rely on segment's length for wave tracks as their length is always. Actual loop length in this case is computed by using segment state's internal graph as a proxy to grab this information.
Signed-off-by: Eric Pouech epouech@codeweavers.com --- dlls/dmime/segmentstate.c | 37 ++++++++++++++++++++++++++++++++++++- dlls/dmime/tests/dmime.c | 18 +++++++++++------- dlls/dmime/wavetrack.c | 6 +++--- 3 files changed, 50 insertions(+), 11 deletions(-)
diff --git a/dlls/dmime/segmentstate.c b/dlls/dmime/segmentstate.c index 0deb396d384..4fece4181e1 100644 --- a/dlls/dmime/segmentstate.c +++ b/dlls/dmime/segmentstate.c @@ -54,6 +54,10 @@ struct segment_state MUSIC_TIME start_point; MUSIC_TIME end_point; MUSIC_TIME played; + + REFERENCE_TIME actual_duration; + MUSIC_TIME actual_end_point; + BOOL auto_download; DWORD repeats, actual_repeats; DWORD track_flags; @@ -227,12 +231,29 @@ static ULONG WINAPI segment_state_graph_Release(IDirectMusicGraph *iface) static HRESULT WINAPI segment_state_graph_StampPMsg(IDirectMusicGraph *iface, DMUS_PMSG *msg) { struct segment_state *This = impl_from_IDirectMusicGraph(iface); + HRESULT hr;
TRACE("(%p, %p)\n", This, msg);
if (!msg) return E_POINTER;
- return IDirectMusicGraph_StampPMsg(This->parent_graph, msg); + hr = IDirectMusicGraph_StampPMsg(This->parent_graph, msg); + if (SUCCEEDED(hr)) + { + switch (msg->dwType) + { + case DMUS_PMSGT_WAVE: + if (msg->dwFlags & (DMUS_PMSGF_REFTIME | DMUS_PMSGF_MUSICTIME)) + { + if (((DMUS_WAVE_PMSG *)msg)->rtDuration > This->actual_duration) + This->actual_duration = ((DMUS_WAVE_PMSG *)msg)->rtDuration; + } + break; + default: ; + } + } + + return hr; }
static HRESULT WINAPI segment_state_graph_InsertTool(IDirectMusicGraph *iface, IDirectMusicTool *tool, @@ -373,6 +394,9 @@ static HRESULT segment_state_play_until(struct segment_state *This, IDirectMusic
played = min(end_time - This->start_time, This->end_point - This->start_point);
+ if (This->track_flags & DMUS_TRACKF_DIRTY) + This->actual_duration = 0; + LIST_FOR_EACH_ENTRY(entry, &This->tracks, struct track_entry, entry) { if (FAILED(hr = IDirectMusicTrack_Play(entry->track, entry->state_data, @@ -424,6 +448,17 @@ static HRESULT segment_state_play_chunk(struct segment_state *This, IDirectMusic if (FAILED(hr = IDirectMusicSegment_GetLoopPoints(This->segment, &This->played, &This->end_point))) break; + if (!This->played && !This->end_point) + { + if (!This->actual_end_point && This->actual_duration) + { + IDirectMusicPerformance_ReferenceToMusicTime(performance, time + This->actual_duration, &This->actual_end_point); + This->actual_end_point -= This->start_time + This->played; + } + This->end_point = This->actual_end_point; + if (next_time < This->start_time + This->end_point) + next_time += This->end_point - This->start_point; + } This->start_time += This->end_point - This->start_point; This->actual_repeats--; This->track_flags |= DMUS_TRACKF_LOOP | DMUS_TRACKF_SEEK; diff --git a/dlls/dmime/tests/dmime.c b/dlls/dmime/tests/dmime.c index 8ae62b38670..4fff7ba7588 100644 --- a/dlls/dmime/tests/dmime.c +++ b/dlls/dmime/tests/dmime.c @@ -3660,11 +3660,17 @@ static void test_wave_pmsg(unsigned num_repeats)
for (i = 0; i <= num_repeats; i++) { - ret = test_tool_wait_message(tool, 500, (DMUS_PMSG **)&wave); - todo_wine_if(num_repeats && ret) - ok(!ret, "got %#lx\n", ret); - if (ret) continue; - ok(wave->dwType == DMUS_PMSGT_WAVE, "got %p\n", wave); + /* Wine's implement queues very less play time at once compared to windows.. + * Discard Wine's internal messages, until next chunk has started. + */ + do + { + ret = test_tool_wait_message(tool, 2000, (DMUS_PMSG **)&wave); + ok(!ret, "got %#lx\n", ret); + } while (num_repeats && !ret && (wave->dwType >= 0x10 || wave->dwType == DMUS_PMSGT_DIRTY)); + if (ret) break; + + ok(wave->dwType == DMUS_PMSGT_WAVE, "got %p %lu\n", wave, wave->dwType); ok(wave->dwSize == sizeof(*wave), "got %lu\n", wave->dwSize); ok(!!wave->punkUser, "got %p\n", wave->punkUser); ok((wave->dwFlags & DMUS_PMSGF_REFTIME) && (wave->dwFlags & DMUS_PMSGF_MUSICTIME), @@ -3672,7 +3678,6 @@ static void test_wave_pmsg(unsigned num_repeats) if (i == 0) mt_start_ref = wave->mtTime; else - todo_wine ok(wave->mtTime == mt_start_ref + length * i, "got %lu (%lu,%lu)\n", wave->mtTime, mt_start_ref, i * length); ok(wave->rtStartOffset == 0, "got %I64d\n", wave->rtStartOffset); ok(wave->rtDuration == 1000000, "got %I64d\n", wave->rtDuration); @@ -3685,7 +3690,6 @@ static void test_wave_pmsg(unsigned num_repeats) }
ret = test_tool_wait_message(tool, 500, &msg); - todo_wine_if(num_repeats) ok(!ret, "got %#lx\n", ret); if (!ret) { diff --git a/dlls/dmime/wavetrack.c b/dlls/dmime/wavetrack.c index 3d64e6e84c5..64480c6422f 100644 --- a/dlls/dmime/wavetrack.c +++ b/dlls/dmime/wavetrack.c @@ -160,11 +160,11 @@ static HRESULT WINAPI wave_track_Play(IDirectMusicTrack8 *iface, void *state_dat
if (track_flags & ~handled_track_flags) FIXME("track_flags %#lx not implemented\n", track_flags & ~handled_track_flags); - if (segment_state) FIXME("segment_state %p not implemented\n", segment_state); - if (!(track_flags & (DMUS_TRACKF_START | DMUS_TRACKF_LOOP))) return S_OK;
- if (FAILED(hr = IDirectMusicPerformance_QueryInterface(performance, + if (FAILED(hr = IDirectMusicSegmentState_QueryInterface(segment_state, + &IID_IDirectMusicGraph, (void **)&graph)) && + FAILED(hr = IDirectMusicPerformance_QueryInterface(performance, &IID_IDirectMusicGraph, (void **)&graph))) return hr;
Can you please update the commit message of the last patch? Looks like an "ignored" is missing ``` don't rely on segment's length for wave tracks as their length is always. ```
Please also rephrase the comment in the test in that patch? I'm a little bit confused what it exactly means. ``` /* Wine's implement queues very less play time at once compared to windows.. ```