2012-02-29 26 views
3

我正在開發一個圖像處理應用程序,它必須能夠處理大圖像,例如我使用的方法是將源圖像分成多個適當大小的圖塊,以便可以將圖塊作爲位圖單獨加載到內存中,而不會超出可怕的VM限制,下一個圖像操作將在一切都是平鋪的,這一切都很好,但直到我想將這些瓦片縫合回最終的jpeg圖像。
我正在尋找一個內置的SDK API或免費潔具的解決方案,可以執行以下操作:
Android將多個位圖拼貼流到單個jpeg文件

  • 打開JPEG輸出文件作爲輸出流從位圖
  • 流RGB像素(塊1)到jpeg輸出流
  • 從位圖(片2)到jpeg輸出流
  • 等。
  • 流RGB像素對所有瓷磚
  • 關閉JPEG輸出流
  • 除了編寫我自己的JPEG編碼器之外的任何想法或指針?

    +0

    只是出於好奇,你如何在開始時切片的圖像? – 2012-02-29 22:28:48

    +0

    我使用帶有Rect的BitmapRegionDecoder來指示我想要抓取的源(​​大位圖/ jpeg)區域,例如如果我的源圖像是2000x2000像素,並且我想要4個圖塊,則第一個圖塊將是(0,0) - (1000,1000),其次是(1000,0) - (2000,1000),第三個圖元(0,1000) - (1000,2000)和第四(1000,1000) - (2000,2000)。我一個接一個地處理這些圖像,然後將其保存到SD卡上的臨時位圖上,然後將問題拼接回來以形成最終圖像(最好是jpeg)。 – 2012-02-29 22:34:32

    回答

    0

    這個怎麼樣:

    FileOutputStream outFile = new FileOutputStream(output_file); 
    bitmap.compress(Bitmap.CompressFormat.JPEG, 100, outFile); 
    outFile.flush(); 
    outFile.close(); 
    

    您可以調整質量設置(100)。請參閱docs

    您仍然需要決定如何對其進行分片。但是,如果您在設備上拍攝圖像,如果首先不會造成內存問題,爲什麼會加載整個圖像?

    將拼接塊拼接在一起:下面是我熟悉的slippy地圖使用的一種簡單方法。在標準尺寸

    1. 切磚(256×256說)
    2. 分配每瓦的X,Y值 - 這可能是一個目錄結構或文件名約定:即「0_0.jpg」
    3. 瓷磚的名稱(數字)與它們的頂部/左側像素位置有關。

    每一瓦片數目可以計算如下:

    tileX = floor(pixelX/256)

    tileY = floor(pixelY/256)

    所以瓦片在像素0,0 =瓦片(0,0),在像素瓦片256,0是瓷磚(1,0)等...

    +1

    這將做一個單一的位圖,但如果我想連接/縫2(或更多)位圖如何工作,有JPEG圖像數據周圍的JPEG頁眉和頁腳數據,FileOutputStream會創建初始流,但怎麼會bitmap.compress方法知道我將傳遞第二個(或更多)位圖,我可以調用bitmap1.compress(...),然後bitmap2.compress(...)和生成的文件將是一個jpeg包含兩個位圖連接在一起(如果是的話,這些將被垂直連接)? – 2012-02-29 22:41:11

    +0

    你問你如何將jpeg圖像一起加入屏幕? – dbryson 2012-02-29 22:43:15

    +0

    內存問題來自於大多數現代手機可以拍攝高分辨率圖像的事實。通過一個800萬像素的照相機,照相機將圖像作爲壓縮文件寫入SD卡,例如, jpeg,但隨後將其作爲位圖加載,導致產生更大的解壓縮圖像,這通常會超過16MB的VM限制(對於內存較少的手機的限制較低),因此在嘗試對可能很大的圖像執行圖像操作時必須非常狡猾位圖,因此平鋪和分割小塊的工作。 – 2012-02-29 22:45:14

    0

    您的拼接方法有兩個主要問題,最終會失敗。如果您要求系統對部分JPEG文件進行解碼,解碼時間將最多接近N倍(N =部件數量)。接下來的問題是,當試圖保存圖像時,將會耗盡內存。 JPEG圖像需要一次壓縮。如果你的整個未壓縮的圖像不適合內存,那麼你將無法使用你正在使用的技術。

    很難說明的是,對於目前設計的Android,您必須使用本機代碼來保存位圖,以便管理大於VM內存限制的映像。這並不困難,但它確實需要重新設計應用程序。

    +0

    感謝BitBank,我認爲本機代碼,但我相對較新的Android開發,我認爲你可以編碼一個jpeg連續,jpeg工作在8x8瓷磚,據我瞭解,然後壓縮,所以它仍然聽起來像它可以工作,但我採取你的表現。 – 2012-03-01 22:26:02

    +1

    JPEG本質上是由8x8塊構成的,但普通的JPEG編碼器不允許您零散地構建文件。您需要編寫自己的JPEG編碼器,並且仍然需要將所有水平片段一次存儲在內存中。您需要將圖像分成較短的橫條紋以對其進行增量編碼。 – BitBank 2012-03-01 22:42:37

    相關問題