如何編輯影像 (HTML)
[ 本文的目標對象是撰寫 Windows 執行階段 App 的 Windows 8.x 和 Windows Phone 8.x 開發人員。如果您正在開發適用於 Windows 10 的 App,請參閱 最新文件 ]
這個主題說明如何使用 BitmapEncoder 編輯現有影像。您可以使用 BitmapEncoder 套用縮放和裁剪等轉換、設定中繼資料和屬性,以及在保留所有未編輯資料的情況下編輯像素。這裡將說明如何利用原始影像資料初始化 BitmapEncoder,套用一或多個編輯作業,然後儲存以更新原始檔案。
您也可以使用 BitmapEncoder 從頭建立新影像;我們將在如何編碼新影像中加以說明。
您必須知道的事
技術
先決條件
- 我們假設您可以使用 JavaScript 建立基本的 Windows 執行階段應用程式。如需詳細資訊,請參閱使用 JavaScript 建立您的第一個 Windows 執行階段應用程式。
- 您擁有 BitmapDecoder 物件。如何解碼影像會逐步引導您執行該程序。
指示
步驟 1: 從原始影像取得解碼器物件
編寫函式,一開始要接收從您要編輯之影像檔所初始化的 BitmapEncoder 物件,以及從檔案開啟的 IRandomAccessStream。這個範例會覆寫原始影像,因此您必須使用透過 ReadWrite 權限所開啟的資料流。
function (decoder, fileStream) {
注意 如需如何取得解碼器和資料流物件的指示,請參閱如何解碼影像。
呼叫 OpenAsync 時,務必將 FileAccessMode 參數變更為 ReadWrite。
步驟 2: 初始化編碼器物件以進行編輯
建立 InMemoryRandomAccessStream 當成編碼目的地,然後使用 CreateForTranscodingAsync 方法建立轉碼 BitmapEncoder。
使用 InMemoryRandomAccessStream 當成儲存編碼檔案的暫時位置。否則,解碼器和編碼器會同時讀取和寫入同一個資料流,而這樣是無法運作的。
// Keep variables in-scope across multiple async
var memStream = new Windows.Storage.Streams.InMemoryRandomAccessStream();
var encoder;
Windows.Graphics.Imaging.BitmapEncoder
.createForTranscodingAsync(memStream, decoder).then(function (_encoder) {
encoder = _encoder;
注意 CreateForTranscodingAsync 僅支援將資料複製到與原始影像格式相同的影像。您無法將格式轉換成另一種格式。
現在您擁有已透過來源 BitmapDecoder 資料初始化的 BitmapEncoder。
步驟 3: 轉換影像
既然您已經有編碼器,就可以執行各種動作,包括設定中繼資料和像素資料。這個範例會使用 BitmapTransform 方法來縮放和旋轉影像。如需有關設定中繼資料的詳細資訊,請參閱如何寫入影像中繼資料。如需有關設定像素資料的詳細資訊,請參閱如何編碼新影像。
// Scaling occurs before flip/rotation.
encoder.bitmapTransform.scaledWidth = 640;
encoder.bitmapTransform.scaledHeight = 480;
// Fant is a relatively high quality interpolation algorithm.
encoder.bitmapTransform.interpolationMode =
Windows.Graphics.Imaging.BitmapInterpolationMode.fant;
// Generate a new thumbnail from the updated pixel data.
// Note: Only JPEG, TIFF and JPEG-XR images support encoding thumbnails.
encoder.isThumbnailGenerated = true;
encoder.bitmapTransform.rotation =
Windows.Graphics.Imaging.BitmapRotation.clockwise90Degrees;
注意 如果使用 CreateForTranscodingAsync 建立 BitmapEncoder,則編碼器會嘗試使用不失真的方式複製所有原始資料。例如,如果您轉碼 JPEG 並且編輯一些影像屬性,但是沒有套用任何轉換或編輯像素資料,就會以不失真的方式複製影像。但是,如果您執行影像處理的方式是從解碼器取得像素資料,然後在編碼器上設定該資料,則一定會在處理過程中有所失真,因為像素資料必須經過重新編碼。
步驟 4: 排清編碼器並處理錯誤
編碼器使用結束後,請排清編碼器以完成編碼作業。您還需要處理影像格式不支援編碼縮圖時的狀況。如果您知道編輯的影像格式一定能支援縮圖 (例如 JPEG),就可以略過這項錯誤處理。
return encoder.flushAsync();
}).then(null, function (error) {
switch (error.number) {
// If the encoder doesn't support writing a thumbnail, then try again
// but disable thumbnail generation.
case -2003292287: // WINCODEC_ERR_UNSUPPORTEDOPERATION
encoder.isThumbnailGenerated = false;
return encoder.flushAsync();
default:
throw error;
}
步驟 5: 將編碼影像儲存到檔案,然後清除
最後,將內容從記憶體中的資料流複製到原始檔案的資料流,然後關閉所有資料流。
}).then(function () {
// Overwrite the contents of the file with the updated image stream.
memStream.seek(0);
fileStream.seek(0);
fileStream.size = 0;
return Windows.Storage.Streams.RandomAccessStream.copyAsync(memStream, fileStream);
}).done(function () {
memStream.close();
fileStream.close();
});