【Pillow入門 第2回】Pythonで本格画像加工!カラーモード変換、明るさ調整、フィルター処理をマスターしよう 🎨

「撮った写真をPythonでオシャレな白黒写真に変換したい!」
「画像の明るさやコントラストを、プログラムで自動調整できないかな?」
「ぼかしやシャープ化みたいな、画像加工アプリにあるような効果ってPythonでできるの?」

こんにちは! Python画像処理探検隊、隊長のPythonistaです! 前回の第1回では、Pillowを使った画像の基本的な操作(読み込み、リサイズ、回転、切り抜きなど)を学びましたね。これで、画像の形を自由自在に変える準備が整いました。

シリーズ第2回の今回は、画像の「見た目」そのものを変化させる、よりクリエイティブな画像加工の世界に足を踏み入れます! 具体的には、

  • 画像のカラーモード変換(グレースケール化、二値化など)
  • ImageEnhanceモジュールを使った、明るさ・コントラスト・彩度の調整
  • ImageFilterモジュールを使った、ぼかし・シャープ化・輪郭抽出といったフィルター処理

といった、本格的な画像加工テクニックを解説していきます。この記事を読み終える頃には、あなたはPythonを使って写真の雰囲気をガラッと変えたり、見栄えを良くしたりする「加工」のスキルを身につけているはずです。さあ、Pillowであなたの写真をアート作品に変身させましょう!


1. 準備:モジュールのインポートと画像ファイルの用意

まずは、今回使用するモジュールをインポートし、加工の対象となる画像ファイルを用意しましょう。Pillowの様々な機能を使うために、Imageクラスに加えてImageEnhanceImageFilterもインポートしておきます。

【Pillowのインストールがまだの方へ】
ターミナルやコマンドプロンプトでpip install Pillowを実行してください。

from PIL import Image, ImageEnhance, ImageFilter
import os

# 加工対象の画像ファイルを用意してください
# このスクリプトと同じディレクトリに置くか、適切なパスを指定します。
image_path = 'sample.jpg' # ご自身の画像ファイルのパスに置き換えてください

# 加工した画像を保存するディレクトリを作成
output_dir = 'processed_images'
os.makedirs(output_dir, exist_ok=True)

# 元画像を開く
try:
    original_img = Image.open(image_path)
    print(f"画像 '{image_path}' を開きました。サイズ: {original_img.size}, モード: {original_img.mode}")
except FileNotFoundError:
    print(f"エラー: ファイル '{image_path}' が見つかりません。")
    original_img = None

この記事のこれ以降のコードは、original_imgオブジェクトが正常に読み込めていることを前提として進めます。


2. 色の世界を操る:カラーモードの変換

画像のカラーモードを変換することで、写真の雰囲気を大きく変えることができます。Pillowではconvert()メソッドを使って簡単に変換できます。

2.1. グレースケール化(白黒写真風)

カラー画像を白黒の濃淡だけで表現するグレースケールに変換するには、モード'L'を指定します。

# original_img が読み込まれている前提
if original_img:
    # グレースケールに変換
    grayscale_img = original_img.convert('L')
    
    # 保存して確認
    grayscale_img.save(os.path.join(output_dir, 'sample_grayscale.jpg'))
    print("\nグレースケール画像を保存しました。")
    # grayscale_img.show()


グレースケール化は、写真をノスタルジックな雰囲気にしたり、色情報をなくして形や陰影を強調したりするのによく使われます。

2.2. 二値化(白と黒だけのイラスト風)

画像を完全に白と黒の2色だけで表現するには、モード'1'を指定します。これはグレースケールとは異なり、中間の灰色が存在しないイラストのような見た目になります。

# original_img が読み込まれている前提
if original_img:
    # 白と黒の2値に変換
    binary_img = original_img.convert('1')
    
    # 保存して確認
    binary_img.save(os.path.join(output_dir, 'sample_binary.png')) # 2値画像はPNGなどが適しています
    print("二値化画像を保存しました。")
    # binary_img.show()

