jadechoghari commited on
Commit
04754d2
·
verified ·
1 Parent(s): e87a6fe

Create processor.py

Browse files

this is the processor of vfusion3d

Files changed (1) hide show
  1. processor.py +88 -0
processor.py ADDED
@@ -0,0 +1,88 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import subprocess
2
+ import importlib
3
+ import sys
4
+
5
+ # a helper function to install packages
6
+ def install_package(package_name):
7
+ if importlib.util.find_spec(package_name) is None:
8
+ logger.info(f"Package '{package_name}' not found. Installing...")
9
+ subprocess.check_call([sys.executable, "-m", "pip", "install", package_name])
10
+ else:
11
+ logger.info(f"Package '{package_name}' is already installed.")
12
+ # we ensure the necessary packages are installed
13
+ packages = [
14
+ 'imageio[ffmpeg]', 'PyMCubes', 'trimesh', 'rembg[gpu,cli]', 'kiui', 'torchvision', 'Pillow'
15
+ ]
16
+ for package in packages:
17
+ install_package(package)
18
+
19
+ # only then we import the packages after installation
20
+ import torch
21
+ import numpy as np
22
+ from rembg import remove, new_session
23
+ from functools import partial
24
+ from torchvision.utils import save_image
25
+ from PIL import Image
26
+ from kiui.op import recenter
27
+ import kiui
28
+
29
+ class LRMImageProcessor:
30
+ def __init__(self, source_size=512, *args, **kwargs):
31
+ super().__init__(*args, **kwargs)
32
+ self.source_size = source_size
33
+ self.session = new_session("isnet-general-use")
34
+ self.rembg_remove = partial(remove, session=self.session)
35
+
36
+ def preprocess_image(self, image):
37
+ image = np.array(image)
38
+ image = self.rembg_remove(image)
39
+ mask = self.rembg_remove(image, only_mask=True)
40
+ image = recenter(image, mask, border_ratio=0.20)
41
+ image = torch.tensor(image).permute(2, 0, 1).unsqueeze(0) / 255.0
42
+ if image.shape[1] == 4:
43
+ image = image[:, :3, ...] * image[:, 3:, ...] + (1 - image[:, 3:, ...])
44
+ image = torch.nn.functional.interpolate(image, size=(self.source_size, self.source_size), mode='bicubic', align_corners=True)
45
+ image = torch.clamp(image, 0, 1)
46
+ return image
47
+
48
+ def get_normalized_camera_intrinsics(self, intrinsics: torch.Tensor):
49
+ fx, fy = intrinsics[:, 0, 0], intrinsics[:, 0, 1]
50
+ cx, cy = intrinsics[:, 1, 0], intrinsics[:, 1, 1]
51
+ width, height = intrinsics[:, 2, 0], intrinsics[:, 2, 1]
52
+ fx, fy = fx / width, fy / height
53
+ cx, cy = cx / width, cy / height
54
+ return fx, fy, cx, cy
55
+
56
+ def build_camera_principle(self, RT: torch.Tensor, intrinsics: torch.Tensor):
57
+ fx, fy, cx, cy = self.get_normalized_camera_intrinsics(intrinsics)
58
+ return torch.cat([
59
+ RT.reshape(-1, 12),
60
+ fx.unsqueeze(-1), fy.unsqueeze(-1), cx.unsqueeze(-1), cy.unsqueeze(-1),
61
+ ], dim=-1)
62
+
63
+ def _default_intrinsics(self):
64
+ fx = fy = 384
65
+ cx = cy = 256
66
+ w = h = 512
67
+ intrinsics = torch.tensor([
68
+ [fx, fy],
69
+ [cx, cy],
70
+ [w, h],
71
+ ], dtype=torch.float32)
72
+ return intrinsics
73
+
74
+ def _default_source_camera(self, batch_size: int = 1):
75
+ dist_to_center = 1.5
76
+ canonical_camera_extrinsics = torch.tensor([[
77
+ [0, 0, 1, 1],
78
+ [1, 0, 0, 0],
79
+ [0, 1, 0, 0],
80
+ ]], dtype=torch.float32)
81
+ canonical_camera_intrinsics = self._default_intrinsics().unsqueeze(0)
82
+ source_camera = self.build_camera_principle(canonical_camera_extrinsics, canonical_camera_intrinsics)
83
+ return source_camera.repeat(batch_size, 1)
84
+
85
+ def __call__(self, image, *args, **kwargs):
86
+ processed_image = self.preprocess_image(image)
87
+ source_camera = self._default_source_camera(batch_size=1)
88
+ return processed_image, source_camera