使用 Azure 媒体视频缩略图创建视频摘要

概述

通过 Azure Media Video Thumbnails 媒体处理器 (MP),可创建视频摘要,这对于要预览长视频摘要的客户来说很有用。 例如,当客户将鼠标悬停在缩略图上时,他们可能希望看到一小段“摘要视频”。 使用配置预设值稍稍调整 Azure 媒体视频缩略图 的参数,就可使用 MP 的强大镜头检测和串联技术,以算法形式生成描述性子剪辑。

Azure 媒体视频缩略图 MP 目前处于预览状态。

此主题提供有关 Azure Media Video Thumbnail 的详细信息,并演示如何将它与用于 .NET 的媒体服务 SDK 配合使用。

限制

在某些情况下,如果视频不是由不同的场景构成,则输出仅为单张快照。

视频摘要示例

下面是 Azure 媒体视频缩略图媒体处理器可以执行的操作的一些示例:

原始视频

原始视频

视频缩略图结果

视频缩略图结果

任务配置(预设)

使用 Azure 媒体视频缩略图创建视频缩略图时,必须指定配置预设值。 以上缩略图示例使用以下 JSON 基本配置创建:

{"version":"1.0"}

当前你可更改以下参数:

Param 说明
outputAudio 指定生成的视频是否包含音频。
允许的值为:True 或 False。 默认值为 True。
fadeInFadeOut 指定单独动态缩略图之间是否使用淡入淡出转换。
允许的值为:True 或 False。 默认值为 True。
maxMotionThumbnailDurationInSecs 指定生成的整个视频的时长的整数。 默认值取决于原始视频的持续时间。

下表描述了当 maxMotionThumbnailInSecs 未使用时的默认持续时间。

视频持续时间 d < 3 分钟 3 分钟 < d < 15 分钟
缩略图持续时间 15 秒(2-3 个场景) 30 秒(3-5 个场景)

下面的 JSON 设置可用的参数。

{
    "version": "1.0",
    "options": {
        "outputAudio": "true",
        "maxMotionThumbnailDurationInSecs": "10",
        "fadeInFadeOut": "true"
    }
}

.NET 示例代码

以下程序演示如何:

  1. 创建资产并将媒体文件上传到资产。
  2. 使用基于包含以下 json 预设值的配置文件的视频缩略图任务,创建一个作业。

    {               
        "version": "1.0",
        "options": {
            "outputAudio": "true",
            "maxMotionThumbnailDurationInSecs": "30",
            "fadeInFadeOut": "false"
        }
    }
    
  3. 下载输出文件。

创建和配置 Visual Studio 项目

设置开发环境,并在 app.config 文件中填充连接信息,如使用 .NET 进行媒体服务开发中所述。

示例

using System;
using System.Configuration;
using System.IO;
using System.Linq;
using Microsoft.WindowsAzure.MediaServices.Client;
using System.Threading;
using System.Threading.Tasks;

namespace VideoSummarization
{
    class Program
    {
        // Read values from the App.config file.
        private static readonly string _AADTenantDomain =
            ConfigurationManager.AppSettings["AADTenantDomain"];
        private static readonly string _RESTAPIEndpoint =
            ConfigurationManager.AppSettings["MediaServiceRESTAPIEndpoint"];

        // Field for service context.
        private static CloudMediaContext _context = null;

        static void Main(string[] args)
        {
            var tokenCredentials = new AzureAdTokenCredentials(_AADTenantDomain, AzureEnvironments.AzureChinaCloudEnvironment);
            var tokenProvider = new AzureAdTokenProvider(tokenCredentials);

            _context = new CloudMediaContext(new Uri(_RESTAPIEndpoint), tokenProvider);


            // Run the thumbnail job.
            var asset = RunVideoThumbnailJob(@"C:\supportFiles\VideoThumbnail\BigBuckBunny.mp4",
                                        @"C:\supportFiles\VideoThumbnail\config.json");

            // Download the job output asset.
            DownloadAsset(asset, @"C:\supportFiles\VideoThumbnail\Output");
        }

