From 2fd0687b596f47c0c2bfde4f1fa9b6ba5e3c2f2f Mon Sep 17 00:00:00 2001 From: Ben Hambrecht Date: Fri, 26 Jan 2018 19:49:15 +0100 Subject: [PATCH 1/2] Added my playground files (for syncing btw my machines) --- .gitignore | 3 - ben_cairo_test.py | 54 +++++++++ ben_playground.py | 303 ++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 357 insertions(+), 3 deletions(-) create mode 100644 ben_cairo_test.py create mode 100644 ben_playground.py diff --git a/.gitignore b/.gitignore index f0f3ca3f..29cac87a 100644 --- a/.gitignore +++ b/.gitignore @@ -6,6 +6,3 @@ playground.py special_animations.py prettiness_hall_of_fame.py files/ -ben_playground.py - -ben_cairo_test.py diff --git a/ben_cairo_test.py b/ben_cairo_test.py new file mode 100644 index 00000000..85af2269 --- /dev/null +++ b/ben_cairo_test.py @@ -0,0 +1,54 @@ +#!/usr/bin/env python +"""demonstrate pycairo and pygame""" + +from __future__ import print_function + +import math +import sys + +import cairo +import pygame + + +def draw(surface): + x, y, radius = (250, 250, 200) + ctx = cairo.Context(surface) + ctx.set_line_width(15) + ctx.arc(x, y, radius, 0, 2.0 * math.pi) + ctx.set_source_rgb(0.8, 0.8, 0.8) + ctx.fill_preserve() + ctx.set_source_rgb(1, 1, 1) + ctx.stroke() + + +def input(events): + for event in events: + if event.type == pygame.QUIT: + sys.exit(0) + else: + print(event) + + +def main(): + width, height = 512, 512 + surface = cairo.ImageSurface(cairo.FORMAT_ARGB32, width, height) + + pygame.init() + pygame.display.set_mode((width, height)) + screen = pygame.display.get_surface() + + draw(surface) + + # Create PyGame surface from Cairo Surface + buf = surface.get_data() + image = pygame.image.frombuffer(buf, (width, height), "ARGB") + # Tranfer to Screen + screen.blit(image, (0, 0)) + pygame.display.flip() + + while True: + input(pygame.event.get()) + + +if __name__ == "__main__": + main() \ No newline at end of file diff --git a/ben_playground.py b/ben_playground.py new file mode 100644 index 00000000..1b7445fd --- /dev/null +++ b/ben_playground.py @@ -0,0 +1,303 @@ +#!/usr/bin/env python + +from helpers import * + +from mobject.tex_mobject import TexMobject +from mobject import Mobject +from mobject.image_mobject import ImageMobject +from mobject.vectorized_mobject import * +from mobject.point_cloud_mobject import PointCloudDot + +from animation.animation import Animation +from animation.transform import * +from animation.simple_animations import * +from animation.continual_animation import * +from animation.playground import * + +from topics.geometry import * +from topics.characters import * +from topics.functions import * +from topics.number_line import * +from topics.combinatorics import * +from scene import Scene +from camera import Camera +from mobject.svg_mobject import * +from mobject.tex_mobject import * + +from mobject.vectorized_mobject import * + +## To watch one of these scenes, run the following: +## python extract_scene.py -p file_name + +LIGHT_COLOR = YELLOW +DEGREES = 360/TAU +SWITCH_ON_RUN_TIME = 1.5 + + +class AmbientLight(VMobject): + + # Parameters are: + # * a source point + # * possibly a target + # * an opacity function and its inverse + # * a light color + # * a max opacity + + # If the target is None, create annuli. + # If there is a target, create annular sectors. + + CONFIG = { + "source_point" : ORIGIN, + "opacity_function" : lambda r : 1.0/(r+1.0)**2, + "color" : LIGHT_COLOR, + "max_opacity" : 1.0, + "num_levels" : 10, + "radius" : 5.0 + } + + def generate_points(self): + + for submob in self.submobjects: + self.remove(submob) + + # create annuli + dr = self.radius / self.num_levels + for r in np.arange(0, self.radius, dr): + alpha = self.max_opacity * self.opacity_function(r) + annulus = Annulus( + inner_radius = r, + outer_radius = r + dr, + color = self.color, + fill_opacity = alpha + ) + annulus.move_arc_center_to(self.source_point) + self.add(annulus) + + # else: + + # # look for the screen and create annular sectors + # lower_angle, upper_angle = self.viewing_angles(self.screen) + # dr = self.radius / self.num_levels + # for r in np.arange(0, self.radius, dr): + # alpha = self.max_opacity * self.opacity_function(r) + # annular_sector = AnnularSector( + # inner_radius = r, + # outer_radius = r + dr, + # color = self.color, + # fill_opacity = alpha, + # start_angle = lower_angle, + # angle = upper_angle - lower_angle + # ) + # annular_sector.move_arc_center_to(self.source_point) + # self.add(annular_sector) + + + + + + # def redraw(self): + # if self.screen != None: + # lower_angle, upper_angle = self.viewing_angles(self.screen) + # for submob in self.submobjects: + # if type(submob) == AnnularSector: + # submob.start_angle = lower_angle + # submob.angle = upper_angle - lower_angle + # submob.generate_points() + # submob.move_arc_center_to(self.source_point) + + + #submob.generate_points() + + + def move_source_to(self,point): + self.source_point = np.array(point) + for submob in self.submobjects: + if type(submob) == Annulus: + submob.shift(self.source_point - submob.get_center()) + + def dimming(self,new_alpha): + old_alpha = self.max_opacity + self.max_opacity = new_alpha + for submob in self.submobjects: + old_submob_alpha = submob.fill_opacity + new_submob_alpha = old_submob_alpha * new_alpha/old_alpha + submob.set_fill(opacity = new_submob_alpha) + + +class Spotlight(VMobject): + + CONFIG = { + "source_point" : ORIGIN, + "opacity_function" : lambda r : 1.0/(r+1.0)**2, + "color" : LIGHT_COLOR, + "max_opacity" : 1.0, + "num_levels" : 10, + "radius" : 5.0, + "screen" : None + } + + def track_screen(self): + self.generate_points() + + def generate_points(self): + + for submob in self.submobjects: + self.remove(submob) + + if self.screen != None: + # look for the screen and create annular sectors + lower_angle, upper_angle = self.viewing_angles(self.screen) + dr = self.radius / self.num_levels + for r in np.arange(0, self.radius, dr): + alpha = self.max_opacity * self.opacity_function(r) + annular_sector = AnnularSector( + inner_radius = r, + outer_radius = r + dr, + color = self.color, + fill_opacity = alpha, + start_angle = lower_angle, + angle = upper_angle - lower_angle + ) + annular_sector.move_arc_center_to(self.source_point) + self.add(annular_sector) + + + def viewing_angle_of_point(self,point): + distance_vector = point - self.source_point + angle = angle_of_vector(distance_vector) + return angle + + def viewing_angles(self,screen): + + viewing_angles = np.array(map(self.viewing_angle_of_point, + screen.get_anchors())) + lower_angle = upper_angle = 0 + if len(viewing_angles) != 0: + lower_angle = np.min(viewing_angles) + upper_angle = np.max(viewing_angles) + + return lower_angle, upper_angle + + def move_source_to(self,point): + self.source_point = np.array(point) + self.shift(np.array(point) - self.source_point) + self.generate_points() + + def dimming(self,new_alpha): + old_alpha = self.max_opacity + self.max_opacity = new_alpha + for submob in self.submobjects: + old_submob_alpha = submob.fill_opacity + new_submob_alpha = old_submob_alpha * new_alpha/old_alpha + submob.set_fill(opacity = new_submob_alpha) + + + +class SwitchOn(LaggedStart): + CONFIG = { + "lag_ratio": 0.2, + "run_time": SWITCH_ON_RUN_TIME + } + + def __init__(self, light, **kwargs): + if not isinstance(light,AmbientLight) and not isinstance(light,Spotlight): + raise Exception("Only LightCones and Candles can be switched on") + LaggedStart.__init__(self, + FadeIn, light, **kwargs) + + +class SwitchOff(LaggedStart): + CONFIG = { + "lag_ratio": 0.2, + "run_time": SWITCH_ON_RUN_TIME + } + + def __init__(self, light, **kwargs): + if not isinstance(light,AmbientLight) and not isinstance(light,Spotlight): + raise Exception("Only LightCones and Candles can be switched on") + light.submobjects = light.submobjects[::-1] + LaggedStart.__init__(self, + FadeOut, light, **kwargs) + light.submobjects = light.submobjects[::-1] + + +# class LightSource(Mobject): + +# # A light source is composed of: +# # * a lighthouse +# # * possibly a screen +# # * and two light fields: +# # * an undirected one (annuli) +# # * one directed at the screen (annular sectors) + +# CONFIG = { +# "location" : ORIGIN, +# "icon" : SVGMobject(file_name = 'lighthouse', height = 0.5), +# "ambient_light" : LightField(), +# "spot_light_field" : LightField(), +# } + +# def __init__(self,**kwargs): +# Mobject.__init__(self,**kwargs) +# self.icon.next_to(self.location, DOWN, buff = 0) +# self.spot_light_field.max_opacity = 0 +# self.ambient_light_field.move_source_to(self.location) +# self.spot_light_field.move_source_to(self.location) +# self.add(self.icon,self.ambient_light_field,self.spot_light_field) + +# def dim_ambient(self,new_alpha): +# self.ambient_light_field.dimming(new_alpha) + + + +class ScreenTracker(ContinualAnimation): + def __init__(self, spotlight, screen, **kwargs): + self.spotlight = spotlight + self.screen = screen + ContinualAnimation.__init__(self, self.spotlight, **kwargs) + +# def update_mobject(self, dt): + #self.spotlight.generate_points() + + + + +class IntroScene(Scene): + def construct(self): + + screen = Square().shift([4,0,0]) + #ambient_light = AmbientLight( + # source_point = np.array([-1,1,0]), + # max_opacity = 1.0, + # opacity_function = lambda r: 1.0/(r/1+1)**2, + # num_levels = 10, + #) + + #ambient_light.move_source_to([-5,0,0]) + self.add(screen)#,ambient_light) + + spotlight = Spotlight( + source_point = np.array([-1,1,0]), + max_opacity = 1.0, + opacity_function = lambda r: 1.0/(r/2+1)**2, + num_levels = 10, + screen = screen, + ) + + self.add(spotlight) + + ca = ScreenTracker(spotlight,screen) + self.add(ca) + + #self.play(SwitchOn(ambient_light)) + #self.play(ApplyMethod(ambient_light.move_source_to,[-3,1,0])) + #self.play(SwitchOn(spotlight)) + #self.play(ApplyMethod(spotlight.move_source_to,[-3,-1,0])) + #self.play(ApplyMethod(spotlight.dimming,0.2)) + self.play(screen.rotate, TAU/8, run_time = 3) + self.play(ApplyMethod(spotlight.move_source_to,[-4,0,0])) + + self.wait() + + + From daadc857c45ab608a8815f45b635def9fcc8c70d Mon Sep 17 00:00:00 2001 From: Ben Hambrecht Date: Fri, 26 Jan 2018 19:50:12 +0100 Subject: [PATCH 2/2] Revert "Added my playground files (for syncing btw my machines)" This reverts commit 2fd0687b596f47c0c2bfde4f1fa9b6ba5e3c2f2f. --- .gitignore | 3 + ben_cairo_test.py | 54 --------- ben_playground.py | 303 ---------------------------------------------- 3 files changed, 3 insertions(+), 357 deletions(-) delete mode 100644 ben_cairo_test.py delete mode 100644 ben_playground.py diff --git a/.gitignore b/.gitignore index 29cac87a..f0f3ca3f 100644 --- a/.gitignore +++ b/.gitignore @@ -6,3 +6,6 @@ playground.py special_animations.py prettiness_hall_of_fame.py files/ +ben_playground.py + +ben_cairo_test.py diff --git a/ben_cairo_test.py b/ben_cairo_test.py deleted file mode 100644 index 85af2269..00000000 --- a/ben_cairo_test.py +++ /dev/null @@ -1,54 +0,0 @@ -#!/usr/bin/env python -"""demonstrate pycairo and pygame""" - -from __future__ import print_function - -import math -import sys - -import cairo -import pygame - - -def draw(surface): - x, y, radius = (250, 250, 200) - ctx = cairo.Context(surface) - ctx.set_line_width(15) - ctx.arc(x, y, radius, 0, 2.0 * math.pi) - ctx.set_source_rgb(0.8, 0.8, 0.8) - ctx.fill_preserve() - ctx.set_source_rgb(1, 1, 1) - ctx.stroke() - - -def input(events): - for event in events: - if event.type == pygame.QUIT: - sys.exit(0) - else: - print(event) - - -def main(): - width, height = 512, 512 - surface = cairo.ImageSurface(cairo.FORMAT_ARGB32, width, height) - - pygame.init() - pygame.display.set_mode((width, height)) - screen = pygame.display.get_surface() - - draw(surface) - - # Create PyGame surface from Cairo Surface - buf = surface.get_data() - image = pygame.image.frombuffer(buf, (width, height), "ARGB") - # Tranfer to Screen - screen.blit(image, (0, 0)) - pygame.display.flip() - - while True: - input(pygame.event.get()) - - -if __name__ == "__main__": - main() \ No newline at end of file diff --git a/ben_playground.py b/ben_playground.py deleted file mode 100644 index 1b7445fd..00000000 --- a/ben_playground.py +++ /dev/null @@ -1,303 +0,0 @@ -#!/usr/bin/env python - -from helpers import * - -from mobject.tex_mobject import TexMobject -from mobject import Mobject -from mobject.image_mobject import ImageMobject -from mobject.vectorized_mobject import * -from mobject.point_cloud_mobject import PointCloudDot - -from animation.animation import Animation -from animation.transform import * -from animation.simple_animations import * -from animation.continual_animation import * -from animation.playground import * - -from topics.geometry import * -from topics.characters import * -from topics.functions import * -from topics.number_line import * -from topics.combinatorics import * -from scene import Scene -from camera import Camera -from mobject.svg_mobject import * -from mobject.tex_mobject import * - -from mobject.vectorized_mobject import * - -## To watch one of these scenes, run the following: -## python extract_scene.py -p file_name - -LIGHT_COLOR = YELLOW -DEGREES = 360/TAU -SWITCH_ON_RUN_TIME = 1.5 - - -class AmbientLight(VMobject): - - # Parameters are: - # * a source point - # * possibly a target - # * an opacity function and its inverse - # * a light color - # * a max opacity - - # If the target is None, create annuli. - # If there is a target, create annular sectors. - - CONFIG = { - "source_point" : ORIGIN, - "opacity_function" : lambda r : 1.0/(r+1.0)**2, - "color" : LIGHT_COLOR, - "max_opacity" : 1.0, - "num_levels" : 10, - "radius" : 5.0 - } - - def generate_points(self): - - for submob in self.submobjects: - self.remove(submob) - - # create annuli - dr = self.radius / self.num_levels - for r in np.arange(0, self.radius, dr): - alpha = self.max_opacity * self.opacity_function(r) - annulus = Annulus( - inner_radius = r, - outer_radius = r + dr, - color = self.color, - fill_opacity = alpha - ) - annulus.move_arc_center_to(self.source_point) - self.add(annulus) - - # else: - - # # look for the screen and create annular sectors - # lower_angle, upper_angle = self.viewing_angles(self.screen) - # dr = self.radius / self.num_levels - # for r in np.arange(0, self.radius, dr): - # alpha = self.max_opacity * self.opacity_function(r) - # annular_sector = AnnularSector( - # inner_radius = r, - # outer_radius = r + dr, - # color = self.color, - # fill_opacity = alpha, - # start_angle = lower_angle, - # angle = upper_angle - lower_angle - # ) - # annular_sector.move_arc_center_to(self.source_point) - # self.add(annular_sector) - - - - - - # def redraw(self): - # if self.screen != None: - # lower_angle, upper_angle = self.viewing_angles(self.screen) - # for submob in self.submobjects: - # if type(submob) == AnnularSector: - # submob.start_angle = lower_angle - # submob.angle = upper_angle - lower_angle - # submob.generate_points() - # submob.move_arc_center_to(self.source_point) - - - #submob.generate_points() - - - def move_source_to(self,point): - self.source_point = np.array(point) - for submob in self.submobjects: - if type(submob) == Annulus: - submob.shift(self.source_point - submob.get_center()) - - def dimming(self,new_alpha): - old_alpha = self.max_opacity - self.max_opacity = new_alpha - for submob in self.submobjects: - old_submob_alpha = submob.fill_opacity - new_submob_alpha = old_submob_alpha * new_alpha/old_alpha - submob.set_fill(opacity = new_submob_alpha) - - -class Spotlight(VMobject): - - CONFIG = { - "source_point" : ORIGIN, - "opacity_function" : lambda r : 1.0/(r+1.0)**2, - "color" : LIGHT_COLOR, - "max_opacity" : 1.0, - "num_levels" : 10, - "radius" : 5.0, - "screen" : None - } - - def track_screen(self): - self.generate_points() - - def generate_points(self): - - for submob in self.submobjects: - self.remove(submob) - - if self.screen != None: - # look for the screen and create annular sectors - lower_angle, upper_angle = self.viewing_angles(self.screen) - dr = self.radius / self.num_levels - for r in np.arange(0, self.radius, dr): - alpha = self.max_opacity * self.opacity_function(r) - annular_sector = AnnularSector( - inner_radius = r, - outer_radius = r + dr, - color = self.color, - fill_opacity = alpha, - start_angle = lower_angle, - angle = upper_angle - lower_angle - ) - annular_sector.move_arc_center_to(self.source_point) - self.add(annular_sector) - - - def viewing_angle_of_point(self,point): - distance_vector = point - self.source_point - angle = angle_of_vector(distance_vector) - return angle - - def viewing_angles(self,screen): - - viewing_angles = np.array(map(self.viewing_angle_of_point, - screen.get_anchors())) - lower_angle = upper_angle = 0 - if len(viewing_angles) != 0: - lower_angle = np.min(viewing_angles) - upper_angle = np.max(viewing_angles) - - return lower_angle, upper_angle - - def move_source_to(self,point): - self.source_point = np.array(point) - self.shift(np.array(point) - self.source_point) - self.generate_points() - - def dimming(self,new_alpha): - old_alpha = self.max_opacity - self.max_opacity = new_alpha - for submob in self.submobjects: - old_submob_alpha = submob.fill_opacity - new_submob_alpha = old_submob_alpha * new_alpha/old_alpha - submob.set_fill(opacity = new_submob_alpha) - - - -class SwitchOn(LaggedStart): - CONFIG = { - "lag_ratio": 0.2, - "run_time": SWITCH_ON_RUN_TIME - } - - def __init__(self, light, **kwargs): - if not isinstance(light,AmbientLight) and not isinstance(light,Spotlight): - raise Exception("Only LightCones and Candles can be switched on") - LaggedStart.__init__(self, - FadeIn, light, **kwargs) - - -class SwitchOff(LaggedStart): - CONFIG = { - "lag_ratio": 0.2, - "run_time": SWITCH_ON_RUN_TIME - } - - def __init__(self, light, **kwargs): - if not isinstance(light,AmbientLight) and not isinstance(light,Spotlight): - raise Exception("Only LightCones and Candles can be switched on") - light.submobjects = light.submobjects[::-1] - LaggedStart.__init__(self, - FadeOut, light, **kwargs) - light.submobjects = light.submobjects[::-1] - - -# class LightSource(Mobject): - -# # A light source is composed of: -# # * a lighthouse -# # * possibly a screen -# # * and two light fields: -# # * an undirected one (annuli) -# # * one directed at the screen (annular sectors) - -# CONFIG = { -# "location" : ORIGIN, -# "icon" : SVGMobject(file_name = 'lighthouse', height = 0.5), -# "ambient_light" : LightField(), -# "spot_light_field" : LightField(), -# } - -# def __init__(self,**kwargs): -# Mobject.__init__(self,**kwargs) -# self.icon.next_to(self.location, DOWN, buff = 0) -# self.spot_light_field.max_opacity = 0 -# self.ambient_light_field.move_source_to(self.location) -# self.spot_light_field.move_source_to(self.location) -# self.add(self.icon,self.ambient_light_field,self.spot_light_field) - -# def dim_ambient(self,new_alpha): -# self.ambient_light_field.dimming(new_alpha) - - - -class ScreenTracker(ContinualAnimation): - def __init__(self, spotlight, screen, **kwargs): - self.spotlight = spotlight - self.screen = screen - ContinualAnimation.__init__(self, self.spotlight, **kwargs) - -# def update_mobject(self, dt): - #self.spotlight.generate_points() - - - - -class IntroScene(Scene): - def construct(self): - - screen = Square().shift([4,0,0]) - #ambient_light = AmbientLight( - # source_point = np.array([-1,1,0]), - # max_opacity = 1.0, - # opacity_function = lambda r: 1.0/(r/1+1)**2, - # num_levels = 10, - #) - - #ambient_light.move_source_to([-5,0,0]) - self.add(screen)#,ambient_light) - - spotlight = Spotlight( - source_point = np.array([-1,1,0]), - max_opacity = 1.0, - opacity_function = lambda r: 1.0/(r/2+1)**2, - num_levels = 10, - screen = screen, - ) - - self.add(spotlight) - - ca = ScreenTracker(spotlight,screen) - self.add(ca) - - #self.play(SwitchOn(ambient_light)) - #self.play(ApplyMethod(ambient_light.move_source_to,[-3,1,0])) - #self.play(SwitchOn(spotlight)) - #self.play(ApplyMethod(spotlight.move_source_to,[-3,-1,0])) - #self.play(ApplyMethod(spotlight.dimming,0.2)) - self.play(screen.rotate, TAU/8, run_time = 3) - self.play(ApplyMethod(spotlight.move_source_to,[-4,0,0])) - - self.wait() - - -