Repository: ManimCommunity/manim
File: manim/mobject/functions.py (Python)

Code before:
        discontinuities = np.array(list(discontinuities))
        boundary_times = [
            self.t_min,
            self.t_max,
            *(discontinuities - dt),
            *(discontinuities + dt),
        ]
        boundary_times.sort()
        for t1, t2 in zip(boundary_times[0::2], boundary_times[1::2]):
            t_range = list(np.arange(t1, t2, self.get_step_size(t1)))
            if t_range[-1] != t2:
                t_range.append(t2)
            points = np.array([self.function(t) for t in t_range])
            valid_indices = np.apply_along_axis(np.all, 1, np.isfinite(points))
            points = points[valid_indices]
            if len(points) > 0:
                self.start_new_path(points[0])
                self.add_points_as_corners(points[1:])
        self.make_smooth()
        return self


class FunctionGraph(ParametricFunction):
    def __init__(self, function, x_min=None, x_max=None, **kwargs):
        self.x_min = x_min or -config["frame_x_radius"]
        self.x_max = x_max or config["frame_x_radius"]
        self.parametric_function = lambda t: np.array([t, function(t), 0])
        ParametricFunction.__init__(
            self, self.parametric_function, self.x_min, self.x_max, **kwargs
        )
        self.function = function

    def get_function(self):
        return self.function

    def get_point_from_function(self, x):
        return self.parametric_function(x)


Review comment (suggestion):
If `x_min` or `x_max` are `0`, then the values from the config will be used instead. Best to explicitly check `if x_min is None:` and such

Code after:
        discontinuities = np.array(list(discontinuities))
        boundary_times = [
            self.t_min,
            self.t_max,
            *(discontinuities - dt),
            *(discontinuities + dt),
        ]
        boundary_times.sort()
        for t1, t2 in zip(boundary_times[0::2], boundary_times[1::2]):
            t_range = list(np.arange(t1, t2, self.get_step_size(t1)))
            if t_range[-1] != t2:
                t_range.append(t2)
            points = np.array([self.function(t) for t in t_range])
            valid_indices = np.apply_along_axis(np.all, 1, np.isfinite(points))
            points = points[valid_indices]
            if len(points) > 0:
                self.start_new_path(points[0])
                self.add_points_as_corners(points[1:])
        self.make_smooth()
        return self


class FunctionGraph(ParametricFunction):
    def __init__(self, function, x_min=None, x_max=None, color=YELLOW, **kwargs):
        if x_min is None:
            x_min = -config["frame_x_radius"]
        if x_max is None:
            x_max = config["frame_x_radius"]
        self.x_min = x_min
        self.x_max = x_max
        self.parametric_function = lambda t: np.array([t, function(t), 0])
        ParametricFunction.__init__(
            self,
            self.parametric_function,
            t_min=self.x_min,
            t_max=self.x_max,
            color=color,
            **kwargs
        )
        self.function = function

    def get_function(self):
        return self.function

    def get_point_from_function(self, x):
        return self.parametric_function(x)