Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -394,36 +394,36 @@ std::vector<std::vector<torch::Tensor>> build_hierarchy(std::vector<torch::Tenso
std::vector<torch::Tensor> grid_evencorners(grids.size());
std::vector<torch::Tensor> grid_oddcorners(grids.size());

texture_positions[0] = torch::zeros({seq2pos.size() / 3, 3}, float_options);
texture_positions[1] = torch::zeros({seq2pos.size() / 3}, float_options);
texture_positions[0] = torch::zeros({(int64_t)(seq2pos.size() / 3), 3}, float_options);
texture_positions[1] = torch::zeros({(int64_t)(seq2pos.size() / 3)}, float_options);
float* positions_out_ptr = texture_positions[0].data_ptr<float>();
memcpy(positions_out_ptr, seq2pos.data(), sizeof(float) * seq2pos.size());
positions_out_ptr = texture_positions[1].data_ptr<float>();
for (int i = 0; i < grids[0].seq2grid.size(); ++i) {
for (int i = 0; i < (int)grids[0].seq2grid.size(); ++i) {
positions_out_ptr[i] = (i < grids[0].num_origin_seq);
}

for (int i = 0; i < grids.size(); ++i) {
grid_neighbors[i] = torch::zeros({grids[i].seq2grid.size(), 9}, int64_options);
long* nptr = grid_neighbors[i].data_ptr<long>();
for (int j = 0; j < grids[i].seq2neighbor.size(); ++j) {
for (int i = 0; i < (int)grids.size(); ++i) {
grid_neighbors[i] = torch::zeros({(int64_t)grids[i].seq2grid.size(), 9}, int64_options);
int64_t* nptr = grid_neighbors[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].seq2neighbor.size(); ++j) {
nptr[j] = grids[i].seq2neighbor[j];
}

grid_evencorners[i] = torch::zeros({grids[i].seq2evencorner.size()}, int64_options);
grid_oddcorners[i] = torch::zeros({grids[i].seq2oddcorner.size()}, int64_options);
long* dptr = grid_evencorners[i].data_ptr<long>();
for (int j = 0; j < grids[i].seq2evencorner.size(); ++j) {
grid_evencorners[i] = torch::zeros({(int64_t)grids[i].seq2evencorner.size()}, int64_options);
grid_oddcorners[i] = torch::zeros({(int64_t)grids[i].seq2oddcorner.size()}, int64_options);
int64_t* dptr = grid_evencorners[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].seq2evencorner.size(); ++j) {
dptr[j] = grids[i].seq2evencorner[j];
}
dptr = grid_oddcorners[i].data_ptr<long>();
for (int j = 0; j < grids[i].seq2oddcorner.size(); ++j) {
dptr = grid_oddcorners[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].seq2oddcorner.size(); ++j) {
dptr[j] = grids[i].seq2oddcorner[j];
}
if (i + 1 < grids.size()) {
grid_downsamples[i] = torch::zeros({grids[i].downsample_seq.size()}, int64_options);
long* dptr = grid_downsamples[i].data_ptr<long>();
for (int j = 0; j < grids[i].downsample_seq.size(); ++j) {
if (i + 1 < (int)grids.size()) {
grid_downsamples[i] = torch::zeros({(int64_t)grids[i].downsample_seq.size()}, int64_options);
int64_t* dptr = grid_downsamples[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].downsample_seq.size(); ++j) {
dptr[j] = grids[i].downsample_seq[j];
}
}
Expand Down Expand Up @@ -534,38 +534,38 @@ std::vector<std::vector<torch::Tensor>> build_hierarchy_with_feat(
std::vector<torch::Tensor> grid_evencorners(grids.size());
std::vector<torch::Tensor> grid_oddcorners(grids.size());

texture_positions[0] = torch::zeros({seq2pos.size() / 3, 3}, float_options);
texture_positions[1] = torch::zeros({seq2pos.size() / 3}, float_options);
texture_feats[0] = torch::zeros({seq2feat.size() / feat_channel, feat_channel}, float_options);
texture_positions[0] = torch::zeros({(int64_t)(seq2pos.size() / 3), 3}, float_options);
texture_positions[1] = torch::zeros({(int64_t)(seq2pos.size() / 3)}, float_options);
texture_feats[0] = torch::zeros({(int64_t)(seq2feat.size() / feat_channel), (int64_t)feat_channel}, float_options);
float* positions_out_ptr = texture_positions[0].data_ptr<float>();
memcpy(positions_out_ptr, seq2pos.data(), sizeof(float) * seq2pos.size());
positions_out_ptr = texture_positions[1].data_ptr<float>();
for (int i = 0; i < grids[0].seq2grid.size(); ++i) {
for (int i = 0; i < (int)grids[0].seq2grid.size(); ++i) {
positions_out_ptr[i] = (i < grids[0].num_origin_seq);
}
float* feats_out_ptr = texture_feats[0].data_ptr<float>();
memcpy(feats_out_ptr, seq2feat.data(), sizeof(float) * seq2feat.size());

for (int i = 0; i < grids.size(); ++i) {
grid_neighbors[i] = torch::zeros({grids[i].seq2grid.size(), 9}, int64_options);
long* nptr = grid_neighbors[i].data_ptr<long>();
for (int j = 0; j < grids[i].seq2neighbor.size(); ++j) {
for (int i = 0; i < (int)grids.size(); ++i) {
grid_neighbors[i] = torch::zeros({(int64_t)grids[i].seq2grid.size(), 9}, int64_options);
int64_t* nptr = grid_neighbors[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].seq2neighbor.size(); ++j) {
nptr[j] = grids[i].seq2neighbor[j];
}
grid_evencorners[i] = torch::zeros({grids[i].seq2evencorner.size()}, int64_options);
grid_oddcorners[i] = torch::zeros({grids[i].seq2oddcorner.size()}, int64_options);
long* dptr = grid_evencorners[i].data_ptr<long>();
for (int j = 0; j < grids[i].seq2evencorner.size(); ++j) {
grid_evencorners[i] = torch::zeros({(int64_t)grids[i].seq2evencorner.size()}, int64_options);
grid_oddcorners[i] = torch::zeros({(int64_t)grids[i].seq2oddcorner.size()}, int64_options);
int64_t* dptr = grid_evencorners[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].seq2evencorner.size(); ++j) {
dptr[j] = grids[i].seq2evencorner[j];
}
dptr = grid_oddcorners[i].data_ptr<long>();
for (int j = 0; j < grids[i].seq2oddcorner.size(); ++j) {
dptr = grid_oddcorners[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].seq2oddcorner.size(); ++j) {
dptr[j] = grids[i].seq2oddcorner[j];
}
if (i + 1 < grids.size()) {
grid_downsamples[i] = torch::zeros({grids[i].downsample_seq.size()}, int64_options);
long* dptr = grid_downsamples[i].data_ptr<long>();
for (int j = 0; j < grids[i].downsample_seq.size(); ++j) {
if (i + 1 < (int)grids.size()) {
grid_downsamples[i] = torch::zeros({(int64_t)grids[i].downsample_seq.size()}, int64_options);
int64_t* dptr = grid_downsamples[i].data_ptr<int64_t>();
for (int j = 0; j < (int)grids[i].downsample_seq.size(); ++j) {
dptr[j] = grids[i].downsample_seq[j];
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,24 +100,24 @@ std::vector<torch::Tensor> rasterize_image_cpu(torch::Tensor V, torch::Tensor F,
auto INT64_options = torch::TensorOptions().dtype(torch::kInt64).requires_grad(false);
auto findices = torch::zeros({height, width}, options);
INT64 maxint = (INT64)MAXINT * (INT64)MAXINT + (MAXINT - 1);
auto z_min = torch::ones({height, width}, INT64_options) * (long)maxint;
auto z_min = torch::ones({height, width}, INT64_options) * (int64_t)maxint;

if (!use_depth_prior) {
for (int i = 0; i < num_faces; ++i) {
rasterizeImagecoordsKernelCPU(V.data_ptr<float>(), F.data_ptr<int>(), 0,
(INT64*)z_min.data_ptr<long>(), occlusion_truncation, width, height, num_vertices, num_faces, i);
(INT64*)z_min.data_ptr<int64_t>(), occlusion_truncation, width, height, num_vertices, num_faces, i);
}
} else {
for (int i = 0; i < num_faces; ++i)
rasterizeImagecoordsKernelCPU(V.data_ptr<float>(), F.data_ptr<int>(), D.data_ptr<float>(),
(INT64*)z_min.data_ptr<long>(), occlusion_truncation, width, height, num_vertices, num_faces, i);
(INT64*)z_min.data_ptr<int64_t>(), occlusion_truncation, width, height, num_vertices, num_faces, i);
}

auto float_options = torch::TensorOptions().dtype(torch::kFloat32).requires_grad(false);
auto barycentric = torch::zeros({height, width, 3}, float_options);
for (int i = 0; i < width * height; ++i)
barycentricFromImgcoordCPU(V.data_ptr<float>(), F.data_ptr<int>(),
findices.data_ptr<int>(), (INT64*)z_min.data_ptr<long>(), width, height, num_vertices, num_faces, barycentric.data_ptr<float>(), i);
findices.data_ptr<int>(), (INT64*)z_min.data_ptr<int64_t>(), width, height, num_vertices, num_faces, barycentric.data_ptr<float>(), i);

return {findices, barycentric};
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -108,20 +108,20 @@ std::vector<torch::Tensor> rasterize_image_gpu(torch::Tensor V, torch::Tensor F,
auto INT64_options = torch::TensorOptions().dtype(torch::kInt64).device(torch::kCUDA, device_id).requires_grad(false);
auto findices = torch::zeros({height, width}, options);
INT64 maxint = (INT64)MAXINT * (INT64)MAXINT + (MAXINT - 1);
auto z_min = torch::ones({height, width}, INT64_options) * (long)maxint;
auto z_min = torch::ones({height, width}, INT64_options) * (int64_t)maxint;

if (!use_depth_prior) {
rasterizeImagecoordsKernelGPU<<<(num_faces+255)/256,256,0,at::cuda::getCurrentCUDAStream()>>>(V.data_ptr<float>(), F.data_ptr<int>(), 0,
(INT64*)z_min.data_ptr<long>(), occlusion_truncation, width, height, num_vertices, num_faces);
(INT64*)z_min.data_ptr<int64_t>(), occlusion_truncation, width, height, num_vertices, num_faces);
} else {
rasterizeImagecoordsKernelGPU<<<(num_faces+255)/256,256,0,at::cuda::getCurrentCUDAStream()>>>(V.data_ptr<float>(), F.data_ptr<int>(), D.data_ptr<float>(),
(INT64*)z_min.data_ptr<long>(), occlusion_truncation, width, height, num_vertices, num_faces);
(INT64*)z_min.data_ptr<int64_t>(), occlusion_truncation, width, height, num_vertices, num_faces);
}

auto float_options = torch::TensorOptions().dtype(torch::kFloat32).device(torch::kCUDA, device_id).requires_grad(false);
auto barycentric = torch::zeros({height, width, 3}, float_options);
barycentricFromImgcoordGPU<<<(width * height + 255)/256, 256>>>(V.data_ptr<float>(), F.data_ptr<int>(),
findices.data_ptr<int>(), (INT64*)z_min.data_ptr<long>(), width, height, num_vertices, num_faces, barycentric.data_ptr<float>());
findices.data_ptr<int>(), (INT64*)z_min.data_ptr<int64_t>(), width, height, num_vertices, num_faces, barycentric.data_ptr<float>());

return {findices, barycentric};
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
# init
Original file line number Diff line number Diff line change
Expand Up @@ -48,8 +48,10 @@ class Dino_v2(nn.Module):

def __init__(self, dino_v2_path):
super(Dino_v2, self).__init__()
print(f"[Dino_v2] Loading DINOv2 from: {dino_v2_path}...")
self.dino_processor = AutoImageProcessor.from_pretrained(dino_v2_path)
self.dino_v2 = AutoModel.from_pretrained(dino_v2_path)
print(f"[Dino_v2] DINOv2 loaded successfully")

for param in self.parameters():
param.requires_grad = False
Expand Down
8 changes: 4 additions & 4 deletions Gen_3D_Modules/Hunyuan3D_2_1/hy3dpaint/textureGenPipeline.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,14 +39,14 @@


class Hunyuan3DPaintConfig:
def __init__(self, max_num_view, resolution):
def __init__(self, max_num_view, resolution, multiview_pretrained_path=None, dino_ckpt_path=None, realesrgan_ckpt_path=None):
self.device = "cuda"

self.multiview_cfg_path = "cfgs/hunyuan-paint-pbr.yaml"
self.custom_pipeline = "hunyuanpaintpbr"
self.multiview_pretrained_path = "tencent/Hunyuan3D-2.1"
self.dino_ckpt_path = "facebook/dinov2-giant"
self.realesrgan_ckpt_path = "/home/ubuntu/oldrigger/AutoRigger/auto_rigger/models/ComfyUI/custom_nodes/ComfyUI-3D-Pack/Checkpoints/Diffusers/tencent/Hunyuan3D-2.1/RealESRGAN_x4plus.pth"
self.multiview_pretrained_path = multiview_pretrained_path or "tencent/Hunyuan3D-2.1"
self.dino_ckpt_path = dino_ckpt_path or "facebook/dinov2-giant"
self.realesrgan_ckpt_path = realesrgan_ckpt_path or "RealESRGAN_x4plus.pth"

self.raster_mode = "cr"
self.bake_mode = "back_sample"
Expand Down
17 changes: 13 additions & 4 deletions Gen_3D_Modules/Hunyuan3D_2_1/hy3dpaint/utils/multiview_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,17 +34,26 @@ def __init__(self, config) -> None:
self.cfg = cfg
self.mode = self.cfg.model.params.stable_diffusion_config.custom_pipeline[2:]

model_path = huggingface_hub.snapshot_download(
repo_id=config.multiview_pretrained_path,
allow_patterns=["hunyuan3d-paintpbr-v2-1/*"],
)
if os.path.isdir(config.multiview_pretrained_path):
print(f"[multiviewDiffusionNet] Using local model path: {config.multiview_pretrained_path}")
model_path = config.multiview_pretrained_path
else:
print(f"[multiviewDiffusionNet] Checking/Downloading model from HF: {config.multiview_pretrained_path}...")
model_path = huggingface_hub.snapshot_download(
repo_id=config.multiview_pretrained_path,
allow_patterns=["hunyuan3d-paintpbr-v2-1/*"],
)
print(f"[multiviewDiffusionNet] model_path: {model_path}")

model_path = os.path.join(model_path, "hunyuan3d-paintpbr-v2-1")
print(f"[multiviewDiffusionNet] Loading DiffusionPipeline from {model_path}...")
print(f"[multiviewDiffusionNet] Custom pipeline: {custom_pipeline}")
pipeline = DiffusionPipeline.from_pretrained(
model_path,
custom_pipeline=custom_pipeline,
torch_dtype=torch.float16
)
print(f"[multiviewDiffusionNet] DiffusionPipeline loaded.")

pipeline.scheduler = UniPCMultistepScheduler.from_config(pipeline.scheduler.config, timestep_spacing="trailing")
pipeline.set_progress_bar_config(disable=True)
Expand Down
28 changes: 24 additions & 4 deletions nodes.py
Original file line number Diff line number Diff line change
Expand Up @@ -5300,6 +5300,7 @@ def INPUT_TYPES(cls):

@staticmethod
def _ensure_weights():
# 1. Main Model (Hunyuan3D-2.1)
repo_id = f"{Load_Hunyuan3D_21_TexGen_Pipeline._REPO_ID_BASE}/{Load_Hunyuan3D_21_TexGen_Pipeline._REPO_NAME}"
safe_repo_name = Load_Hunyuan3D_21_TexGen_Pipeline._REPO_NAME.replace(".", "_")
base_dir = os.path.join(CKPT_DIFFUSERS_PATH, f"{Load_Hunyuan3D_21_TexGen_Pipeline._REPO_ID_BASE}/{safe_repo_name}")
Expand Down Expand Up @@ -5334,7 +5335,21 @@ def _ensure_weights():
else:
print(f"Hunyuan3D-2.1 TexGen weights already loaded")

return base_dir
# 2. DINOv2
dino_repo = "facebook/dinov2-giant"
dino_dir = os.path.join(CKPT_ROOT_PATH, "facebookresearch/dinov2-giant")
if not os.path.exists(os.path.join(dino_dir, "config.json")):
print(f"Loading DINOv2 folder: {dino_repo}")
snapshot_download(
repo_id=dino_repo,
local_dir=dino_dir,
resume_download=True,
ignore_patterns=HF_DOWNLOAD_IGNORE
)
else:
print(f"DINOv2 weights already loaded")

return base_dir, dino_dir

@staticmethod
def _ensure_realesrgan():
Expand Down Expand Up @@ -5368,12 +5383,17 @@ def load(self, max_num_view, resolution, enable_mmgp):
print(f"[TexGen-Loader] Using cached pipeline {cache_key}")
return (self._cache[cache_key],)

base_dir = self._ensure_weights()
base_dir, dino_dir = self._ensure_weights()
realesrgan_path = self._ensure_realesrgan()

# Configure pipeline
conf = Hunyuan3DPaintConfig_2_1(max_num_view=max_num_view, resolution=resolution)
conf.realesrgan_ckpt_path = realesrgan_path
conf = Hunyuan3DPaintConfig_2_1(
max_num_view=max_num_view,
resolution=resolution,
multiview_pretrained_path=base_dir,
dino_ckpt_path=dino_dir,
realesrgan_ckpt_path=realesrgan_path
)
conf.multiview_cfg_path = os.path.join(ROOT_PATH, "Gen_3D_Modules/Hunyuan3D_2_1/hy3dpaint/cfgs/hunyuan-paint-pbr.yaml")
conf.custom_pipeline = os.path.join(ROOT_PATH, "Gen_3D_Modules/Hunyuan3D_2_1/hy3dpaint/hunyuanpaintpbr")

Expand Down