Repository: godotengine/godot
File: editor/plugins/node_3d_editor_plugin.cpp (C++)

Code before:
			i--;
		}
	}

	clicked_wants_append = b->is_shift_pressed();

	if (selection_results.size() == 1) {
		clicked = selection_results[0].item->get_instance_id();
		selection_results.clear();

		if (clicked.is_valid()) {
			_select_clicked(spatial_editor->get_tool_mode() == Node3DEditor::TOOL_MODE_SELECT);
		}
	} else if (!selection_results.is_empty()) {
		NodePath root_path = get_tree()->get_edited_scene_root()->get_path();
		StringName root_name = root_path.get_name(root_path.get_name_count() - 1);

		for (int i = 0; i < selection_results.size(); i++) {
			Node3D *spat = selection_results[i].item;

			Ref<Texture2D> icon = EditorNode::get_singleton()->get_object_icon(spat, "Node");

			String node_path = "/" + root_name + "/" + root_path.rel_path_to(spat->get_path());

			int locked = 0;
			if (_is_node_locked(spat)) {
				locked = 1;
			} else {
				Node *ed_scene = EditorNode::get_singleton()->get_edited_scene();
				Node *node = spat;

				while (node && node != ed_scene->get_parent()) {
					Node3D *selected_tmp = Object::cast_to<Node3D>(node);
					if (selected_tmp && node->has_meta("_edit_group_")) {
						locked = 2;
					}
					node = node->get_parent();
				}
			}

			String suffix;
			if (locked == 1) {
				suffix = " (" + TTR("Locked") + ")";
			} else if (locked == 2) {
				suffix = " (" + TTR("Grouped") + ")";
			}
			selection_menu->add_item((String)spat->get_name() + suffix);
			selection_menu->set_item_icon(i, icon);
			selection_menu->set_item_metadata(i, node_path);
			selection_menu->set_item_tooltip(i, String(spat->get_name()) + "\nType: " + spat->get_class() + "\nPath: " + node_path);
		}

Review comment (suggestion):
```suggestion
					if (!selection_results.has(node)) {
```

Code after:

void Node3DEditorViewport::_surface_focus_exit() {
	view_menu->set_disable_shortcuts(true);
}

bool Node3DEditorViewport ::_is_node_locked(const Node *p_node) {
	return p_node->get_meta("_edit_lock_", false);
}

void Node3DEditorViewport::_list_select(Ref<InputEventMouseButton> b) {
	Vector<_RayResult> potential_selection_results;
	_find_items_at_pos(b->get_position(), potential_selection_results, spatial_editor->get_tool_mode() == Node3DEditor::TOOL_MODE_SELECT);

	Node *edited_scene = EditorNode::get_singleton()->get_edited_scene();

	// Filter to a list of nodes which include either the edited scene or nodes directly owned by the edited scene.
	// If a node has an invalid owner, recursively check their parents until a valid node is found.
	for (int i = 0; i < potential_selection_results.size(); i++) {
		Node3D *node = potential_selection_results[i].item;
		while (true) {
			if (node == nullptr || node == edited_scene->get_parent()) {
				break;
			} else {
				Node *node_owner = node->get_owner();
				if (node == edited_scene || node_owner == edited_scene || (node_owner != nullptr && edited_scene->is_editable_instance(node_owner))) {
					if (selection_results.has(node)) {
						selection_results.append(node);
					}
					break;
				}
			}
			node = Object::cast_to<Node3D>(node->get_parent());
		}
	}

	clicked_wants_append = b->is_shift_pressed();

	if (selection_results.size() == 1) {
		clicked = selection_results[0]->get_instance_id();
		selection_results.clear();

		if (clicked.is_valid()) {
			_select_clicked(spatial_editor->get_tool_mode() == Node3DEditor::TOOL_MODE_SELECT);
		}
	} else if (!selection_results.is_empty()) {
		NodePath root_path = get_tree()->get_edited_scene_root()->get_path();
		StringName root_name = root_path.get_name(root_path.get_name_count() - 1);

		for (int i = 0; i < selection_results.size(); i++) {
			Node3D *spat = selection_results[i];