从ASP.NET中的Seek位置流式传输MP4视频

时间:2012-03-23 16:46:43

标签: c# asp.net .net video-streaming mp4

我从搜索位置流式传输mp4视频时遇到问题。从开始就正确播放。

第一个问题是mp4视频是通过jw播放器flash播放器流式传输的。当用户点击时间栏从视频的任何其他部分开始流式传输mp4视频时,jw播放器将发送开始参数以及时间信息,例如

http://[url]/stream/mp4.ashx?file=Madagascar3-trailer-48861c.mp4&start=53.71

所以jwplayer发送时间间隔来寻找mp4流。

我使用以下代码将大约时间间隔转换为字节,因为搜索将从字节开始。

 double total_duration = Convert.ToDouble(context.Request.Params["d"]);
 double startduration = Convert.ToDouble(context.Request.Params["start"]);
 double length_sec = (double)size / total_duration; // total length per second
 start = (long)(length_sec * startduration);

以下是我用于从搜索位置开始流式传输的完整示例代码,例如53.71

private void ChunkDownload(string fullpath, HttpContext context)
{
    long size, start, end, length, fp = 0;
    using (StreamReader reader = new StreamReader(fullpath))
    {
        size = reader.BaseStream.Length;
        start = 0;
        end = size - 1;
        length = size;

        double total_duration = Convert.ToDouble(context.Request.Params["d"]);
        double startduration = Convert.ToDouble(context.Request.Params["start"]);
        double length_sec = (double)size / total_duration; // total length per second
        start = (long)(length_sec * startduration);

        context.Response.AddHeader("Accept-Ranges", "0-" + size);
        long anotherStart = start;
        long anotherEnd = end;

        // End bytes can not be larger than $end.
        anotherEnd = (anotherEnd > end) ? end : anotherEnd;
        // Validate the requested range and return an error if it's not correct.
        if (anotherStart > anotherEnd || anotherStart > size - 1 || anotherEnd >= size)
        {

            context.Response.AddHeader("Content-Range", "bytes " + start + "-" + end + "/" + size);
            throw new HttpException(416, "Requested Range Not Satisfiable");
        }
        start = anotherStart;
        end = anotherEnd;

        length = end - start + 1; // Calculate new content length
        fp = reader.BaseStream.Seek(start, SeekOrigin.Begin);
        context.Response.StatusCode = 206;

    }
    // Notify the client the byte range we'll be outputting
    context.Response.AddHeader("Content-Range", "bytes " + start + "-" + end + "/" + size);
    context.Response.AddHeader("Content-Length", length.ToString());

    context.Response.WriteFile(fullpath, fp, length);
    context.Response.End();

}

但它无法通过播放器或直接检查流URL来识别为有效的mp4流。

任何人都可以帮我解决这个问题。

6 个答案:

答案 0 :(得分:2)

同意,你不能只是寻找像这样的mp4 / m3u8文件。

但我认为你无法找到解决方案或解决方法,我们在我的iPhone开发团队中有高级iPhone开发人员和外部顾问进行反复试验,我们花了这么多资源但问题仍无法解决。

答案 1 :(得分:2)

使用Google搜索后,找不到相关的API。

如果无法解决问题,您可以检查解决方法。

如果可能,请提供更多信息以供进一步研究。

答案 2 :(得分:1)

没有有效的内容类型定义。尝试将ContentType设置为video / mp4。

更新

虽然定义了内容类型,但根据您的代码,http状态代码为206,我建议您查看此页面:206 Partial Content

答案 3 :(得分:0)

穆罕默德,

我注意到你正在对内容标题进行大量计算和操作。也许当你对它们进行所有数学运算时,它会导致标题由于额外的小数位(无效)而无效,或者这些设置存在其他问题。

意思是,我建议您执行以下操作:

  1. 使用相同的播放器等从站点运行带有流的示例视频,然后使用工具在成功运行时查看标题。只需要有一组基线和有效值格式进行比较。

  2. 运行您的应用程序并在设置后跟踪标题,可能如下:how to dump response headers in ASP.Net 更好的是,安装“Live HTTP Headers”FireFox插件或类似的东西。

  3. 将标题的工作集与您的标题进行比较。你在设定的价值观中看到了什么奇怪的东西吗?是否有可能是内容范围/长度/等。以某种方式抵消或无效?只要寻找一致性,一个小错误就很容易打破整个请求。

    也许我在这里遗漏了一些东西,但我希望这会引发一些想法。

答案 4 :(得分:0)

我认为你不能像这样寻找一个mp4文件。 即使你有标题,你也需要寻找一个I帧来让视频可以播放。你很可能会使用错误的API。

答案 5 :(得分:0)

我不会评论这篇文章中的回复内容,但你肯定有一个问题是MP4解析。与MP3不同,你不能轻易地将时间偏移转换为像这样的字节范围。您需要解析mp4 moov元素并根据您感兴趣的时间偏移在相关轨道中查找正确的块。它是这样的:moov-> trak-> mdia-> minf-&gt ; stbl-> stts stts框将为您提供所需的时间映射示例。