        static IAsset RunVideoThumbnailJob(string inputMediaFilePath, string configurationFile)
        {
            // Create an asset and upload the input media file to storage.
            IAsset asset = CreateAssetAndUploadSingleFile(inputMediaFilePath,
                "My Video Thumbnail Input Asset",
                AssetCreationOptions.None);

            // Declare a new job.
            IJob job = _context.Jobs.Create("My Video Thumbnail Job");

            // Get a reference to Azure Media Video Thumbnails.
            string MediaProcessorName = "Azure Media Video Thumbnails";

            var processor = GetLatestMediaProcessorByName(MediaProcessorName);

            // Read configuration from the specified file.
            string configuration = File.ReadAllText(configurationFile);

            // Create a task with the encoding details, using a string preset.
            ITask task = job.Tasks.AddNew("My Video Thumbnail Task",
                processor,
                configuration,
                TaskOptions.None);

            // Specify the input asset.
            task.InputAssets.Add(asset);

            // Add an output asset to contain the results of the job.
            task.OutputAssets.AddNew("My Video Thumbnail Output Asset", AssetCreationOptions.None);

            // Use the following event handler to check job progress.  
            job.StateChanged += new EventHandler<JobStateChangedEventArgs>(StateChanged);

            // Launch the job.
            job.Submit();

            // Check job execution and wait for job to finish.
            Task progressJobTask = job.GetExecutionProgressTask(CancellationToken.None);

            progressJobTask.Wait();

            // If job state is Error, the event handling
            // method for job progress should log errors.  Here we check
            // for error state and exit if needed.
            if (job.State == JobState.Error)
            {
                ErrorDetail error = job.Tasks.First().ErrorDetails.First();
                Console.WriteLine(string.Format("Error: {0}. {1}",
                                                error.Code,
                                                error.Message));
                return null;
            }

            return job.OutputMediaAssets[0];
        }

        static IAsset CreateAssetAndUploadSingleFile(string filePath, string assetName, AssetCreationOptions options)
        {
            IAsset asset = _context.Assets.Create(assetName, options);

            var assetFile = asset.AssetFiles.Create(Path.GetFileName(filePath));
            assetFile.Upload(filePath);

            return asset;
        }

        static void DownloadAsset(IAsset asset, string outputDirectory)
        {
            foreach (IAssetFile file in asset.AssetFiles)
            {
                file.Download(Path.Combine(outputDirectory, file.Name));
            }
        }

        static IMediaProcessor GetLatestMediaProcessorByName(string mediaProcessorName)
        {
            var processor = _context.MediaProcessors
                .Where(p => p.Name == mediaProcessorName)
                .ToList()
                .OrderBy(p => new Version(p.Version))
                .LastOrDefault();

            if (processor == null)
                throw new ArgumentException(string.Format("Unknown media processor",
                                                           mediaProcessorName));

            return processor;
        }

        static private void StateChanged(object sender, JobStateChangedEventArgs e)
        {
            Console.WriteLine("Job state changed event:");
            Console.WriteLine("  Previous state: " + e.PreviousState);
            Console.WriteLine("  Current state: " + e.CurrentState);

            switch (e.CurrentState)
            {
                case JobState.Finished:
                    Console.WriteLine();
                    Console.WriteLine("Job is finished.");
                    Console.WriteLine();
                    break;
                case JobState.Canceling:
                case JobState.Queued:
                case JobState.Scheduled:
                case JobState.Processing:
                    Console.WriteLine("Please wait...\n");
                    break;
                case JobState.Canceled:
                case JobState.Error:
                    // Cast sender as a job.
                    IJob job = (IJob)sender;
                    // Display or log error details as needed.
                    // LogJobStop(job.Id);
                    break;
                default:
                    break;
            }
        }

    }
}

视频缩略图输出

视频缩略图输出

Azure 媒体服务分析概述

Azure Media Analytics demos(Azure 媒体分析演示)