예제 #1
0
    def point_to_rgb(self, point: np.ndarray) -> np.ndarray:
        x0, y0 = self.get_corner(UL)[:2]
        x1, y1 = self.get_corner(DR)[:2]
        x_alpha = inverse_interpolate(x0, x1, point[0])
        y_alpha = inverse_interpolate(y0, y1, point[1])
        if not (0 <= x_alpha <= 1) and (0 <= y_alpha <= 1):
            # TODO, raise smarter exception
            raise Exception("Cannot sample color from outside an image")

        pw, ph = self.image.size
        rgb = self.image.getpixel((
            int((pw - 1) * x_alpha),
            int((ph - 1) * y_alpha),
        ))
        return np.array(rgb) / 255
예제 #2
0
    def update_mobject(self, alpha):
        if self.num_anims == 0:
            # This probably doesn't matter for anything, but just in case,
            # we want it in the future, we set current_alpha even in this case
            self.current_alpha = alpha
            return

        gt_alpha_iter = iter(filter(
            lambda i: self.critical_alphas[i + 1] >= alpha,
            range(self.num_anims)
        ))
        i = next(gt_alpha_iter, None)
        if i is None:
            # In this case, we assume what is happening is that alpha is 1.0,
            # but that rounding error is causing us to overshoot the end of
            # self.critical_alphas (which is also 1.0)
            if not abs(alpha - 1) < 0.001:
                warnings.warn(
                    "Rounding error not near alpha=1 in Succession.update_mobject,"
                    "instead alpha = %f" % alpha
                )
                print(self.critical_alphas, alpha)
            i = self.num_anims - 1

        # At this point, we should have self.critical_alphas[i] <= alpha <= self.critical_alphas[i +1]

        self.jump_to_start_of_anim(i)
        sub_alpha = inverse_interpolate(
            self.critical_alphas[i],
            self.critical_alphas[i + 1],
            alpha
        )
        self.animations[i].update(sub_alpha)
        self.current_alpha = alpha
예제 #3
0
 def func(values):
     alphas = inverse_interpolate(min_value, max_value, np.array(values))
     alphas = np.clip(alphas, 0, 1)
     scaled_alphas = alphas * (len(rgbs) - 1)
     indices = scaled_alphas.astype(int)
     next_indices = np.clip(indices + 1, 0, len(rgbs) - 1)
     inter_alphas = scaled_alphas % 1
     inter_alphas = inter_alphas.repeat(3).reshape((len(indices), 3))
     result = interpolate(rgbs[indices], rgbs[next_indices], inter_alphas)
     return result
예제 #4
0
 def func(values):
     alphas = inverse_interpolate(
         min_value, max_value, np.array(values)
     )
     alphas = np.clip(alphas, 0, 1)
     # if flip_alphas:
     #     alphas = 1 - alphas
     scaled_alphas = alphas * (len(rgbs) - 1)
     indices = scaled_alphas.astype(int)
     next_indices = np.clip(indices + 1, 0, len(rgbs) - 1)
     inter_alphas = scaled_alphas % 1
     inter_alphas = inter_alphas.repeat(3).reshape((len(indices), 3))
     result = interpolate(rgbs[indices], rgbs[next_indices], inter_alphas)
     return result
예제 #5
0
    def point_from_proportion(self, alpha: float) -> np.ndarray:
        if alpha <= 0:
            return self.get_start()
        elif alpha >= 1:
            return self.get_end()

        partials = [0]
        for tup in self.get_bezier_tuples():
            # Approximate length with straight line from start to end
            arclen = get_norm(tup[0] - tup[-1])
            partials.append(partials[-1] + arclen)
        full = partials[-1]
        if full == 0:
            return self.get_start()
        # First index where the partial lenth is more alpha times the full length
        i = next(
            (i for i, x in enumerate(partials) if x >= full * alpha),
            len(partials)  # Default
        )
        residue = inverse_interpolate(partials[i - 1] / full, partials[i] / full, alpha)
        return self.get_nth_curve_function(i - 1)(residue)