他のカラーモード(例: 'RGBA'(透明度付き)、'CMYK'(印刷用))への変換もconvert()メソッドで行えます。


3. 見栄えを調整!ImageEnhanceモジュール

ImageEnhanceモジュールを使うと、画像の明るさ、コントラスト、彩度、シャープネスといった「見栄え」に関わる要素を調整できます。

基本的な使い方:

  1. 調整したい種類のエンハンサーオブジェクトを作成します(例: ImageEnhance.Brightness(img))。
  2. エンハンサーオブジェクトのenhance(factor)メソッドを呼び出して、調整後の画像オブジェクトを取得します。

factorという「係数」で調整度合いを指定します。factor=1.0が元の画像で、そこから値を増減させて効果を適用します。

3.1. 明るさの調整 (ImageEnhance.Brightness)

factorが1.0より小さいと暗く、大きいと明るくなります。0.0で真っ黒になります。

# original_img が読み込まれている前提
if original_img:
    # 明るさ調整用のエンハンサーを作成
    enhancer = ImageEnhance.Brightness(original_img)
    
    # 元の画像の50%暗くする (factor=0.5)
    darker_img = enhancer.enhance(0.5)
    darker_img.save(os.path.join(output_dir, 'sample_darker.jpg'))
    
    # 元の画像の50%明るくする (factor=1.5)
    brighter_img = enhancer.enhance(1.5)
    brighter_img.save(os.path.join(output_dir, 'sample_brighter.jpg'))
    print("\n明るさを調整した画像を保存しました。")

[50%明るい]

[50%暗い]



3.2. コントラストの調整 (ImageEnhance.Contrast)

factorが1.0より小さいとコントラストが低く(のっぺりした印象に)、大きいとコントラストが高く(メリハリのある印象に)なります。0.0で灰一色になります。

# original_img が読み込まれている前提
if original_img:
    enhancer = ImageEnhance.Contrast(original_img)
    high_contrast_img = enhancer.enhance(1.8) # コントラストを上げる
    high_contrast_img.save(os.path.join(output_dir, 'sample_high_contrast.jpg'))
    print("コントラストを調整した画像を保存しました。")

3.3. 彩度の調整 (ImageEnhance.Color)

factorが1.0より小さいと色の鮮やかさが失われ、大きいと鮮やかになります。0.0でグレースケール画像と同じになります。

# original_img が読み込まれている前提
if original_img:
    enhancer = ImageEnhance.Color(original_img)
    vivid_img = enhancer.enhance(2.0) # 彩度を上げる
    vivid_img.save(os.path.join(output_dir, 'sample_vivid.jpg'))
    print("彩度を調整した画像を保存しました。")

3.4. シャープネスの調整 (ImageEnhance.Sharpness)

factorが1.0より小さいと画像がぼやけ、大きいとシャープ(くっきり)になります。0.0で完全にぼやけた画像、2.0でシャープネスをかけた画像になります。

# original_img が読み込まれている前提
if original_img:
    enhancer = ImageEnhance.Sharpness(original_img)
    sharpened_img = enhancer.enhance(2.0)
    sharpened_img.save(os.path.join(output_dir, 'sample_sharpened.jpg'))
    print("シャープネスを調整した画像を保存しました。")


4. クリエイティブな効果を適用!ImageFilterモジュール

ImageFilterモジュールには、あらかじめ定義された様々な画像フィルターが含まれています。これらを使うと、ぼかしや輪郭抽出といった、より芸術的な効果を簡単に適用できます。使い方はimg.filter(フィルターの種類)です。

4.1. ぼかし効果

  • ImageFilter.BLUR: シンプルなぼかしフィルター。
  • ImageFilter.BoxBlur(radius): 指定したradius(半径)のボックスぼかし。radiusが大きいほど強くぼける。
  • ImageFilter.GaussianBlur(radius=2): より自然な見た目のガウシアンぼかし。
