Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to load an object twice ? It seems that the function set_cp() and set_name() duplicates the category_id #1120

Closed
prrw opened this issue Jun 27, 2024 · 4 comments
Labels
first answer provided question Question, not yet a bug ;)

Comments

@prrw
Copy link

prrw commented Jun 27, 2024

Describe the issue

I want to load an object (PLY file) twice in my environment. Since it is the same object, I want to associate it with same category_id and name. However, it seems that on the second time, it creates a duplicate category_id with a different name (Ending with .001). For example, if I am loading an object XYZ.ply twice, it creates category_id with same index and two names XYZ and XYZ.001. However I want the same category to appear for both the objects.
Moreover, I also get the the warning:
Warning! Detected output entries with duplicate keys and paths

What is the best way to load an object twice and generating coco_annotations with same category without duplicating it ?

Minimal code example

No response

Files required to run the code

No response

Expected behavior

I expect the categoryId not to be duplicated with a duplicate categoryName.

BlenderProc version

v2.7.0

@prrw prrw added the question Question, not yet a bug ;) label Jun 27, 2024
@cornerfarmer
Copy link
Member

In blender each object needs to have a unique name. However you can of course set the same category id for multiple objects. Please provide a minimal code example that reproduces your issue.

@prrw
Copy link
Author

prrw commented Jun 28, 2024

The following code will compile using standard examples of BlenderProc. I am using BlenderProc v2.7.0.

import blenderproc as bproc
import numpy as np
import argparse
import os

parser = argparse.ArgumentParser()
parser.add_argument('camera', nargs='?', default="examples/resources/camera_positions", help="Path to the camera file")
parser.add_argument('object', nargs='?', default="examples/advanced/random_backgrounds/object.ply", help="Path to the object file")
parser.add_argument('output_dir', nargs='?', default="examples/advanced/coco_annotations/output", help="Path to where the final files will be saved ")
args = parser.parse_args()

bproc.init()

# Define a function that samples the pose of a given sphere
def sample_pose(obj: bproc.types.MeshObject):
    obj.set_location(np.random.uniform([1, 1, 0.5], [-1, -1, 1]))
    obj.set_rotation_euler(bproc.sampler.uniformSO3())

objs = []
# load the objects into the scene
obj1 = bproc.loader.load_obj(args.object)
obj2 = bproc.loader.load_obj(args.object)

# Set some category ids for loaded objects
obj1[0].set_cp('category_id', 1)
obj1[0].set_name('Object')
objs.append(obj1[0])
obj2[0].set_cp('category_id', 1)
obj2[0].set_name('Object')
objs.append(obj2[0])

# Sample the poses of all objects
bproc.object.sample_poses(objs,sample_pose_func=sample_pose)

# define a light and set its location and energy level
light = bproc.types.Light()
light.set_type("POINT")
light.set_location([5, -5, 5])
light.set_energy(1000)

# define the camera intrinsics
bproc.camera.set_resolution(512, 512)

# read the camera positions file and convert into homogeneous camera-world transformation
with open(args.camera, "r") as f:
    for line in f.readlines():
        line = [float(x) for x in line.split()]
        position, euler_rotation = line[:3], line[3:6]
        matrix_world = bproc.math.build_transformation_mat(position, euler_rotation)
        bproc.camera.add_camera_pose(matrix_world)

# activate normal rendering
bproc.renderer.enable_normals_output()

# render the whole pipeline
data = bproc.renderer.render()
seg_data = bproc.renderer.render_segmap(map_by=["instance", "class", "name"])

# Write data to coco file
bproc.writer.write_coco_annotations(os.path.join(args.output_dir, 'coco_data'),
                        instance_segmaps=seg_data["instance_segmaps"],
                        instance_attribute_maps=seg_data["instance_attribute_maps"],
                        colors=data["colors"],
                        color_file_format="JPEG")

You can run it with the following line.

blenderproc run <this_script>.py examples/resources/camera_positions examples/advanced/random_backgrounds/object.ply examples/advanced/coco_annotations/output

Here one PLY file is loaded twice and assigned same categoryId and Name. However, upon inspecting the coco_annotations.json, it can be confirmed that upon adding the same CategoryName twice, the CategoryName changes from Object to Object.001. However, since this is the same object and same category, it would be logical to have the same CategoryName to preserve the ground truth. Here screen shot of the COCO file.
image

If I load an object multiple times randomly, the CategoryName ends with .001 , .002, .003 depending on the instance number. This generates multiple catrgory labels for same category. I hope , I was able to explain the problem in a clearer way. THanks :) Help very much appreciated.

@cornerfarmer
Copy link
Member

Hey,

thanks for the nice example. In the standard case, the name of the coco category depends on the order of the objects in the attribute maps. However, you can also set any name you want via the label_mapping parameter:

label_mapping = bproc.utility.LabelIdMapping.from_dict({"Object": 1})
bproc.writer.write_coco_annotations(os.path.join(args.output_dir, 'coco_data'),
                        instance_segmaps=seg_data["instance_segmaps"],
                        instance_attribute_maps=seg_data["instance_attribute_maps"],
                        label_mapping=label_mapping,
                        colors=data["colors"],
                        color_file_format="JPEG")

With that, the coco output should the way you want

@prrw
Copy link
Author

prrw commented Jul 1, 2024

Thanks a lot for the prompt reply. It worked.

@prrw prrw closed this as completed Jul 1, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
first answer provided question Question, not yet a bug ;)
Projects
None yet
Development

No branches or pull requests

2 participants