LoginSignup
6
8

More than 1 year has passed since last update.

【DeepFake】PyTorchを使用してCEOを女体化するAIをつくる

Last updated at Posted at 2022-09-23

男に生まれたなら、
たまには女になりたいって思いますよね。

ということで、
今回はPyTorchを使って、DeepFakeで
CEOを女体化するAIをつくります。

DeepFakeは肖像権の問題など
法的には危ないので注意してくださいね。

くれぐれもアダルトなビデオに人気女優の顔を貼り付けるような
悪徳ビジネスはしないようにお願いいたします。

準備するもの

CEOを女体化

NVIDIA GPUとCUDAのバージョンを確認します。

!nvidia-smi
!nvcc --version

sber-swapというDeepFakeツール、モデルをもろもろインストールします。

!git clone https://github.com/sberbank-ai/sber-swap.git
%cd sber-swap
!wget -P ./arcface_model https://github.com/sberbank-ai/sber-swap/releases/download/arcface/backbone.pth
!wget -P ./arcface_model https://github.com/sberbank-ai/sber-swap/releases/download/arcface/iresnet.py
!wget -P ./insightface_func/models/antelope https://github.com/sberbank-ai/sber-swap/releases/download/antelope/glintr100.onnx
!wget -P ./insightface_func/models/antelope https://github.com/sberbank-ai/sber-swap/releases/download/antelope/scrfd_10g_bnkps.onnx
!wget -P ./weights https://github.com/sberbank-ai/sber-swap/releases/download/sber-swap-v2.0/G_unet_2blocks.pth
!wget -P ./weights https://github.com/sberbank-ai/sber-swap/releases/download/super-res/10_net_G.pth

ライブラリをインストールします。

!pip install mxnet-cu101mkl
!pip install onnxruntime-gpu==1.8
!pip install insightface==0.2.1
!pip install kornia==0.5.4

インポートします。

import cv2
import torch
import time
import os
import matplotlib.pyplot as plt

from IPython.display import HTML
from base64 import b64encode

from utils.inference.image_processing import crop_face, get_final_image, show_images
from utils.inference.video_processing import read_video, get_target, get_final_video, add_audio_from_another_video, face_enhancement
from utils.inference.core import model_inference

from network.AEI_Net import AEI_Net
from coordinate_reg.image_infer import Handler
from insightface_func.i import Face_detect_crop
from arcface_model.iresnet import iresnet100
from models.pix2pix_model import Pix2PixModel
from models.config_sr import TestOptions

モデルをつくります。

app = Face_detect_crop(name='antelope', root='./insightface_func/models')
app.prepare(ctx_id= 0, det_thresh=0.6, det_size=(640,640))

G = AEI_Net(backbone='unet', num_blocks=2, c_id=512)
G.eval()
G.load_state_dict(torch.load('weights/G_unet_2blocks.pth', map_location=torch.device('cpu')))
G = G.cuda()
G = G.half()

netArc = iresnet100(fp16=False)
netArc.load_state_dict(torch.load('arcface_model/backbone.pth'))
netArc=netArc.cuda()
netArc.eval()

handler = Handler('./coordinate_reg/model/2d106det', 0, ctx_id=0, det_size=640)

use_sr = True
if use_sr:
    os.environ['CUDA_VISIBLE_DEVICES'] = '0'
    torch.backends.cudnn.benchmark = True
    opt = TestOptions()
    model = Pix2PixModel(opt)
    model.netG.train()

画像と動画をアップロードします。
今回はtarget_type(完成形)をビデオにしています。

変数名 パス
source_path CEOの画像のパス
target_path (画像変換を行う場合)女性の画像のパス
path_to_video 女性の動画のパス

画像や動画はgoogle colabのここに格納します。

ちなみに、
フリーの画像や動画はpixabayなどからダウンロードできます。

target_type = 'video'

source_path = 'examples/images/jin.png'
target_path = 'examples/images/woman.png'
path_to_video = 'examples/videos/woman.mp4'

source_full = cv2.imread(source_path)
OUT_VIDEO_NAME = "examples/results/result.mp4"
crop_size = 224

try:
    source = crop_face(source_full, app, crop_size)[0]
    source = [source[:, :, ::-1]]
    print("Everything is ok!")
except TypeError:
    print("Bad source images")

if target_type == 'image':
    target_full = cv2.imread(target_path)
    full_frames = [target_full]
else:
    full_frames, fps = read_video(path_to_video)
target = get_target(full_frames, app, crop_size)

モデルを推論しましょう。

batch_size = 40

START_TIME = time.time()

final_frames_list, crop_frames_list, full_frames, tfm_array_list = model_inference(
    full_frames,
    source,
    target,
    netArc,
    G,
    app,
    set_target = False,
    crop_size=crop_size,
    BS=batch_size
)

if use_sr:
  final_frames_list = face_enhancement(final_frames_list, model)

if target_type == 'video':
  get_final_video(
      final_frames_list,
      crop_frames_list,
      full_frames,
      tfm_array_list,
      OUT_VIDEO_NAME,
      fps,
      handler
  )

  add_audio_from_another_video(path_to_video, OUT_VIDEO_NAME, "audio")

  print(f'Full pipeline took {time.time() - START_TIME}')
  print(f"Video saved with path {OUT_VIDEO_NAME}")
else:
  result = get_final_image(
      final_frames_list,
      crop_frames_list,
      full_frames[0],
      tfm_array_list,
      handler
  )
  cv2.imwrite('examples/results/result.png', result)

表示しましょう。

if target_type == 'image':
  show_images(
      [
          source[0][:,:,::-1],
          target_full,
          result
      ],
      [
          'Source Image',
          'Target Image',
          'Swapped Image'
      ],
      figsize=(20, 15)
  )
else:
  video_file = open(OUT_VIDEO_NAME, "r+b").read()
  video_url = f"data:video/mp4;base64,{b64encode(video_file).decode()}"
  
  HTML(f"""<video width={800} controls><source src="{video_url}"></video>""")

先ほどの動画が出力されました。

このように出力されます。(※sber-swap公式参照)

結論

気持ち悪い。


▼ ワンコインAI無料お試し

▼ DeepRecommendから限定情報を受け取る

6
8
7

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
8