首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> .NET 網頁程式設計 >> 關於.NET

WinRT 開發實戰:使用 BitmapEncoder 建立 GIF 動畫完整教學

     編輯:關於.NET

前言

Windows 8 透過 Windows Imaging Component (WIC) 提供強大的影像編碼功能。本文示範如何使用 BitmapEncoder 與 GifEncoderId 建立翻頁式動畫 (Flipbook Animation) 並匯出為 GIF 檔案,核心技術來自 Flipflop 應用實作。

核心架構:GifMaker 類別

封裝動畫幀管理與 GIF 產生邏輯:

using System;
using System.Collections.Generic;
using System.Runtime.InteropServices.WindowsRuntime;
using Windows.Foundation;
using Windows.Graphics.Imaging;
using Windows.Storage;

namespace Utilities
{
    public sealed class GifMaker
    {
        readonly List frames = new List();
        private readonly uint frameWidth;
        private readonly uint frameHeight;

        public GifMaker(uint width, uint height)
        {
            frameWidth = width;
            frameHeight = height;
        }

        public void AppendNewFrame([ReadOnlyArray] byte[] frame)
        {
            frames.Add(frame);
        }

        public IAsyncInfo GenerateAsync(StorageFile file, int delay = 100)
        {
            return AsyncInfo.Run(async ctx =>
            {
                var outStream = await file.OpenAsync(FileAccessMode.ReadWrite);
                var encoder = await BitmapEncoder.CreateAsync(BitmapEncoder.GifEncoderId, outStream);

                for (int i = 0; i < frames.Count; i++)
                {
                    var pixels = frames[i];
                    encoder.SetPixelData(
                        BitmapPixelFormat.Rgba8,
                        BitmapAlphaMode.Ignore,
                        frameWidth, frameHeight,
                        92.0, 92.0, // DPI
                        pixels);

                    // 設定幀延遲 (僅第一幀需設定全域延遲)
                    if (i == 0)
                    {
                        var properties = new BitmapPropertySet
                        {
                            { "/grctlext/Delay", new BitmapTypedValue(delay / 10, PropertyType.UInt16) }
                        };
                        await encoder.BitmapProperties.SetPropertiesAsync(properties);
                    }

                    if (i < frames.Count - 1)
                        await encoder.GoToNextFrameAsync();
                }

                await encoder.FlushAsync();
                outStream.Dispose();
            });
        }
    }
}

關鍵技術點解析

1. 動態幀建立:GoToNextFrameAsync()

BitmapEncoder.GoToNextFrameAsync() 會在目前幀之後建立新的空白幀,讓開發者依序填入每一張動畫畫面。

2. GIF 延遲控制:/grctlext/Delay

透過 BitmapProperties 設定 Graphics Control Extension 的 Delay 欄位,單位為 1/100 秒:

var properties = new BitmapPropertySet
{
    { "/grctlext/Delay", new BitmapTypedValue(delay / 10, PropertyType.UInt16) }
};
await encoder.BitmapProperties.SetPropertiesAsync(properties);

3. 像素資料格式

使用 BitmapPixelFormat.Rgba8 (32-bit RGBA) 搭配 BitmapAlphaMode.Ignore,DPI 設為 92.0 (標準螢幕解析度)。

JavaScript 版本實作 (WinJS)

var picker = new Windows.Storage.Pickers.FileSavePicker();
picker.fileTypeChoices.insert("Gif files", [".gif"]);
picker.pickSaveFileAsync().then(function(file) {
    if (!file) return;
    
    var gifMaker = new Utilities.GifMaker(800, 600);
    for (var i = 0; i < currentFlipflop.pages.length; i++) {
        var bytes = Flipflop.Tools.GetBytesfromFlipflop(currentFlipflop.pages[i], 800, 600);
        gifMaker.appendNewFrame(bytes);
    }
    gifMaker.generateAsync(file, 200).done();
});

完整應用流程

  1. 建立 GifMaker 實例,指定畫面寬高
  2. 依序呼叫 AppendNewFrame() 加入每一幀的像素位元組陣列
  3. 使用檔案選取器讓使用者指定輸出路徑
  4. 呼叫 GenerateAsync() 非同步產生 GIF 檔案
  5. 設定 delay 參數控制播放速度 (毫秒)

效果展示

Flipflop GIF 動畫範例 1

Flipflop GIF 動畫範例 2

延伸應用

  • 繪圖應用的動畫匯出功能
  • 教學簡報轉 GIF
  • 遊戲重播片段匯出
  • UI 互動原型動畫輸出

作者:cnblogs Kevin Fan

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved