読者です 読者をやめる 読者になる 読者になる

人工知能に関する断創録

人工知能、認知科学、心理学、ロボティクス、生物学などに興味を持っています。このブログでは人工知能のさまざまな分野について調査したことをまとめています。最近は、機械学習・Deep Learningに関する記事が多いです。



イメージを描画する

Pygame

BMP、GIF、PNG、JPGなどのイメージを画面に描画する方法です。pygame.imageを使います。GIFやPNGなどはお絵描きソフトで透明色(アルファ値)を指定して保存できますが、透明色が指定されていないときにスクリプト中で透明色を指定する方法も説明します。また、イメージのロードが簡単にできるように関数にまとめておきます。

背景の画像は、ぐったりにゃんこのホームページさん(リンク切れ)からお借りしました。また飛行機の画像は、FLYING YOGIさんからお借りしました。ちなみにサンプルスクリプト(1)の蛇はパイソンです。パイソンってのは蛇の種名ですね。プログラミング言語 Pythonのマスコットになってます。

draw_image.zip
f:id:aidiary:20100605092330p:plain
f:id:aidiary:20100605092329p:plain

サンプルスクリプト(1)

#!/usr/bin/env python
# -*- coding: utf-8 -*-
import pygame
from pygame.locals import *
import sys
 
SCREEN_SIZE = (640, 480)
 
pygame.init()
screen = pygame.display.set_mode(SCREEN_SIZE)
pygame.display.set_caption(u"イメージの描画")
 
# イメージを用意
backImg = pygame.image.load("moriyama.jpg").convert()        # 背景
pythonImg = pygame.image.load("python.png").convert_alpha()  # 蛇
 
while True:
    screen.blit(backImg, (0,0))        # 背景を描画
    screen.blit(pythonImg, (320,400))  # 蛇を描画
    pygame.display.update()
    
    for event in pygame.event.get():
        if event.type == QUIT:
            sys.exit()

サンプルスクリプト(2)

#!/usr/bin/env python
# -*- coding: utf-8 -*-
import pygame
from pygame.locals import *
import sys
 
SCREEN_SIZE = (640, 480)
 
pygame.init()
screen = pygame.display.set_mode(SCREEN_SIZE)
pygame.display.set_caption(u"透明色の指定")
 
planeImg = pygame.image.load("plane.png").convert()
 
# 透明色を指定したイメージを作成
planeImg2 = pygame.image.load("plane.png").convert()
colorkey = planeImg2.get_at((0,0))  # 左上の色を透明色に
planeImg2.set_colorkey(colorkey, RLEACCEL)
 
while True:
    screen.fill((0,0,0))
    screen.blit(planeImg, (100,100))
    screen.blit(planeImg2, (200,100))
    pygame.display.update()
    
    for event in pygame.event.get():
        if event.type == QUIT:
            sys.exit()

イメージを描画する

イメージを描画するには、まずファイルからイメージをロードする必要があります。Pygameは、BMP、GIF、JPG、PNGといったメジャーな画像ファイル形式以外にPCX、TGA、TIF、LBM、PBM、XPMもサポートしています。

# イメージを用意
backImg = pygame.image.load("moriyama.jpg").convert()        # 背景
pythonImg = pygame.image.load("python.png").convert_alpha()  # 蛇

イメージのロードには、pygame.image.load()関数を使います。引数にはファイル名を指定します。戻り値はイメージが描画されたSurfaceです。ウィンドウを表示する(2008/5/3)でも少し説明しましたが、Surfaceとはイメージが描画されたキャンバスみたいなものです。このSurfaceをメイン画面のSurface上に配置(blitと呼ぶ)することでイメージが描画できます。

上の例では、load()でロードしたSurfaceに対してSurface.convert()、Surface.convert_alpha()を適用しています。これは、ロードしたイメージをディスプレイと同じ形式に変換するための処理です。イメージがディスプレイと同じ形式だと描画がより高速になります。 convert()はオリジナルのイメージに透明色(アルファ値)が指定されていないときに使います。一方、convert_alpha()はオリジナルのイメージに透明色が指定されているときに使います。どちらも新たなSurfaceを返します。上の例では、背景のJPEGには透明色がないので convert()、蛇には透明色が指定してあるのでconvert_alpha()を使っています。実行画面を見るとわかりますが、蛇の背景は透明になってます。

screen.blit(backImg, (0,0))        # 背景を描画
screen.blit(pythonImg, (320,400))  # 蛇を描画

イメージを画面に描画するにはSurface.blit()を使います。実際は、描画というより転送というイメージです。draw()ではなく blit()という関数なのもそのためです。上の例ではメイン画面のSurfaceであるscreenにロードしたイメージを描画しています。第2引数は描画位置で左上の座標を指定します。ウィンドウを表示する(2008/5/3)でも説明しましたが、blit()しただけではまだ画面には表示されません。バックバッファに描画されただけだからです。最後にpygame.display.update()で画面を更新するとイメージが表示されます。

透明色を指定する

透明色は、ペイント用のツールでGIFやPNGに対して設定できますが、スクリプト中で透明色を指定することもできます。サンプルスクリプト2の飛行機の画像は背景の透明色を指定していないため青い四角形が見えてしまっています。

planeImg2 = pygame.image.load("plane.png").convert()
colorkey = planeImg2.get_at((0,0))  # 左上の色を透明色に
planeImg2.set_colorkey(colorkey, RLEACCEL)

透明色をしてするにはSurfaceにカラーキーをセットします。カラーキーとは透明色のことです。カラーキーはSurface.set_colorkey()でセットします。第1引数は(R,G,B)で表した色タプルです。第2引数はRLEACCELを指定します。上の例では、(R,G,B)を直接セットする代わりにイメージの左上隅 (0,0) の色をSurface.get_at()関数で取得しています。ほとんどの場合、左上隅が背景色だからこういう書き方をします。

イメージのロード用関数

イメージをロードする処理をまとめて下のような関数にしておくと簡単にロードできます。引数colorkeyに-1を与えると自動的に左上隅の色を透明色に設定します。戻り値はイメージのSurfaceとイメージの矩形です。イメージの矩形は後でスプライトを使うときに役立ちます。

下の関数は画像に透明色が指定されていないことを前提にしてます(convert()を使っている!)。Surface.get_colorkey()で透明色が指定されているかいないか調べられるため透明色を使っている場合はconvert_alpha()を使うように改造できます。

def load_image(filename, colorkey=None):
    try:
        image = pygame.image.load(filename)
    except pygame.error, message:
        print "Cannot load image:", filename
        raise SystemExit, message
    image = image.convert()
    if colorkey is not None:
        if colorkey is -1:
            colorkey = image.get_at((0,0))
        image.set_colorkey(colorkey, RLEACCEL)
    return image, image.get_rect()

# 使い方
planeImg, planeRect = load_image("plane.png", colorkey=-1)