4

PNGファイルがあり、Glossライブラリには。のBitmapコンストラクタがありPictureます。ファイルタイプが原因で使用できないloadBMP :: FilePath -> IO Pictureため、PNGファイルをロードしてBMPに変換し、、またはのいずれかにフィードする方法を探して bitmapOfBMP :: BMP -> PicturebitmapOfForeignPtr :: Int -> Int -> ForeignPtr Word8 -> Bool -> PictureますbitmapOfByteString :: Int -> Int -> ByteString -> Bool -> Picture


JuicyPixelsでテストする

import Data.ByteString as B
import System.IO as A

import Codec.Picture.Png
import Graphics.Gloss.Interface.Pure.Game


main = do
    png <- B.readFile "samus.png"
    let img = decodePng png
    case img of
        Left x -> A.putStrLn x
        Right x -> do
            let bmp = encodeDynamicPng x
            case bmp of
                Left x -> A.putStrLn x
                Right x -> do
                    let pic = bitmapOfByteString 29 52 x True
                    game pic

game pic
    =  play
        (InWindow "Test" (700, 500) (10, 10))
        white
        30
        pic
        draw
        (const id)
        (const id)

draw bmp
    = bmp

すべてが成功しますが、イメージはまったく同じではありません。

4

3 に答える 3

4

だから私はJuicyPixel-repaを作りました。画像をRepa配列として読み込み、gloss-osmで行ったように、次のように変換しPictureます。

repaToPicture :: Bool -> Array F.F DIM3 Word8 -> (Int, Int, Picture)
repaToPicture b arr =
let fptr = F.toForeignPtr arr
bs = BI.fromForeignPtr fptr 0 len
in (col, row, bitmapOfByteString row col bs b)
 where
  len = row * col * depth
  (Z :. row :. col :. depth) = extent arr

または、JuicyPixelsを直接使用して、DynamicImage型を大文字で囲みimgData、含まれているから基になるものを取得することもできますImage

于 2012-08-31T21:48:39.620 に答える
3

答えは一人ではありませんでしたが、トーマスの答えのおかげで、質問の中ではなく、ここに投稿します。

念のため、目標はBMPファイルを光沢のある画像に変換することなので、という関数を作成しbmpToPicました。他の2つの関数を使用し、多くのインポートが必要なため、モジュールに入れました。また、repaToPictureトーマスの答えはここでは少し異なります。

module PngToPic
    (pngToPic)
    where

import Data.ByteString as B
import Data.Word

import Codec.Picture.Png
import Codec.Picture.Repa
import qualified Data.ByteString.Internal as BI
import Data.Array.Repa ((:.)(..), Z, Z(..), extent, DIM3, Array)
import qualified Data.Array.Repa as R
import qualified Data.Array.Repa.Repr.ForeignPtr as F
import Graphics.Gloss.Data.Picture


pngToPic :: ByteString -> Picture
pngToPic png
    = let
        Right img -- unsafe
            = decodePng png
        repa
            = imgData (convertImage img :: Img RGBA)
    in repaToPicture True repa

repaToPicture :: Bool -> Array F.F DIM3 Word8 -> Picture
repaToPicture b arr
    = bitmapOfByteString row col bs b
    where
        bs
            = BI.fromForeignPtr fptr 0 (R.size sh)
        fptr
            = F.toForeignPtr arr'
        sh@(Z :. col :. row :. depth)
            = extent arr'
        arr'
            = flipVert arr

flipVert :: Array F.F DIM3 Word8 -> Array F.F DIM3 Word8
flipVert g
    = R.computeS $ R.backpermute e flop g
    where
        e@(Z :. x :. y :. _)
            = extent g
        flop (Z :. i         :. j         :. k)
            = Z :. x - i - 1 :. j :. k

あなたはそれを次のように使用します:

import Data.ByteString as B

import Graphics.Gloss.Interface.Pure.Game

import PngToPic

main = do
    png <- B.readFile "someImage.png"
    game $ pngToPic png

game pic
    = play
        (InWindow "Test" (700, 500) (10, 10))
        white
        30
        pic
        id
        (const id)
        (const id)

画像はウィンドウの中央に表示されます。

于 2012-09-05T18:40:43.723 に答える
0

2017年にこれに遭遇した人にとって、これは非常に簡単になりました!上記のサンプルコードが機能しなくなったため、理解するのに少し時間がかかりました。PNGを画像に読み込むための私の関数は次のとおりです。

import Codec.Picture.Repa (readImageRGBA, toByteString, reverseColorChannel)
import Graphics.Gloss

readPng :: FilePath -> Int -> Int -> IO Picture
readPng path w h = do
  (Right img) <- readImageRGBA path
  let bs = toByteString $ reverseColorChannel img
  return $ bitmapOfByteString w h (BitmapFormat TopToBottom PxRGBA) bs True
于 2017-11-26T17:26:57.753 に答える