# original_img が読み込まれている前提
if original_img:
    # ガウシアンぼかし
    blurred_img = original_img.filter(ImageFilter.GaussianBlur(radius=5))
    blurred_img.save(os.path.join(output_dir, 'sample_blurred.jpg'))
    print("\nぼかし効果を適用した画像を保存しました。")

4.2. 輪郭抽出とエッジ強調

  • ImageFilter.CONTOUR: 輪郭だけを線画のように抽出します。
  • ImageFilter.FIND_EDGES: エッジ(色の境界)を検出して表示します。
  • ImageFilter.EDGE_ENHANCE / EDGE_ENHANCE_MORE: エッジを強調し、画像をくっきりさせます。
  • ImageFilter.EMBOSS: 画像をエンボス加工(浮き彫り)したような効果を与えます。
  • ImageFilter.SHARPEN: 画像をシャープにします。
# original_img が読み込まれている前提
if original_img:
    # 輪郭抽出
    contour_img = original_img.filter(ImageFilter.CONTOUR)
    contour_img.save(os.path.join(output_dir, 'sample_contour.png'))
    print("輪郭抽出した画像を保存しました。")
    
    # エッジ検出
    find_edges_img = original_img.filter(ImageFilter.FIND_EDGES)
    find_edges_img.save(os.path.join(output_dir, 'sample_find_edges.png'))
    print("エッジ検出した画像を保存しました。")



5. 合わせ技!簡単な写真編集関数を作ってみよう

最後に、これまでのテクニックを組み合わせて、画像を「いい感じの雰囲気」にする簡単な関数を作ってみましょう。

from PIL import Image, ImageEnhance, ImageFilter

def apply_vintage_effect(input_path, output_path):
    """画像に簡単なヴィンテージ風エフェクトをかける関数"""
    try:
        with Image.open(input_path) as img:
            print(f"\n--- ヴィンテージ風加工を開始: {input_path} ---")
            
            # 1. 少しだけ彩度を落とす
            color_enhancer = ImageEnhance.Color(img)
            img = color_enhancer.enhance(0.7)
            
            # 2. 少しだけコントラストを上げる
            contrast_enhancer = ImageEnhance.Contrast(img)
            img = contrast_enhancer.enhance(1.2)
            
            # 3. ほんの少しだけぼかす
            img = img.filter(ImageFilter.GaussianBlur(radius=0.5))
            
            img.save(output_path)
            print(f"加工後の画像を '{output_path}' に保存しました。")
            # img.show()
            
    except FileNotFoundError:
        print(f"エラー: ファイル '{input_path}' が見つかりません。")
    except Exception as e:
        print(f"エラーが発生しました: {e}")

# 関数を実行してみる
if __name__ == "__main__":
    apply_vintage_effect('sample.jpg', os.path.join(output_dir, 'sample_vintage.jpg'))

このように処理を関数化することで、様々な画像に対して同じエフェクトを簡単に適用できるようになります。


まとめ:Pillowで画像の「表現力」を手に入れよう!

今回は、Pillow入門シリーズの第2回として、画像の見た目を本格的に加工するためのテクニックを学びました。

  • カラーモード変換 (convert()): 画像をグレースケールや白黒に変換して雰囲気を変える。
  • ImageEnhanceモジュール: 明るさ、コントラスト、彩度、シャープネスを調整し、写真の見栄えを良くする。
  • ImageFilterモジュール: ぼかしや輪郭抽出といった、よりクリエイティブなフィルター効果を適用する。

これらの機能を組み合わせることで、単なる変形だけでなく、画像の「表現」を大きく変えることができるようになります。SNS用の写真加工や、Webサイトの画像素材作成など、あなたのアイデア次第で様々な応用が考えられます。

次回は、Pillowのもう一つの強力な機能、画像の上に文字や図形を描画するためのImageDrawモジュールについて解説していきます。お楽しみに!

その他の投稿はこちら

コメント

このブログの人気の投稿

タイトルまとめ

これで迷わない!WindowsでPython環境構築する一番やさしい方法 #0

【Python標準ライブラリ完結!】11の冒険をありがとう!君のPython力が飛躍する「次の一歩」とは? 🚀