def generate(self, x: np.ndarray, y: np.ndarray | None = None, **kwargs) -> np.ndarray:
        """
        Generate adversarial samples and return them in an array.

        :param x: Sample image/texture.
        :param y: Not used.
        :param label: A dictionary of target labels for object detector. The fields of the dictionary are as follows:

                    - `groundtruth_boxes_list`: A list of `nb_samples` size of 2-D tf.float32 tensors of shape
                                                [num_boxes, 4] containing coordinates of the groundtruth boxes.
                                                Groundtruth boxes are provided in [y_min, x_min, y_max, x_max]
                                                format and also assumed to be normalized as well as clipped
                                                relative to the image window with conditions y_min <= y_max and
                                                x_min <= x_max.
                    - `groundtruth_classes_list`: A list of `nb_samples` size of 1-D tf.float32 tensors of shape
                                                  [num_boxes] containing the class targets with the zero index
                                                  assumed to map to the first non-background class.
                    - `groundtruth_weights_list`: A list of `nb_samples` size of 1-D tf.float32 tensors of shape
                                                  [num_boxes] containing weights for groundtruth boxes.
        :type label: dict[str, list[np.ndarray]]
        :param mask: Input mask.
        :type mask: `np.ndarray`.
        :param target_class: Target class.
        :type target_class: int
        :param victim_class: Victim class.
        :type victim_class: int
        :param custom_loss: Custom loss function from users.
        :type custom_loss: Tensor
        :param rendering_function: A rendering function to use textures as input.
        :type rendering_function: Callable
        :return: Adversarial image/texture.
        """
        # Check input shape
        assert x.ndim == 4, "The ShapeShifter attack can only be applied to images."
        assert x.shape[0] == 1, "The ShapeShifter attack can only be applied to one image."
        assert list(x.shape[1:]) == self.estimator.input_shape

        # Check if label is provided
        label: dict[str, list[np.ndarray]] | None = kwargs.get("label")
        if label is None and not self.texture_as_input:  # pragma: no cover
            raise ValueError("Need the target labels for image as input.")

        # Check whether users have a custom loss
        custom_loss = kwargs.get("custom_loss")

        # Build the TensorFlow graph
        if not self.graph_available:
            self.graph_available = True

            if self.texture_as_input:
                # Check whether users provide a rendering function
                rendering_function = kwargs.get("rendering_function")
                if rendering_function is None:  # pragma: no cover
                    raise ValueError("Need a rendering function to use textures as input.")

                # Build the TensorFlow graph
                (
                    self.project_texture_op,
                    self.current_image_assign_to_input_image_op,
                    self.accumulated_gradients_op,
                    self.final_attack_optimization_op,
                    self.current_variable,
                    self.current_value,
                ) = self._build_graph(
                    initial_shape=x.shape, custom_loss=custom_loss, rendering_function=rendering_function
                )

            else:
                (
                    self.project_texture_op,
                    self.current_image_assign_to_input_image_op,
                    self.accumulated_gradients_op,
                    self.final_attack_optimization_op,
                    self.current_variable,
                    self.current_value,
                ) = self._build_graph(initial_shape=x.shape, custom_loss=custom_loss)

        # Use mask or not
        if self.texture_as_input:
            # Check whether users have a mask
            mask = kwargs.get("mask")
            if mask is None:
                mask = np.ones_like(x)
        else:
            mask = None

        # Get victim class
        victim_class = kwargs.get("victim_class")
        if victim_class is None:  # pragma: no cover
            raise ValueError("Need to provide a victim class.")

        if not isinstance(victim_class, int):  # pragma: no cover
            raise TypeError("Victim class must be of type `int`.")

        # Get target class
        target_class = kwargs.get("target_class")
        if target_class is None:
            logger.warning("Target class not provided, an untargeted attack is defaulted.")
            target_class = victim_class

        if not isinstance(target_class, int):  # pragma: no cover
            raise TypeError("Target class must be of type `int`.")

        # Run attack
        if label is None:  # pragma: no cover
            raise ValueError("Labels cannot be None.")
        result = self._attack_training(
            x=x,
            y=label,
            mask=mask,
            target_class=target_class,
            victim_class=victim_class,
            project_texture_op=self.project_texture_op,
            current_image_assign_to_input_image_op=self.current_image_assign_to_input_image_op,
            accumulated_gradients_op=self.accumulated_gradients_op,
            final_attack_optimization_op=self.final_attack_optimization_op,
            current_variable=self.current_variable,
            current_value=self.current_value,
        )

        return result[1]

        Generate adversarial samples and return them in an array.

        :param x: Sample image/texture.
        :param y: Not used.
        :param label: A dictionary of target labels for object detector. The fields of the dictionary are as follows:

                    - `groundtruth_boxes_list`: A list of `nb_samples` size of 2-D tf.float32 tensors of shape
                                                [num_boxes, 4] containing coordinates of the groundtruth boxes.
                                                Groundtruth boxes are provided in [y_min, x_min, y_max, x_max]
                                                format and also assumed to be normalized as well as clipped
                                                relative to the image window with conditions y_min <= y_max and
                                                x_min <= x_max.
                    - `groundtruth_classes_list`: A list of `nb_samples` size of 1-D tf.float32 tensors of shape
                                                  [num_boxes] containing the class targets with the zero index
                                                  assumed to map to the first non-background class.
                    - `groundtruth_weights_list`: A list of `nb_samples` size of 1-D tf.float32 tensors of shape
                                                  [num_boxes] containing weights for groundtruth boxes.
        :type label: dict[str, list[np.ndarray]]
        :param mask: Input mask.
        :type mask: `np.ndarray`.
        :param target_class: Target class.
        :type target_class: int
        :param victim_class: Victim class.
        :type victim_class: int
        :param custom_loss: Custom loss function from users.
        :type custom_loss: Tensor
        :param rendering_function: A rendering function to use textures as input.
        :type rendering_function: Callable
        :return: Adversarial image/texture.
        
art/attacks/evasion/shapeshifter.py