0sphinx.addnodesdocument)}( rawsourcechildren](docutils.nodessection)}(hhh](h title)}(h$Seamless interoperation with the DOMh]h Text$Seamless interoperation with the DOM}(hhparenthhhsourceNlineNuba attributes}(ids]classes]names]dupnames]backrefs]utagnamehhh hhh_/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/docs/sphinx/integration_javascript.rsthKubh )}(hhh](h)}(hKPractical example: a simple, responsive website using no HTML or CSS at allh]hKPractical example: a simple, responsive website using no HTML or CSS at all}(hh1hh/hhhNhNubah}(h ]h"]h$]h&]h(]uh*hhh,hhhh+hKubh paragraph)}(hXQTo many programmers, using 'static' HTML and CSS feels like being locked up in a closet. As an alternative, responsiveness can simply be programmed using Transcrypt, as can be seen on `the website of Transcrypt itself `_. The site adapts to diverse screen formats, device types and landscape vs. portrait mode.h](hTo many programmers, using ‘static’ HTML and CSS feels like being locked up in a closet. As an alternative, responsiveness can simply be programmed using Transcrypt, as can be seen on }(hTo many programmers, using 'static' HTML and CSS feels like being locked up in a closet. As an alternative, responsiveness can simply be programmed using Transcrypt, as can be seen on hh?hhhNhNubh reference)}(h?`the website of Transcrypt itself `_h]h the website of Transcrypt itself}(h the website of Transcrypt itselfhhJubah}(h ]h"]h$]h&]h(]name the website of Transcrypt itselfrefurihttp://www.transcrypt.orguh*hHhh?ubh target)}(h h]h}(h ] the-website-of-transcrypt-itselfah"]h$] the website of transcrypt itselfah&]h(]refurih\uh*h] referencedKhh?ubhZ. The site adapts to diverse screen formats, device types and landscape vs. portrait mode.}(hZ. The site adapts to diverse screen formats, device types and landscape vs. portrait mode.hh?hhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhh,hhubeh}(h ]Ipractical-example-a-simple-responsive-website-using-no-html-or-css-at-allah"]h$]Kpractical example: a simple, responsive website using no html or css at allah&]h(]uh*h hh hhhh+hKubh )}(hhh](h)}(hSVG example: Turtle graphicsh]hSVG example: Turtle graphics}(hhhhhhhNhNubah}(h ]h"]h$]h&]h(]uh*hhhhhhh+hK ubh>)}(hX*Turtle graphics* are a way to teach computer programming to children, invented by Seymour Papert in the 1960's. Lines are drawn as 'track' of a walking turtle, that can move ahead and turn. Children use turtle graphics intuitively by imagining what they would do if they were the turtle. This leads to a *recipe of motion*, indeed an *algorithm*, which is the basis of imperative (as opposed to e.g. declarative) programming.h](h emphasis)}(h*Turtle graphics*h]hTurtle graphics}(hhhhubah}(h ]h"]h$]h&]h(]uh*hhhubhX& are a way to teach computer programming to children, invented by Seymour Papert in the 1960’s. Lines are drawn as ‘track’ of a walking turtle, that can move ahead and turn. Children use turtle graphics intuitively by imagining what they would do if they were the turtle. This leads to a }(hX  are a way to teach computer programming to children, invented by Seymour Papert in the 1960's. Lines are drawn as 'track' of a walking turtle, that can move ahead and turn. Children use turtle graphics intuitively by imagining what they would do if they were the turtle. This leads to a hhhhhNhNubh)}(h*recipe of motion*h]hrecipe of motion}(hhhhubah}(h ]h"]h$]h&]h(]uh*hhhubh , indeed an }(h , indeed an hhhhhNhNubh)}(h *algorithm*h]h algorithm}(hhhhubah}(h ]h"]h$]h&]h(]uh*hhhubhP, which is the basis of imperative (as opposed to e.g. declarative) programming.}(hP, which is the basis of imperative (as opposed to e.g. declarative) programming.hhhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhhhhubh>)}(hX-*SVG* or *Scalable Vector Graphics* are a way to display high quality graphs, e.g. in the browser. SVG, as opposed to e.g. the HTML Canvas, bypasses the pixel paradigm and works with floating point coordinates directly. As a consequence, SVG plots can be zoomed without becoming ragged or 'pixelated'.h](h)}(h*SVG*h]hSVG}(hhhhubah}(h ]h"]h$]h&]h(]uh*hhhubh or }(h or hhhhhNhNubh)}(h*Scalable Vector Graphics*h]hScalable Vector Graphics}(hhhhubah}(h ]h"]h$]h&]h(]uh*hhhubhX are a way to display high quality graphs, e.g. in the browser. SVG, as opposed to e.g. the HTML Canvas, bypasses the pixel paradigm and works with floating point coordinates directly. As a consequence, SVG plots can be zoomed without becoming ragged or ‘pixelated’.}(hX  are a way to display high quality graphs, e.g. in the browser. SVG, as opposed to e.g. the HTML Canvas, bypasses the pixel paradigm and works with floating point coordinates directly. As a consequence, SVG plots can be zoomed without becoming ragged or 'pixelated'.hhhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhhhhubh>)}(hXWhen looking under the hood of SVG, there's an amazing correspondence between the primitives in an SVG *path* and the primitives of turtle graphics. So both from an aestethical and from a conceptual point of view, turtle graphics and SVG form a happy mariage.h](hiWhen looking under the hood of SVG, there’s an amazing correspondence between the primitives in an SVG }(hgWhen looking under the hood of SVG, there's an amazing correspondence between the primitives in an SVG hjhhhNhNubh)}(h*path*h]hpath}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubh and the primitives of turtle graphics. So both from an aestethical and from a conceptual point of view, turtle graphics and SVG form a happy mariage.}(h and the primitives of turtle graphics. So both from an aestethical and from a conceptual point of view, turtle graphics and SVG form a happy mariage.hjhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhhhhubh>)}(hXTurtle graphics in Transcrypt do not require the use of any graphics libraries. Below are two turtle graphics examples and the source code of Transcrypt's *turtle* module, which is quite compact. As can be seen from the code integration between Transcrypt and JavaScript is trivial.h](hTurtle graphics in Transcrypt do not require the use of any graphics libraries. Below are two turtle graphics examples and the source code of Transcrypt’s }(hTurtle graphics in Transcrypt do not require the use of any graphics libraries. Below are two turtle graphics examples and the source code of Transcrypt's hj(hhhNhNubh)}(h*turtle*h]hturtle}(hhhj1ubah}(h ]h"]h$]h&]h(]uh*hhj(ubhw module, which is quite compact. As can be seen from the code integration between Transcrypt and JavaScript is trivial.}(hw module, which is quite compact. As can be seen from the code integration between Transcrypt and JavaScript is trivial.hj(hhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhhhhubh container)}(hhh](h caption)}(h(Drawing a alternatingly floodfilled starh]h(Drawing a alternatingly floodfilled star}(hjShjQubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhjLubh literal_block)}(hX# Free after the example from the Python 3.5 manual from turtle import * up () goto (-250, -21) startPos = pos () down () color ('red', 'yellow') begin_fill () while True: forward (500) right (170) if distance (startPos) < 1: break end_fill () done () h]hX# Free after the example from the Python 3.5 manual from turtle import * up () goto (-250, -21) startPos = pos () down () color ('red', 'yellow') begin_fill () while True: forward (500) right (170) if distance (startPos) < 1: break end_fill () done () }(hhhjaubah}(h ]h"]h$]h&]h(]sourceS/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/turtle_demos/star.py xml:spacepreserveforcehighlight_args} linenostartKsuh*j_hh+hKhjLubeh}(h ]id1ah"]literal-block-wrapperah$]h&]h(] literal_blockuh*jJhhhhhhhNubh>)}(h{`Click here to view the resulting zoomable star `_.h](hI)}(hz`Click here to view the resulting zoomable star `_h]h.Click here to view the resulting zoomable star}(h.Click here to view the resulting zoomable starhjubah}(h ]h"]h$]h&]h(]name.Click here to view the resulting zoomable starh[Fhttp://www.transcrypt.org/live/transcrypt/demos/turtle_demos/star.htmluh*hHhjubh^)}(hI h]h}(h ].click-here-to-view-the-resulting-zoomable-starah"]h$].click here to view the resulting zoomable starah&]h(]refurijuh*h]hlKhjubh.}(h.hjhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hK hhhhubjK)}(hhh](jP)}(h#Drawing the contours of a snowflakeh]h#Drawing the contours of a snowflake}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hK"hjubj`)}(hXfrom turtle import * josh = Turtle () def draw (length): if length > 9: draw (length / 3) josh.left (60) draw (length / 3) josh.right (120) draw (length / 3) josh.left (60) draw (length / 3) else: josh.forward (length) length = 150 josh.up () josh.forward (length / 2) josh.left (90) josh.forward (length / 4) josh.right (90) josh.down () for i in range (3): josh.right (120) draw (length) josh.done () h]hXfrom turtle import * josh = Turtle () def draw (length): if length > 9: draw (length / 3) josh.left (60) draw (length / 3) josh.right (120) draw (length / 3) josh.left (60) draw (length / 3) else: josh.forward (length) length = 150 josh.up () josh.forward (length / 2) josh.left (90) josh.forward (length / 4) josh.right (90) josh.down () for i in range (3): josh.right (120) draw (length) josh.done () }(hhhjubah}(h ]h"]h$]h&]h(]sourceX/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/turtle_demos/snowflake.pyjqjrjsjt}jvKsuh*j_hh+hK"hjubeh}(h ]id2ah"]j{ah$]h&]h(] literal_blockuh*jJhhhhhhhNubh>)}(h`Click here to view the resulting zoomable snowflake `_.h](hI)}(h`Click here to view the resulting zoomable snowflake `_h]h3Click here to view the resulting zoomable snowflake}(h3Click here to view the resulting zoomable snowflakehjubah}(h ]h"]h$]h&]h(]name3Click here to view the resulting zoomable snowflakeh[Khttp://www.transcrypt.org/live/demos/transcrypt/turtle_demos/snowflake.htmluh*hHhjubh^)}(hN h]h}(h ]3click-here-to-view-the-resulting-zoomable-snowflakeah"]h$]3click here to view the resulting zoomable snowflakeah&]h(]refurijuh*h]hlKhjubh.}(hjhjhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hK&hhhhubjK)}(hhh](jP)}(hpTranscrypt's turtle graphics module sits directly on top of SVG, no libraries needed, so a very compact downloadh]hrTranscrypt’s turtle graphics module sits directly on top of SVG, no libraries needed, so a very compact download}(hj hjubah}(h ]h"]h$]h&]h(]uh*jOhh+hK(hjubj`)}(hX__pragma__ ('skip') document = Math = setInterval = clearInterval = 0 __pragma__ ('noskip') _debug = False #def abs (vec2D): # return Math.sqrt (vec2D [0] * vec2D [0] + vec2D [1] * vec2D [1]) _ns = 'http://www.w3.org/2000/svg' _svg = document.createElementNS (_ns, 'svg') _defaultElement = document.getElementById ('__turtlegraph__') if not _defaultElement: _defaultElement = document.body _defaultElement.appendChild (_svg) _width = None _height = None _offset = None def _rightSize (self): nonlocal _width nonlocal _height nonlocal _offset _width = _defaultElement.offsetWidth _height = _defaultElement.offsetHeight _offset = [_width // 2, _height // 2] _svg.setAttribute ('width', _width) _svg.setAttribute ('height', _height) window.onresize = _rightSize _rightSize () def bgcolor (color): nonlocal _defaultElement _bgcolor = color _defaultElement.style.backgroundColor = _bgcolor bgcolor ('white') def setDefaultElement (element): nonlocal _defaultElement _defaultElement.removeChild (_svg) _defaultElement = element element.appendChild (_svg) _rightSize () bgcolor ('white') _allTurtles = [] class Turtle: def __init__ (self): _allTurtles.append (self) self._paths = [] self.reset () def reset (self): self._heading = Math.PI / 2 self.pensize (1) self.color ('black', 'black') self.down () self._track = [] # Need to make track explicitly because: self.home () # Makes a position but needs a track to put in in self.clear () # Makes a track but needs a position to initialize it with def clear (self): for path in self._paths: _svg.removeChild (path) self._paths = [] self._track = [] self._moveto (self._position) def _flush (self): if _debug: print ('Flush:', self._track) if len (self._track) > 1: path = document.createElementNS (_ns, 'path') path.setAttribute ('d', ' '.join (self._track)) path.setAttribute ('stroke', self._pencolor if self._pencolor != None else 'none') path.setAttribute ('stroke-width', self._pensize) path.setAttribute ('fill', self._fillcolor if self._fill and self._fillcolor != None else 'none') path.setAttribute ('fill-rule', 'evenodd') _svg.appendChild (path) self._paths.append (path) self._track = [] self._moveto (self._position) # _track should start with a move command def done (self): self._flush () def pensize (self, width): self._flush () if width == None: return self._pensize else: self._pensize = width def color (self, pencolor, fillcolor = None): self._flush () self._pencolor = pencolor if fillcolor != None: self._fillcolor = fillcolor def goto (self, x, y = None): if y == None: self._position = x else: self._position = [x, y] self._track.append ('{} {} {}'.format ( 'L' if self._down else 'M', self._position [0] + _offset [0], self._position [1] + _offset [1]) ) def _moveto (self, x, y = None): wasdown = self.isdown () self.up () self.goto (x, y) if wasdown: self.down () def home (self): self._moveto (0, 0) def position (self): return self._position [:] def pos (self): return self.position () def distance (self, x, y = None): if y == None: other = x else: other = [x, y] dX = other [0] - self._position [0] dY = other [1] - self._position [1] return Math.sqrt (dX * dX + dY * dY) def up (self): self._down = False def down (self): self._down = True def isdown (self): return self._down def _predict (self, length): delta = [Math.sin (self._heading), Math.cos (self._heading)] return [self._position [0] + length * delta [0], self._position [1] + length * delta [1]] def forward (self, length): self._position = self._predict (length) self._track.append ('{} {} {}'.format ( 'L' if self._down else 'M', self._position [0] + _offset [0], self._position [1] + _offset [1]) ) def back (self, length): self.forward (-length) def circle (self, radius): self.left (90) opposite = self._predict (2 * (radius + 1) + 1) self.right (90) self._track.append ('{} {} {} {} {} {} {} {}'.format ( 'A', radius, radius, 0, 1, 0, opposite [0] + _offset [0], opposite [1] + _offset [1] )) self._track.append ('{} {} {} {} {} {} {} {}'.format ( 'A', radius, radius, 0, 1, 0, self._position [0] + _offset [0], self._position [1] + _offset [1] )) def left (self, angle): self._heading = (self._heading + Math.PI * angle / 180) % (2 * Math.PI) def right (self, angle): self.left (-angle) def begin_fill (self): self._flush () self._fill = True def end_fill (self): self._flush () self._fill = False def speed (speed = None): pass _defaultTurtle = Turtle () _timer = None def reset (): nonlocal _timer, _allTurtles if _timer: clearTimeout (_timer) bgcolor ('white') for turtle in _allTurtles: turtle.reset () turtle.done () def clear (): nonlocal _allTurtles for turtle in _allTurtles: turtle.clear () def ontimer (fun, t = 0): nonlocal _timer _timer = setTimeout (fun, t) def done (): _defaultTurtle.done () def pensize (width): _defaultTurtle.pensize (width) def color (pencolor, fillcolor = None): _defaultTurtle.color (pencolor, fillcolor) def home (): _defaultTurtle.home () def goto (x, y = None): _defaultTurtle.goto (x, y) def position (): return _defaultTurtle.position () def pos (): return _defaultTurtle.pos () def distance (x, y = None): return _defaultTurtle.distance (x, y) def up (): _defaultTurtle.up () def down (): _defaultTurtle.down () def forward (length): _defaultTurtle.forward (length) def back (length): _defaultTurtle.back (length) def circle (radius): _defaultTurtle.circle (radius) def left (angle): _defaultTurtle.left (angle) def right (angle): _defaultTurtle.right (angle) def begin_fill (): _defaultTurtle.begin_fill () def end_fill (): _defaultTurtle.end_fill () def speed (speed): _defaultTurtle.speed (speed) h]hX__pragma__ ('skip') document = Math = setInterval = clearInterval = 0 __pragma__ ('noskip') _debug = False #def abs (vec2D): # return Math.sqrt (vec2D [0] * vec2D [0] + vec2D [1] * vec2D [1]) _ns = 'http://www.w3.org/2000/svg' _svg = document.createElementNS (_ns, 'svg') _defaultElement = document.getElementById ('__turtlegraph__') if not _defaultElement: _defaultElement = document.body _defaultElement.appendChild (_svg) _width = None _height = None _offset = None def _rightSize (self): nonlocal _width nonlocal _height nonlocal _offset _width = _defaultElement.offsetWidth _height = _defaultElement.offsetHeight _offset = [_width // 2, _height // 2] _svg.setAttribute ('width', _width) _svg.setAttribute ('height', _height) window.onresize = _rightSize _rightSize () def bgcolor (color): nonlocal _defaultElement _bgcolor = color _defaultElement.style.backgroundColor = _bgcolor bgcolor ('white') def setDefaultElement (element): nonlocal _defaultElement _defaultElement.removeChild (_svg) _defaultElement = element element.appendChild (_svg) _rightSize () bgcolor ('white') _allTurtles = [] class Turtle: def __init__ (self): _allTurtles.append (self) self._paths = [] self.reset () def reset (self): self._heading = Math.PI / 2 self.pensize (1) self.color ('black', 'black') self.down () self._track = [] # Need to make track explicitly because: self.home () # Makes a position but needs a track to put in in self.clear () # Makes a track but needs a position to initialize it with def clear (self): for path in self._paths: _svg.removeChild (path) self._paths = [] self._track = [] self._moveto (self._position) def _flush (self): if _debug: print ('Flush:', self._track) if len (self._track) > 1: path = document.createElementNS (_ns, 'path') path.setAttribute ('d', ' '.join (self._track)) path.setAttribute ('stroke', self._pencolor if self._pencolor != None else 'none') path.setAttribute ('stroke-width', self._pensize) path.setAttribute ('fill', self._fillcolor if self._fill and self._fillcolor != None else 'none') path.setAttribute ('fill-rule', 'evenodd') _svg.appendChild (path) self._paths.append (path) self._track = [] self._moveto (self._position) # _track should start with a move command def done (self): self._flush () def pensize (self, width): self._flush () if width == None: return self._pensize else: self._pensize = width def color (self, pencolor, fillcolor = None): self._flush () self._pencolor = pencolor if fillcolor != None: self._fillcolor = fillcolor def goto (self, x, y = None): if y == None: self._position = x else: self._position = [x, y] self._track.append ('{} {} {}'.format ( 'L' if self._down else 'M', self._position [0] + _offset [0], self._position [1] + _offset [1]) ) def _moveto (self, x, y = None): wasdown = self.isdown () self.up () self.goto (x, y) if wasdown: self.down () def home (self): self._moveto (0, 0) def position (self): return self._position [:] def pos (self): return self.position () def distance (self, x, y = None): if y == None: other = x else: other = [x, y] dX = other [0] - self._position [0] dY = other [1] - self._position [1] return Math.sqrt (dX * dX + dY * dY) def up (self): self._down = False def down (self): self._down = True def isdown (self): return self._down def _predict (self, length): delta = [Math.sin (self._heading), Math.cos (self._heading)] return [self._position [0] + length * delta [0], self._position [1] + length * delta [1]] def forward (self, length): self._position = self._predict (length) self._track.append ('{} {} {}'.format ( 'L' if self._down else 'M', self._position [0] + _offset [0], self._position [1] + _offset [1]) ) def back (self, length): self.forward (-length) def circle (self, radius): self.left (90) opposite = self._predict (2 * (radius + 1) + 1) self.right (90) self._track.append ('{} {} {} {} {} {} {} {}'.format ( 'A', radius, radius, 0, 1, 0, opposite [0] + _offset [0], opposite [1] + _offset [1] )) self._track.append ('{} {} {} {} {} {} {} {}'.format ( 'A', radius, radius, 0, 1, 0, self._position [0] + _offset [0], self._position [1] + _offset [1] )) def left (self, angle): self._heading = (self._heading + Math.PI * angle / 180) % (2 * Math.PI) def right (self, angle): self.left (-angle) def begin_fill (self): self._flush () self._fill = True def end_fill (self): self._flush () self._fill = False def speed (speed = None): pass _defaultTurtle = Turtle () _timer = None def reset (): nonlocal _timer, _allTurtles if _timer: clearTimeout (_timer) bgcolor ('white') for turtle in _allTurtles: turtle.reset () turtle.done () def clear (): nonlocal _allTurtles for turtle in _allTurtles: turtle.clear () def ontimer (fun, t = 0): nonlocal _timer _timer = setTimeout (fun, t) def done (): _defaultTurtle.done () def pensize (width): _defaultTurtle.pensize (width) def color (pencolor, fillcolor = None): _defaultTurtle.color (pencolor, fillcolor) def home (): _defaultTurtle.home () def goto (x, y = None): _defaultTurtle.goto (x, y) def position (): return _defaultTurtle.position () def pos (): return _defaultTurtle.pos () def distance (x, y = None): return _defaultTurtle.distance (x, y) def up (): _defaultTurtle.up () def down (): _defaultTurtle.down () def forward (length): _defaultTurtle.forward (length) def back (length): _defaultTurtle.back (length) def circle (radius): _defaultTurtle.circle (radius) def left (angle): _defaultTurtle.left (angle) def right (angle): _defaultTurtle.right (angle) def begin_fill (): _defaultTurtle.begin_fill () def end_fill (): _defaultTurtle.end_fill () def speed (speed): _defaultTurtle.speed (speed) }(hhhjubah}(h ]h"]h$]h&]h(]sourceS/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/modules/turtle/__init__.pyjqjrjsjt}jvKsuh*j_hh+hK(hjubeh}(h ]id3ah"]j{ah$]h&]h(] literal_blockuh*jJhhhhhhhNubh>)}(hXRemark: In a later stage animation may be added. As a further step, for complicated fractals, transparent server side compilation of a relatively simple algorithm would allow on-line editing combined with fast client side rendering of high-resolution graphics.h]hXRemark: In a later stage animation may be added. As a further step, for complicated fractals, transparent server side compilation of a relatively simple algorithm would allow on-line editing combined with fast client side rendering of high-resolution graphics.}(hj1hj/hhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hK,hhhhubeh}(h ]svg-example-turtle-graphicsah"]h$]svg example: turtle graphicsah&]h(]uh*h hh hhhh+hK ubeh}(h ]$seamless-interoperation-with-the-domah"]h$]$seamless interoperation with the domah&]h(]uh*h hhhhhh+hKubh )}(hhh](h)}(hMixed examplesh]hMixed examples}(hjRhjPhhhNhNubah}(h ]h"]h$]h&]h(]uh*hhjMhhhh+hK0ubh )}(hhh](h)}(h Example: Pongh]h Example: Pong}(hjchjahhhNhNubah}(h ]h"]h$]h&]h(]uh*hhj^hhhh+hK3ubh>)}(hIn using the fabric.js JavaScript library this for example, the only thing differing from plain JavaScipt is that *new * is replaced by *__new__ ()*.h](hrIn using the fabric.js JavaScript library this for example, the only thing differing from plain JavaScipt is that }(hrIn using the fabric.js JavaScript library this for example, the only thing differing from plain JavaScipt is that hjohhhNhNubh)}(h*new *h]hnew }(hhhjxubah}(h ]h"]h$]h&]h(]uh*hhjoubh is replaced by }(h is replaced by hjohhhNhNubh)}(h*__new__ ()*h]h__new__ ()}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjoubh.}(hjhjohhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hK5hj^hhubh^)}(h.. _code_pong:h]h}(h ]h"]h$]h&]h(]refid code-ponguh*h]hK7hj^hhhh+ubh table)}(hhh]h tgroup)}(hhh](h colspec)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK.uh*jhjubj)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK9uh*jhjubh tbody)}(hhh]h row)}(hhh](h entry)}(hhh]jK)}(hhh](jP)}(hpong.pyh]hpong.py}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hK:hjubj`)}(hX9__pragma__ ('skip') document = window = Math = Date = 0 # Prevent complaints by optional static checker __pragma__ ('noskip') __pragma__ ('noalias', 'clear') from com.fabricjs import fabric orthoWidth = 1000 orthoHeight = 750 fieldHeight = 650 enter, esc, space = 13, 27, 32 window.onkeydown = lambda event: event.keyCode != space # Prevent scrolldown on spacebar press class Attribute: # Attribute in the gaming sense of the word, rather than of an object def __init__ (self, game): self.game = game # Attribute knows game it's part of self.game.attributes.append (self) # Game knows all its attributes self.install () # Put in place graphical representation of attribute self.reset () # Reset attribute to start position def reset (self): # Restore starting positions or score, then commit to fabric self.commit () # Nothing to restore for the Attribute base class def predict (self): pass def interact (self): pass def commit (self): pass class Sprite (Attribute): # Here, a sprite is an attribute that can move def __init__ (self, game, width, height): self.width = width self.height = height Attribute.__init__ (self, game) def install (self): # The sprite holds an image that fabric can display self.image = __new__ (fabric.Rect ({ 'width': self.game.scaleX (self.width), 'height': self.game.scaleY (self.height), 'originX': 'center', 'originY': 'center', 'fill': 'white' })) __pragma__ ('kwargs') def reset (self, vX = 0, vY = 0, x = 0, y = 0): self.vX = vX # Speed self.vY = vY self.x = x # Predicted position, can be commit, no bouncing initially self.y = y Attribute.reset (self) __pragma__ ('nokwargs') def predict (self): # Predict position, do not yet commit, bouncing may alter it self.x += self.vX * self.game.deltaT self.y += self.vY * self.game.deltaT def commit (self): # Update fabric image for asynch draw self.image.left = self.game.orthoX (self.x) self.image.top = self.game.orthoY (self.y) def draw (self): self.game.canvas.add (self.image) class Paddle (Sprite): margin = 30 # Distance of paddles from walls width = 10 height = 100 speed = 400 # / s def __init__ (self, game, index): self.index = index # Paddle knows its player index, 0 == left, 1 == right Sprite.__init__ (self, game, self.width, self.height) def reset (self): # Put paddle in rest position, dependent on player index Sprite.reset ( self, x = orthoWidth // 2 - self.margin if self.index else -orthoWidth // 2 + self.margin, y = 0 ) def predict (self): # Let paddle react on keys self.vY = 0 if self.index: # Right player if self.game.keyCode == ord ('K'): # Letter K pressed self.vY = self.speed elif self.game.keyCode == ord ('M'): self.vY = -self.speed else: # Left player if self.game.keyCode == ord ('A'): self.vY = self.speed elif self.game.keyCode == ord ('Z'): self.vY = -self.speed Sprite.predict (self) # Do not yet commit, paddle may bounce with walls def interact (self): # Paddles and ball assumed infinitely thin # Paddle touches wall self.y = Math.max (self.height // 2 - fieldHeight // 2, Math.min (self.y, fieldHeight // 2 - self.height // 2)) # Paddle hits ball if ( (self.y - self.height // 2) < self.game.ball.y < (self.y + self.height // 2) and ( (self.index == 0 and self.game.ball.x < self.x) # On or behind left paddle or (self.index == 1 and self.game.ball.x > self.x) # On or behind right paddle ) ): self.game.ball.x = self.x # Ball may have gone too far already self.game.ball.vX = -self.game.ball.vX # Bounce on paddle self.game.ball.speedUp (self) class Ball (Sprite): side = 8 speed = 300 # / s def __init__ (self, game): Sprite.__init__ (self, game, self.side, self.side) def reset (self): # Launch according to service direction with random angle offset from horizontal angle = ( self.game.serviceIndex * Math.PI # Service direction + (1 if Math.random () > 0.5 else -1) * Math.random () * Math.atan (fieldHeight / orthoWidth) ) Sprite.reset ( self, vX = self.speed * Math.cos (angle), vY = self.speed * Math.sin (angle) ) def predict (self): Sprite.predict (self) # Integrate velocity to position if self.x < -orthoWidth // 2: # If out on left side self.game.scored (1) # Right player scored elif self.x > orthoWidth // 2: self.game.scored (0) if self.y > fieldHeight // 2: # If it hits top wall self.y = fieldHeight // 2 # It may have gone too far already self.vY = -self.vY # Bounce elif self.y < -fieldHeight // 2: self.y = -fieldHeight // 2 self.vY = -self.vY def speedUp (self, bat): factor = 1 + 0.15 * (1 - Math.abs (self.y - bat.y) / (bat.height // 2)) ** 2 # Speed will increase more if paddle hit near centre if Math.abs (self.vX) < 3 * self.speed: self.vX *= factor self.vY *= factor class Scoreboard (Attribute): nameShift = 75 hintShift = 25 def install (self): # Graphical representation of scoreboard are four labels and a separator line self.playerLabels = [__new__ (fabric.Text ('Player {}'.format (name), { 'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}' .format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (fieldHeight // 2 + self.nameShift) })) for name, position in (('AZ keys:', -7/16), ('KM keys:', 1/16))] self.hintLabel = __new__ (fabric.Text ('[spacebar] starts game, [enter] resets score', { 'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 70), 'left': self.game.orthoX (-7/16 * orthoWidth), 'top': self.game.orthoY (fieldHeight // 2 + self.hintShift) })) self.image = __new__ (fabric.Line ([ self.game.orthoX (-orthoWidth // 2), self.game.orthoY (fieldHeight // 2), self.game.orthoX (orthoWidth // 2), self.game.orthoY (fieldHeight // 2) ], {'stroke': 'white'} )) def increment (self, playerIndex): self.scores [playerIndex] += 1 def reset (self): self.scores = [0, 0] Attribute.reset (self) # Only does a commit here def commit (self): # Committing labels is adapting their texts self.scoreLabels = [__new__ (fabric.Text ('{}'.format (score), { 'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (fieldHeight // 2 + self.nameShift) })) for score, position in zip (self.scores, (-2/16, 6/16))] def draw (self): for playerLabel, scoreLabel in zip (self.playerLabels, self.scoreLabels): self.game.canvas.add (playerLabel) self.game.canvas.add (scoreLabel) self.game.canvas.add (self.hintLabel) self.game.canvas.add (self.image) class Game: def __init__ (self): self.serviceIndex = 1 if Math.random () > 0.5 else 0 # Index of player that has initial service self.pause = True # Start game in paused state self.keyCode = None self.textFrame = document.getElementById ('text_frame') self.canvasFrame = document.getElementById ('canvas_frame') self.buttonsFrame = document.getElementById ('buttons_frame') self.canvas = __new__ (fabric.Canvas ('canvas', {'backgroundColor': 'black', 'originX': 'center', 'originY': 'center'})) self.canvas.onWindowDraw = self.draw # Install draw callback, will be called asynch self.canvas.lineWidth = 2 self.canvas.clear () self.attributes = [] # All attributes will insert themselves here self.paddles = [Paddle (self, index) for index in range (2)] # Pass game as parameter self self.ball = Ball (self) self.scoreboard = Scoreboard (self) window.setInterval (self.update, 10) # Install update callback, time in ms window.setInterval (self.draw, 20) # Install draw callback, time in ms window.addEventListener ('keydown', self.keydown) window.addEventListener ('keyup', self.keyup) self.buttons = [] for key in ('A', 'Z', 'K', 'M', 'space', 'enter'): button = document.getElementById (key) button.addEventListener ('mousedown', (lambda aKey: lambda: self.mouseOrTouch (aKey, True)) (key)) # Returns inner lambda button.addEventListener ('touchstart', (lambda aKey: lambda: self.mouseOrTouch (aKey, True)) (key)) button.addEventListener ('mouseup', (lambda aKey: lambda: self.mouseOrTouch (aKey, False)) (key)) button.addEventListener ('touchend', (lambda aKey: lambda: self.mouseOrTouch (aKey, False)) (key)) button.style.cursor = 'pointer' button.style.userSelect = 'none' self.buttons.append (button) self.time = + __new__ (Date) window.onresize = self.resize self.resize () def install (self): for attribute in self.attributes: attribute.install () def mouseOrTouch (self, key, down): if down: if key == 'space': self.keyCode = space elif key == 'enter': self.keyCode = enter else: self.keyCode = ord (key) else: self.keyCode = None def update (self): # Note that update and draw are not synchronized oldTime = self.time self.time = + __new__ (Date) self.deltaT = (self.time - oldTime) / 1000. if self.pause: # If in paused state if self.keyCode == space: # If spacebar hit self.pause = False # Start playing elif self.keyCode == enter: # Else if enter hit self.scoreboard.reset () # Reset score else: # Else, so if in active state for attribute in self.attributes: # Compute predicted values attribute.predict () for attribute in self.attributes: # Correct values for bouncing and scoring attribute.interact () for attribute in self.attributes: # Commit them to pyglet for display attribute.commit () def scored (self, playerIndex): # Player has scored self.scoreboard.increment (playerIndex) # Increment player's points self.serviceIndex = 1 - playerIndex # Grant service to the unlucky player for paddle in self.paddles: # Put paddles in rest position paddle.reset () self.ball.reset () # Put ball in rest position self.pause = True # Wait for next round def commit (self): for attribute in self.attributes: attribute.commit () def draw (self): self.canvas.clear () for attribute in self.attributes: attribute.draw () def resize (self): self.pageWidth = window.innerWidth self.pageHeight = window.innerHeight self.textTop = 0 if self.pageHeight > 1.2 * self.pageWidth: self.canvasWidth = self.pageWidth self.canvasTop = self.textTop + 300 else: self.canvasWidth = 0.6 * self.pageWidth self.canvasTop = self.textTop + 200 self.canvasLeft = 0.5 * (self.pageWidth - self.canvasWidth) self.canvasHeight = 0.6 * self.canvasWidth self.buttonsTop = self.canvasTop + self.canvasHeight + 50 self.buttonsWidth = 500 self.textFrame.style.top = self.textTop; self.textFrame.style.left = self.canvasLeft + 0.05 * self.canvasWidth self.textFrame.style.width = 0.9 * self.canvasWidth self.canvasFrame.style.top = self.canvasTop self.canvasFrame.style.left = self.canvasLeft self.canvas.setDimensions ({'width': self.canvasWidth, 'height': self.canvasHeight}) self.buttonsFrame.style.top = self.buttonsTop self.buttonsFrame.style.left = 0.5 * (self.pageWidth - self.buttonsWidth) self.buttonsFrame.style.width = self.canvasWidth self.install () self.commit () self.draw () def scaleX (self, x): return x * (self.canvas.width / orthoWidth) def scaleY (self, y): return y * (self.canvas.height / orthoHeight) def orthoX (self, x): return self.scaleX (x + orthoWidth // 2) def orthoY (self, y): return self.scaleY (orthoHeight - fieldHeight // 2 - y) def keydown (self, event): self.keyCode = event.keyCode def keyup (self, event): self.keyCode = None game = Game () # Create and run game h]hX9__pragma__ ('skip') document = window = Math = Date = 0 # Prevent complaints by optional static checker __pragma__ ('noskip') __pragma__ ('noalias', 'clear') from com.fabricjs import fabric orthoWidth = 1000 orthoHeight = 750 fieldHeight = 650 enter, esc, space = 13, 27, 32 window.onkeydown = lambda event: event.keyCode != space # Prevent scrolldown on spacebar press class Attribute: # Attribute in the gaming sense of the word, rather than of an object def __init__ (self, game): self.game = game # Attribute knows game it's part of self.game.attributes.append (self) # Game knows all its attributes self.install () # Put in place graphical representation of attribute self.reset () # Reset attribute to start position def reset (self): # Restore starting positions or score, then commit to fabric self.commit () # Nothing to restore for the Attribute base class def predict (self): pass def interact (self): pass def commit (self): pass class Sprite (Attribute): # Here, a sprite is an attribute that can move def __init__ (self, game, width, height): self.width = width self.height = height Attribute.__init__ (self, game) def install (self): # The sprite holds an image that fabric can display self.image = __new__ (fabric.Rect ({ 'width': self.game.scaleX (self.width), 'height': self.game.scaleY (self.height), 'originX': 'center', 'originY': 'center', 'fill': 'white' })) __pragma__ ('kwargs') def reset (self, vX = 0, vY = 0, x = 0, y = 0): self.vX = vX # Speed self.vY = vY self.x = x # Predicted position, can be commit, no bouncing initially self.y = y Attribute.reset (self) __pragma__ ('nokwargs') def predict (self): # Predict position, do not yet commit, bouncing may alter it self.x += self.vX * self.game.deltaT self.y += self.vY * self.game.deltaT def commit (self): # Update fabric image for asynch draw self.image.left = self.game.orthoX (self.x) self.image.top = self.game.orthoY (self.y) def draw (self): self.game.canvas.add (self.image) class Paddle (Sprite): margin = 30 # Distance of paddles from walls width = 10 height = 100 speed = 400 # / s def __init__ (self, game, index): self.index = index # Paddle knows its player index, 0 == left, 1 == right Sprite.__init__ (self, game, self.width, self.height) def reset (self): # Put paddle in rest position, dependent on player index Sprite.reset ( self, x = orthoWidth // 2 - self.margin if self.index else -orthoWidth // 2 + self.margin, y = 0 ) def predict (self): # Let paddle react on keys self.vY = 0 if self.index: # Right player if self.game.keyCode == ord ('K'): # Letter K pressed self.vY = self.speed elif self.game.keyCode == ord ('M'): self.vY = -self.speed else: # Left player if self.game.keyCode == ord ('A'): self.vY = self.speed elif self.game.keyCode == ord ('Z'): self.vY = -self.speed Sprite.predict (self) # Do not yet commit, paddle may bounce with walls def interact (self): # Paddles and ball assumed infinitely thin # Paddle touches wall self.y = Math.max (self.height // 2 - fieldHeight // 2, Math.min (self.y, fieldHeight // 2 - self.height // 2)) # Paddle hits ball if ( (self.y - self.height // 2) < self.game.ball.y < (self.y + self.height // 2) and ( (self.index == 0 and self.game.ball.x < self.x) # On or behind left paddle or (self.index == 1 and self.game.ball.x > self.x) # On or behind right paddle ) ): self.game.ball.x = self.x # Ball may have gone too far already self.game.ball.vX = -self.game.ball.vX # Bounce on paddle self.game.ball.speedUp (self) class Ball (Sprite): side = 8 speed = 300 # / s def __init__ (self, game): Sprite.__init__ (self, game, self.side, self.side) def reset (self): # Launch according to service direction with random angle offset from horizontal angle = ( self.game.serviceIndex * Math.PI # Service direction + (1 if Math.random () > 0.5 else -1) * Math.random () * Math.atan (fieldHeight / orthoWidth) ) Sprite.reset ( self, vX = self.speed * Math.cos (angle), vY = self.speed * Math.sin (angle) ) def predict (self): Sprite.predict (self) # Integrate velocity to position if self.x < -orthoWidth // 2: # If out on left side self.game.scored (1) # Right player scored elif self.x > orthoWidth // 2: self.game.scored (0) if self.y > fieldHeight // 2: # If it hits top wall self.y = fieldHeight // 2 # It may have gone too far already self.vY = -self.vY # Bounce elif self.y < -fieldHeight // 2: self.y = -fieldHeight // 2 self.vY = -self.vY def speedUp (self, bat): factor = 1 + 0.15 * (1 - Math.abs (self.y - bat.y) / (bat.height // 2)) ** 2 # Speed will increase more if paddle hit near centre if Math.abs (self.vX) < 3 * self.speed: self.vX *= factor self.vY *= factor class Scoreboard (Attribute): nameShift = 75 hintShift = 25 def install (self): # Graphical representation of scoreboard are four labels and a separator line self.playerLabels = [__new__ (fabric.Text ('Player {}'.format (name), { 'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}' .format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (fieldHeight // 2 + self.nameShift) })) for name, position in (('AZ keys:', -7/16), ('KM keys:', 1/16))] self.hintLabel = __new__ (fabric.Text ('[spacebar] starts game, [enter] resets score', { 'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 70), 'left': self.game.orthoX (-7/16 * orthoWidth), 'top': self.game.orthoY (fieldHeight // 2 + self.hintShift) })) self.image = __new__ (fabric.Line ([ self.game.orthoX (-orthoWidth // 2), self.game.orthoY (fieldHeight // 2), self.game.orthoX (orthoWidth // 2), self.game.orthoY (fieldHeight // 2) ], {'stroke': 'white'} )) def increment (self, playerIndex): self.scores [playerIndex] += 1 def reset (self): self.scores = [0, 0] Attribute.reset (self) # Only does a commit here def commit (self): # Committing labels is adapting their texts self.scoreLabels = [__new__ (fabric.Text ('{}'.format (score), { 'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (fieldHeight // 2 + self.nameShift) })) for score, position in zip (self.scores, (-2/16, 6/16))] def draw (self): for playerLabel, scoreLabel in zip (self.playerLabels, self.scoreLabels): self.game.canvas.add (playerLabel) self.game.canvas.add (scoreLabel) self.game.canvas.add (self.hintLabel) self.game.canvas.add (self.image) class Game: def __init__ (self): self.serviceIndex = 1 if Math.random () > 0.5 else 0 # Index of player that has initial service self.pause = True # Start game in paused state self.keyCode = None self.textFrame = document.getElementById ('text_frame') self.canvasFrame = document.getElementById ('canvas_frame') self.buttonsFrame = document.getElementById ('buttons_frame') self.canvas = __new__ (fabric.Canvas ('canvas', {'backgroundColor': 'black', 'originX': 'center', 'originY': 'center'})) self.canvas.onWindowDraw = self.draw # Install draw callback, will be called asynch self.canvas.lineWidth = 2 self.canvas.clear () self.attributes = [] # All attributes will insert themselves here self.paddles = [Paddle (self, index) for index in range (2)] # Pass game as parameter self self.ball = Ball (self) self.scoreboard = Scoreboard (self) window.setInterval (self.update, 10) # Install update callback, time in ms window.setInterval (self.draw, 20) # Install draw callback, time in ms window.addEventListener ('keydown', self.keydown) window.addEventListener ('keyup', self.keyup) self.buttons = [] for key in ('A', 'Z', 'K', 'M', 'space', 'enter'): button = document.getElementById (key) button.addEventListener ('mousedown', (lambda aKey: lambda: self.mouseOrTouch (aKey, True)) (key)) # Returns inner lambda button.addEventListener ('touchstart', (lambda aKey: lambda: self.mouseOrTouch (aKey, True)) (key)) button.addEventListener ('mouseup', (lambda aKey: lambda: self.mouseOrTouch (aKey, False)) (key)) button.addEventListener ('touchend', (lambda aKey: lambda: self.mouseOrTouch (aKey, False)) (key)) button.style.cursor = 'pointer' button.style.userSelect = 'none' self.buttons.append (button) self.time = + __new__ (Date) window.onresize = self.resize self.resize () def install (self): for attribute in self.attributes: attribute.install () def mouseOrTouch (self, key, down): if down: if key == 'space': self.keyCode = space elif key == 'enter': self.keyCode = enter else: self.keyCode = ord (key) else: self.keyCode = None def update (self): # Note that update and draw are not synchronized oldTime = self.time self.time = + __new__ (Date) self.deltaT = (self.time - oldTime) / 1000. if self.pause: # If in paused state if self.keyCode == space: # If spacebar hit self.pause = False # Start playing elif self.keyCode == enter: # Else if enter hit self.scoreboard.reset () # Reset score else: # Else, so if in active state for attribute in self.attributes: # Compute predicted values attribute.predict () for attribute in self.attributes: # Correct values for bouncing and scoring attribute.interact () for attribute in self.attributes: # Commit them to pyglet for display attribute.commit () def scored (self, playerIndex): # Player has scored self.scoreboard.increment (playerIndex) # Increment player's points self.serviceIndex = 1 - playerIndex # Grant service to the unlucky player for paddle in self.paddles: # Put paddles in rest position paddle.reset () self.ball.reset () # Put ball in rest position self.pause = True # Wait for next round def commit (self): for attribute in self.attributes: attribute.commit () def draw (self): self.canvas.clear () for attribute in self.attributes: attribute.draw () def resize (self): self.pageWidth = window.innerWidth self.pageHeight = window.innerHeight self.textTop = 0 if self.pageHeight > 1.2 * self.pageWidth: self.canvasWidth = self.pageWidth self.canvasTop = self.textTop + 300 else: self.canvasWidth = 0.6 * self.pageWidth self.canvasTop = self.textTop + 200 self.canvasLeft = 0.5 * (self.pageWidth - self.canvasWidth) self.canvasHeight = 0.6 * self.canvasWidth self.buttonsTop = self.canvasTop + self.canvasHeight + 50 self.buttonsWidth = 500 self.textFrame.style.top = self.textTop; self.textFrame.style.left = self.canvasLeft + 0.05 * self.canvasWidth self.textFrame.style.width = 0.9 * self.canvasWidth self.canvasFrame.style.top = self.canvasTop self.canvasFrame.style.left = self.canvasLeft self.canvas.setDimensions ({'width': self.canvasWidth, 'height': self.canvasHeight}) self.buttonsFrame.style.top = self.buttonsTop self.buttonsFrame.style.left = 0.5 * (self.pageWidth - self.buttonsWidth) self.buttonsFrame.style.width = self.canvasWidth self.install () self.commit () self.draw () def scaleX (self, x): return x * (self.canvas.width / orthoWidth) def scaleY (self, y): return y * (self.canvas.height / orthoHeight) def orthoX (self, x): return self.scaleX (x + orthoWidth // 2) def orthoY (self, y): return self.scaleY (orthoHeight - fieldHeight // 2 - y) def keydown (self, event): self.keyCode = event.keyCode def keyup (self, event): self.keyCode = None game = Game () # Create and run game }(hhhjubah}(h ]h"]h$]h&]h(]sourceK/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/pong/pong.pyjqjrjsjt}jvKsuh*j_hh+hK:hjubeh}(h ]id4ah"]j{ah$]h&]h(] literal_blockuh*jJhjubah}(h ]h"]h$]h&]h(]uh*jhjubj)}(hhh]jK)}(hhh](jP)}(hpong.jsh]hpong.js}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hK:hjubj`)}(hXD// Transcrypt'ed from Python, 2021-06-01 16:19:09 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {fabric} from './com.fabricjs.js'; var __name__ = '__main__'; export var orthoWidth = 1000; export var orthoHeight = 750; export var fieldHeight = 650; var __left0__ = tuple ([13, 27, 32]); export var enter = __left0__ [0]; export var esc = __left0__ [1]; export var space = __left0__ [2]; window.onkeydown = (function __lambda__ (event) { return event.keyCode != space; }); export var Attribute = __class__ ('Attribute', [object], { __module__: __name__, get __init__ () {return __get__ (this, function (self, game) { self.game = game; self.game.attributes.append (self); self.install (); self.reset (); });}, get reset () {return __get__ (this, function (self) { self.commit (); });}, get predict () {return __get__ (this, function (self) { // pass; });}, get interact () {return __get__ (this, function (self) { // pass; });}, get commit () {return __get__ (this, function (self) { // pass; });} }); export var Sprite = __class__ ('Sprite', [Attribute], { __module__: __name__, get __init__ () {return __get__ (this, function (self, game, width, height) { self.width = width; self.height = height; Attribute.__init__ (self, game); });}, get install () {return __get__ (this, function (self) { self.image = new fabric.Rect (dict ({'width': self.game.scaleX (self.width), 'height': self.game.scaleY (self.height), 'originX': 'center', 'originY': 'center', 'fill': 'white'})); });}, get reset () {return __get__ (this, function (self, vX, vY, x, y) { if (typeof vX == 'undefined' || (vX != null && vX.hasOwnProperty ("__kwargtrans__"))) {; var vX = 0; }; if (typeof vY == 'undefined' || (vY != null && vY.hasOwnProperty ("__kwargtrans__"))) {; var vY = 0; }; if (typeof x == 'undefined' || (x != null && x.hasOwnProperty ("__kwargtrans__"))) {; var x = 0; }; if (typeof y == 'undefined' || (y != null && y.hasOwnProperty ("__kwargtrans__"))) {; var y = 0; }; if (arguments.length) { var __ilastarg0__ = arguments.length - 1; if (arguments [__ilastarg0__] && arguments [__ilastarg0__].hasOwnProperty ("__kwargtrans__")) { var __allkwargs0__ = arguments [__ilastarg0__--]; for (var __attrib0__ in __allkwargs0__) { switch (__attrib0__) { case 'self': var self = __allkwargs0__ [__attrib0__]; break; case 'vX': var vX = __allkwargs0__ [__attrib0__]; break; case 'vY': var vY = __allkwargs0__ [__attrib0__]; break; case 'x': var x = __allkwargs0__ [__attrib0__]; break; case 'y': var y = __allkwargs0__ [__attrib0__]; break; } } } } else { } self.vX = vX; self.vY = vY; self.x = x; self.y = y; Attribute.reset (self); });}, get predict () {return __get__ (this, function (self) { self.x += self.vX * self.game.deltaT; self.y += self.vY * self.game.deltaT; });}, get commit () {return __get__ (this, function (self) { self.image.left = self.game.orthoX (self.x); self.image.top = self.game.orthoY (self.y); });}, get draw () {return __get__ (this, function (self) { self.game.canvas.add (self.image); });} }); export var Paddle = __class__ ('Paddle', [Sprite], { __module__: __name__, margin: 30, width: 10, height: 100, speed: 400, get __init__ () {return __get__ (this, function (self, game, index) { self.index = index; Sprite.__init__ (self, game, self.width, self.height); });}, get reset () {return __get__ (this, function (self) { Sprite.reset (self, __kwargtrans__ ({x: (self.index ? Math.floor (orthoWidth / 2) - self.margin : Math.floor (-(orthoWidth) / 2) + self.margin), y: 0})); });}, get predict () {return __get__ (this, function (self) { self.vY = 0; if (self.index) { if (self.game.keyCode == ord ('K')) { self.vY = self.speed; } else if (self.game.keyCode == ord ('M')) { self.vY = -(self.speed); } } else if (self.game.keyCode == ord ('A')) { self.vY = self.speed; } else if (self.game.keyCode == ord ('Z')) { self.vY = -(self.speed); } Sprite.predict (self); });}, get interact () {return __get__ (this, function (self) { self.y = Math.max (Math.floor (self.height / 2) - Math.floor (fieldHeight / 2), Math.min (self.y, Math.floor (fieldHeight / 2) - Math.floor (self.height / 2))); if ((self.y - Math.floor (self.height / 2) < self.game.ball.y && self.game.ball.y < self.y + Math.floor (self.height / 2)) && (self.index == 0 && self.game.ball.x < self.x || self.index == 1 && self.game.ball.x > self.x)) { self.game.ball.x = self.x; self.game.ball.vX = -(self.game.ball.vX); self.game.ball.speedUp (self); } });} }); export var Ball = __class__ ('Ball', [Sprite], { __module__: __name__, side: 8, speed: 300, get __init__ () {return __get__ (this, function (self, game) { Sprite.__init__ (self, game, self.side, self.side); });}, get reset () {return __get__ (this, function (self) { var angle = self.game.serviceIndex * Math.PI + ((Math.random () > 0.5 ? 1 : -(1)) * Math.random ()) * Math.atan (fieldHeight / orthoWidth); Sprite.reset (self, __kwargtrans__ ({vX: self.speed * Math.cos (angle), vY: self.speed * Math.sin (angle)})); });}, get predict () {return __get__ (this, function (self) { Sprite.predict (self); if (self.x < Math.floor (-(orthoWidth) / 2)) { self.game.scored (1); } else if (self.x > Math.floor (orthoWidth / 2)) { self.game.scored (0); } if (self.y > Math.floor (fieldHeight / 2)) { self.y = Math.floor (fieldHeight / 2); self.vY = -(self.vY); } else if (self.y < Math.floor (-(fieldHeight) / 2)) { self.y = Math.floor (-(fieldHeight) / 2); self.vY = -(self.vY); } });}, get speedUp () {return __get__ (this, function (self, bat) { var factor = 1 + 0.15 * Math.pow (1 - Math.abs (self.y - bat.y) / (Math.floor (bat.height / 2)), 2); if (Math.abs (self.vX) < 3 * self.speed) { self.vX *= factor; self.vY *= factor; } });} }); export var Scoreboard = __class__ ('Scoreboard', [Attribute], { __module__: __name__, nameShift: 75, hintShift: 25, get install () {return __get__ (this, function (self) { self.playerLabels = (function () { var __accu0__ = []; for (var [py_name, position] of tuple ([tuple (['AZ keys:', -(7) / 16]), tuple (['KM keys:', 1 / 16])])) { __accu0__.append (new fabric.Text ('Player {}'.format (py_name), dict ({'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (Math.floor (fieldHeight / 2) + self.nameShift)}))); } return __accu0__; }) (); self.hintLabel = new fabric.Text ('[spacebar] starts game, [enter] resets score', dict ({'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 70), 'left': self.game.orthoX ((-(7) / 16) * orthoWidth), 'top': self.game.orthoY (Math.floor (fieldHeight / 2) + self.hintShift)})); self.image = new fabric.Line ([self.game.orthoX (Math.floor (-(orthoWidth) / 2)), self.game.orthoY (Math.floor (fieldHeight / 2)), self.game.orthoX (Math.floor (orthoWidth / 2)), self.game.orthoY (Math.floor (fieldHeight / 2))], dict ({'stroke': 'white'})); });}, get increment () {return __get__ (this, function (self, playerIndex) { self.scores [playerIndex]++; });}, get reset () {return __get__ (this, function (self) { self.scores = [0, 0]; Attribute.reset (self); });}, get commit () {return __get__ (this, function (self) { self.scoreLabels = (function () { var __accu0__ = []; for (var [score, position] of zip (self.scores, tuple ([-(2) / 16, 6 / 16]))) { __accu0__.append (new fabric.Text ('{}'.format (score), dict ({'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (Math.floor (fieldHeight / 2) + self.nameShift)}))); } return __accu0__; }) (); });}, get draw () {return __get__ (this, function (self) { for (var [playerLabel, scoreLabel] of zip (self.playerLabels, self.scoreLabels)) { self.game.canvas.add (playerLabel); self.game.canvas.add (scoreLabel); self.game.canvas.add (self.hintLabel); } self.game.canvas.add (self.image); });} }); export var Game = __class__ ('Game', [object], { __module__: __name__, get __init__ () {return __get__ (this, function (self) { self.serviceIndex = (Math.random () > 0.5 ? 1 : 0); self.pause = true; self.keyCode = null; self.textFrame = document.getElementById ('text_frame'); self.canvasFrame = document.getElementById ('canvas_frame'); self.buttonsFrame = document.getElementById ('buttons_frame'); self.canvas = new fabric.Canvas ('canvas', dict ({'backgroundColor': 'black', 'originX': 'center', 'originY': 'center'})); self.canvas.onWindowDraw = self.draw; self.canvas.lineWidth = 2; self.canvas.clear (); self.attributes = []; self.paddles = (function () { var __accu0__ = []; for (var index = 0; index < 2; index++) { __accu0__.append (Paddle (self, index)); } return __accu0__; }) (); self.ball = Ball (self); self.scoreboard = Scoreboard (self); window.setInterval (self.py_update, 10); window.setInterval (self.draw, 20); window.addEventListener ('keydown', self.keydown); window.addEventListener ('keyup', self.keyup); self.buttons = []; for (var key of tuple (['A', 'Z', 'K', 'M', 'space', 'enter'])) { var button = document.getElementById (key); button.addEventListener ('mousedown', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, true); }); }) (key)); button.addEventListener ('touchstart', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, true); }); }) (key)); button.addEventListener ('mouseup', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, false); }); }) (key)); button.addEventListener ('touchend', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, false); }); }) (key)); button.style.cursor = 'pointer'; button.style.userSelect = 'none'; self.buttons.append (button); } self.time = +(new Date); window.onresize = self.resize; self.resize (); });}, get install () {return __get__ (this, function (self) { for (var attribute of self.attributes) { attribute.install (); } });}, get mouseOrTouch () {return __get__ (this, function (self, key, down) { if (down) { if (key == 'space') { self.keyCode = space; } else if (key == 'enter') { self.keyCode = enter; } else { self.keyCode = ord (key); } } else { self.keyCode = null; } });}, get py_update () {return __get__ (this, function (self) { var oldTime = self.time; self.time = +(new Date); self.deltaT = (self.time - oldTime) / 1000.0; if (self.pause) { if (self.keyCode == space) { self.pause = false; } else if (self.keyCode == enter) { self.scoreboard.reset (); } } else { for (var attribute of self.attributes) { attribute.predict (); } for (var attribute of self.attributes) { attribute.interact (); } for (var attribute of self.attributes) { attribute.commit (); } } });}, get scored () {return __get__ (this, function (self, playerIndex) { self.scoreboard.increment (playerIndex); self.serviceIndex = 1 - playerIndex; for (var paddle of self.paddles) { paddle.reset (); } self.ball.reset (); self.pause = true; });}, get commit () {return __get__ (this, function (self) { for (var attribute of self.attributes) { attribute.commit (); } });}, get draw () {return __get__ (this, function (self) { self.canvas.clear (); for (var attribute of self.attributes) { attribute.draw (); } });}, get resize () {return __get__ (this, function (self) { self.pageWidth = window.innerWidth; self.pageHeight = window.innerHeight; self.textTop = 0; if (self.pageHeight > 1.2 * self.pageWidth) { self.canvasWidth = self.pageWidth; self.canvasTop = self.textTop + 300; } else { self.canvasWidth = 0.6 * self.pageWidth; self.canvasTop = self.textTop + 200; } self.canvasLeft = 0.5 * (self.pageWidth - self.canvasWidth); self.canvasHeight = 0.6 * self.canvasWidth; self.buttonsTop = (self.canvasTop + self.canvasHeight) + 50; self.buttonsWidth = 500; self.textFrame.style.top = self.textTop; self.textFrame.style.left = self.canvasLeft + 0.05 * self.canvasWidth; self.textFrame.style.width = 0.9 * self.canvasWidth; self.canvasFrame.style.top = self.canvasTop; self.canvasFrame.style.left = self.canvasLeft; self.canvas.setDimensions (dict ({'width': self.canvasWidth, 'height': self.canvasHeight})); self.buttonsFrame.style.top = self.buttonsTop; self.buttonsFrame.style.left = 0.5 * (self.pageWidth - self.buttonsWidth); self.buttonsFrame.style.width = self.canvasWidth; self.install (); self.commit (); self.draw (); });}, get scaleX () {return __get__ (this, function (self, x) { return x * (self.canvas.width / orthoWidth); });}, get scaleY () {return __get__ (this, function (self, y) { return y * (self.canvas.height / orthoHeight); });}, get orthoX () {return __get__ (this, function (self, x) { return self.scaleX (x + Math.floor (orthoWidth / 2)); });}, get orthoY () {return __get__ (this, function (self, y) { return self.scaleY ((orthoHeight - Math.floor (fieldHeight / 2)) - y); });}, get keydown () {return __get__ (this, function (self, event) { self.keyCode = event.keyCode; });}, get keyup () {return __get__ (this, function (self, event) { self.keyCode = null; });} }); export var game = Game (); //# sourceMappingURL=pong.map h]hXD// Transcrypt'ed from Python, 2021-06-01 16:19:09 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {fabric} from './com.fabricjs.js'; var __name__ = '__main__'; export var orthoWidth = 1000; export var orthoHeight = 750; export var fieldHeight = 650; var __left0__ = tuple ([13, 27, 32]); export var enter = __left0__ [0]; export var esc = __left0__ [1]; export var space = __left0__ [2]; window.onkeydown = (function __lambda__ (event) { return event.keyCode != space; }); export var Attribute = __class__ ('Attribute', [object], { __module__: __name__, get __init__ () {return __get__ (this, function (self, game) { self.game = game; self.game.attributes.append (self); self.install (); self.reset (); });}, get reset () {return __get__ (this, function (self) { self.commit (); });}, get predict () {return __get__ (this, function (self) { // pass; });}, get interact () {return __get__ (this, function (self) { // pass; });}, get commit () {return __get__ (this, function (self) { // pass; });} }); export var Sprite = __class__ ('Sprite', [Attribute], { __module__: __name__, get __init__ () {return __get__ (this, function (self, game, width, height) { self.width = width; self.height = height; Attribute.__init__ (self, game); });}, get install () {return __get__ (this, function (self) { self.image = new fabric.Rect (dict ({'width': self.game.scaleX (self.width), 'height': self.game.scaleY (self.height), 'originX': 'center', 'originY': 'center', 'fill': 'white'})); });}, get reset () {return __get__ (this, function (self, vX, vY, x, y) { if (typeof vX == 'undefined' || (vX != null && vX.hasOwnProperty ("__kwargtrans__"))) {; var vX = 0; }; if (typeof vY == 'undefined' || (vY != null && vY.hasOwnProperty ("__kwargtrans__"))) {; var vY = 0; }; if (typeof x == 'undefined' || (x != null && x.hasOwnProperty ("__kwargtrans__"))) {; var x = 0; }; if (typeof y == 'undefined' || (y != null && y.hasOwnProperty ("__kwargtrans__"))) {; var y = 0; }; if (arguments.length) { var __ilastarg0__ = arguments.length - 1; if (arguments [__ilastarg0__] && arguments [__ilastarg0__].hasOwnProperty ("__kwargtrans__")) { var __allkwargs0__ = arguments [__ilastarg0__--]; for (var __attrib0__ in __allkwargs0__) { switch (__attrib0__) { case 'self': var self = __allkwargs0__ [__attrib0__]; break; case 'vX': var vX = __allkwargs0__ [__attrib0__]; break; case 'vY': var vY = __allkwargs0__ [__attrib0__]; break; case 'x': var x = __allkwargs0__ [__attrib0__]; break; case 'y': var y = __allkwargs0__ [__attrib0__]; break; } } } } else { } self.vX = vX; self.vY = vY; self.x = x; self.y = y; Attribute.reset (self); });}, get predict () {return __get__ (this, function (self) { self.x += self.vX * self.game.deltaT; self.y += self.vY * self.game.deltaT; });}, get commit () {return __get__ (this, function (self) { self.image.left = self.game.orthoX (self.x); self.image.top = self.game.orthoY (self.y); });}, get draw () {return __get__ (this, function (self) { self.game.canvas.add (self.image); });} }); export var Paddle = __class__ ('Paddle', [Sprite], { __module__: __name__, margin: 30, width: 10, height: 100, speed: 400, get __init__ () {return __get__ (this, function (self, game, index) { self.index = index; Sprite.__init__ (self, game, self.width, self.height); });}, get reset () {return __get__ (this, function (self) { Sprite.reset (self, __kwargtrans__ ({x: (self.index ? Math.floor (orthoWidth / 2) - self.margin : Math.floor (-(orthoWidth) / 2) + self.margin), y: 0})); });}, get predict () {return __get__ (this, function (self) { self.vY = 0; if (self.index) { if (self.game.keyCode == ord ('K')) { self.vY = self.speed; } else if (self.game.keyCode == ord ('M')) { self.vY = -(self.speed); } } else if (self.game.keyCode == ord ('A')) { self.vY = self.speed; } else if (self.game.keyCode == ord ('Z')) { self.vY = -(self.speed); } Sprite.predict (self); });}, get interact () {return __get__ (this, function (self) { self.y = Math.max (Math.floor (self.height / 2) - Math.floor (fieldHeight / 2), Math.min (self.y, Math.floor (fieldHeight / 2) - Math.floor (self.height / 2))); if ((self.y - Math.floor (self.height / 2) < self.game.ball.y && self.game.ball.y < self.y + Math.floor (self.height / 2)) && (self.index == 0 && self.game.ball.x < self.x || self.index == 1 && self.game.ball.x > self.x)) { self.game.ball.x = self.x; self.game.ball.vX = -(self.game.ball.vX); self.game.ball.speedUp (self); } });} }); export var Ball = __class__ ('Ball', [Sprite], { __module__: __name__, side: 8, speed: 300, get __init__ () {return __get__ (this, function (self, game) { Sprite.__init__ (self, game, self.side, self.side); });}, get reset () {return __get__ (this, function (self) { var angle = self.game.serviceIndex * Math.PI + ((Math.random () > 0.5 ? 1 : -(1)) * Math.random ()) * Math.atan (fieldHeight / orthoWidth); Sprite.reset (self, __kwargtrans__ ({vX: self.speed * Math.cos (angle), vY: self.speed * Math.sin (angle)})); });}, get predict () {return __get__ (this, function (self) { Sprite.predict (self); if (self.x < Math.floor (-(orthoWidth) / 2)) { self.game.scored (1); } else if (self.x > Math.floor (orthoWidth / 2)) { self.game.scored (0); } if (self.y > Math.floor (fieldHeight / 2)) { self.y = Math.floor (fieldHeight / 2); self.vY = -(self.vY); } else if (self.y < Math.floor (-(fieldHeight) / 2)) { self.y = Math.floor (-(fieldHeight) / 2); self.vY = -(self.vY); } });}, get speedUp () {return __get__ (this, function (self, bat) { var factor = 1 + 0.15 * Math.pow (1 - Math.abs (self.y - bat.y) / (Math.floor (bat.height / 2)), 2); if (Math.abs (self.vX) < 3 * self.speed) { self.vX *= factor; self.vY *= factor; } });} }); export var Scoreboard = __class__ ('Scoreboard', [Attribute], { __module__: __name__, nameShift: 75, hintShift: 25, get install () {return __get__ (this, function (self) { self.playerLabels = (function () { var __accu0__ = []; for (var [py_name, position] of tuple ([tuple (['AZ keys:', -(7) / 16]), tuple (['KM keys:', 1 / 16])])) { __accu0__.append (new fabric.Text ('Player {}'.format (py_name), dict ({'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (Math.floor (fieldHeight / 2) + self.nameShift)}))); } return __accu0__; }) (); self.hintLabel = new fabric.Text ('[spacebar] starts game, [enter] resets score', dict ({'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 70), 'left': self.game.orthoX ((-(7) / 16) * orthoWidth), 'top': self.game.orthoY (Math.floor (fieldHeight / 2) + self.hintShift)})); self.image = new fabric.Line ([self.game.orthoX (Math.floor (-(orthoWidth) / 2)), self.game.orthoY (Math.floor (fieldHeight / 2)), self.game.orthoX (Math.floor (orthoWidth / 2)), self.game.orthoY (Math.floor (fieldHeight / 2))], dict ({'stroke': 'white'})); });}, get increment () {return __get__ (this, function (self, playerIndex) { self.scores [playerIndex]++; });}, get reset () {return __get__ (this, function (self) { self.scores = [0, 0]; Attribute.reset (self); });}, get commit () {return __get__ (this, function (self) { self.scoreLabels = (function () { var __accu0__ = []; for (var [score, position] of zip (self.scores, tuple ([-(2) / 16, 6 / 16]))) { __accu0__.append (new fabric.Text ('{}'.format (score), dict ({'fill': 'white', 'fontFamily': 'arial', 'fontSize': '{}'.format (self.game.canvas.width / 30), 'left': self.game.orthoX (position * orthoWidth), 'top': self.game.orthoY (Math.floor (fieldHeight / 2) + self.nameShift)}))); } return __accu0__; }) (); });}, get draw () {return __get__ (this, function (self) { for (var [playerLabel, scoreLabel] of zip (self.playerLabels, self.scoreLabels)) { self.game.canvas.add (playerLabel); self.game.canvas.add (scoreLabel); self.game.canvas.add (self.hintLabel); } self.game.canvas.add (self.image); });} }); export var Game = __class__ ('Game', [object], { __module__: __name__, get __init__ () {return __get__ (this, function (self) { self.serviceIndex = (Math.random () > 0.5 ? 1 : 0); self.pause = true; self.keyCode = null; self.textFrame = document.getElementById ('text_frame'); self.canvasFrame = document.getElementById ('canvas_frame'); self.buttonsFrame = document.getElementById ('buttons_frame'); self.canvas = new fabric.Canvas ('canvas', dict ({'backgroundColor': 'black', 'originX': 'center', 'originY': 'center'})); self.canvas.onWindowDraw = self.draw; self.canvas.lineWidth = 2; self.canvas.clear (); self.attributes = []; self.paddles = (function () { var __accu0__ = []; for (var index = 0; index < 2; index++) { __accu0__.append (Paddle (self, index)); } return __accu0__; }) (); self.ball = Ball (self); self.scoreboard = Scoreboard (self); window.setInterval (self.py_update, 10); window.setInterval (self.draw, 20); window.addEventListener ('keydown', self.keydown); window.addEventListener ('keyup', self.keyup); self.buttons = []; for (var key of tuple (['A', 'Z', 'K', 'M', 'space', 'enter'])) { var button = document.getElementById (key); button.addEventListener ('mousedown', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, true); }); }) (key)); button.addEventListener ('touchstart', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, true); }); }) (key)); button.addEventListener ('mouseup', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, false); }); }) (key)); button.addEventListener ('touchend', (function __lambda__ (aKey) { return (function __lambda__ () { return self.mouseOrTouch (aKey, false); }); }) (key)); button.style.cursor = 'pointer'; button.style.userSelect = 'none'; self.buttons.append (button); } self.time = +(new Date); window.onresize = self.resize; self.resize (); });}, get install () {return __get__ (this, function (self) { for (var attribute of self.attributes) { attribute.install (); } });}, get mouseOrTouch () {return __get__ (this, function (self, key, down) { if (down) { if (key == 'space') { self.keyCode = space; } else if (key == 'enter') { self.keyCode = enter; } else { self.keyCode = ord (key); } } else { self.keyCode = null; } });}, get py_update () {return __get__ (this, function (self) { var oldTime = self.time; self.time = +(new Date); self.deltaT = (self.time - oldTime) / 1000.0; if (self.pause) { if (self.keyCode == space) { self.pause = false; } else if (self.keyCode == enter) { self.scoreboard.reset (); } } else { for (var attribute of self.attributes) { attribute.predict (); } for (var attribute of self.attributes) { attribute.interact (); } for (var attribute of self.attributes) { attribute.commit (); } } });}, get scored () {return __get__ (this, function (self, playerIndex) { self.scoreboard.increment (playerIndex); self.serviceIndex = 1 - playerIndex; for (var paddle of self.paddles) { paddle.reset (); } self.ball.reset (); self.pause = true; });}, get commit () {return __get__ (this, function (self) { for (var attribute of self.attributes) { attribute.commit (); } });}, get draw () {return __get__ (this, function (self) { self.canvas.clear (); for (var attribute of self.attributes) { attribute.draw (); } });}, get resize () {return __get__ (this, function (self) { self.pageWidth = window.innerWidth; self.pageHeight = window.innerHeight; self.textTop = 0; if (self.pageHeight > 1.2 * self.pageWidth) { self.canvasWidth = self.pageWidth; self.canvasTop = self.textTop + 300; } else { self.canvasWidth = 0.6 * self.pageWidth; self.canvasTop = self.textTop + 200; } self.canvasLeft = 0.5 * (self.pageWidth - self.canvasWidth); self.canvasHeight = 0.6 * self.canvasWidth; self.buttonsTop = (self.canvasTop + self.canvasHeight) + 50; self.buttonsWidth = 500; self.textFrame.style.top = self.textTop; self.textFrame.style.left = self.canvasLeft + 0.05 * self.canvasWidth; self.textFrame.style.width = 0.9 * self.canvasWidth; self.canvasFrame.style.top = self.canvasTop; self.canvasFrame.style.left = self.canvasLeft; self.canvas.setDimensions (dict ({'width': self.canvasWidth, 'height': self.canvasHeight})); self.buttonsFrame.style.top = self.buttonsTop; self.buttonsFrame.style.left = 0.5 * (self.pageWidth - self.buttonsWidth); self.buttonsFrame.style.width = self.canvasWidth; self.install (); self.commit (); self.draw (); });}, get scaleX () {return __get__ (this, function (self, x) { return x * (self.canvas.width / orthoWidth); });}, get scaleY () {return __get__ (this, function (self, y) { return y * (self.canvas.height / orthoHeight); });}, get orthoX () {return __get__ (this, function (self, x) { return self.scaleX (x + Math.floor (orthoWidth / 2)); });}, get orthoY () {return __get__ (this, function (self, y) { return self.scaleY ((orthoHeight - Math.floor (fieldHeight / 2)) - y); });}, get keydown () {return __get__ (this, function (self, event) { self.keyCode = event.keyCode; });}, get keyup () {return __get__ (this, function (self, event) { self.keyCode = null; });} }); export var game = Game (); //# sourceMappingURL=pong.map}(hhhj"ubah}(h ]h"]h$]h&]h(]sourceV/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/pong/__target__/pong.jsjqjrjsjt}jvKsuh*j_hh+hK:hjubeh}(h ]id5ah"]j{ah$]h&]h(] literal_blockuh*jJhjubah}(h ]h"]h$]h&]h(]uh*jhjubeh}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubeh}(h ]h"]h$]h&]h(]colsKuh*jhjubah}(h ]jah"]h$] code_pongah&]h(]uh*jhj^hhhNhNexpect_referenced_by_name}jXjsexpect_referenced_by_id}jjsubh )}(hhh](h)}(h3Three ways of integration with JavaScript librariesh]h3Three ways of integration with JavaScript libraries}(hjdhjbhhhNhNubah}(h ]h"]h$]h&]h(]uh*hhj_hhhh+hKAubh>)}(h]There are three ways to integrate Transcrypt applications with existing JavaScript libraries.h]h]There are three ways to integrate Transcrypt applications with existing JavaScript libraries.}(hjrhjphhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKChj_hhubh enumerated_list)}(hhh](h list_item)}(hThe simplest way is to use the library as is, without any encapsulation. In this way all symbols of that library will be in the global namespace. While many JavaScript programmers don't seem to mind that, many Python programmers do. h]h>)}(hThe simplest way is to use the library as is, without any encapsulation. In this way all symbols of that library will be in the global namespace. While many JavaScript programmers don't seem to mind that, many Python programmers do.h]hThe simplest way is to use the library as is, without any encapsulation. In this way all symbols of that library will be in the global namespace. While many JavaScript programmers don’t seem to mind that, many Python programmers do.}(hjhjubah}(h ]h"]h$]h&]h(]uh*h=hh+hKEhjubah}(h ]h"]h$]h&]h(]uh*jhjhhhh+hNubj)}(hXAnother way is to encapsulate the JavaScript library as a whole in a Transcrypt module. In the distibution this is done for the *fabric* module, that encapsulates *fabric.js* and is imported in the Pong example. In this way the global namespace stays clean. h]h>)}(hXAnother way is to encapsulate the JavaScript library as a whole in a Transcrypt module. In the distibution this is done for the *fabric* module, that encapsulates *fabric.js* and is imported in the Pong example. In this way the global namespace stays clean.h](hAnother way is to encapsulate the JavaScript library as a whole in a Transcrypt module. In the distibution this is done for the }(hAnother way is to encapsulate the JavaScript library as a whole in a Transcrypt module. In the distibution this is done for the hjubh)}(h*fabric*h]hfabric}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubh module, that encapsulates }(h module, that encapsulates hjubh)}(h *fabric.js*h]h fabric.js}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubhS and is imported in the Pong example. In this way the global namespace stays clean.}(hS and is imported in the Pong example. In this way the global namespace stays clean.hjubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKGhjubah}(h ]h"]h$]h&]h(]uh*jhjhhhh+hNubj)}(hX8The third way is to write a complete Pythonic API for the JavaScript library. This is overkill in most cases and makes it harder to keep up with new versions of the library. Note that Transcrypt was desiged to make seamless cooperation between Transcrypt and JavaScript libraries possible without any glue code. h]h>)}(hX7The third way is to write a complete Pythonic API for the JavaScript library. This is overkill in most cases and makes it harder to keep up with new versions of the library. Note that Transcrypt was desiged to make seamless cooperation between Transcrypt and JavaScript libraries possible without any glue code.h]hX7The third way is to write a complete Pythonic API for the JavaScript library. This is overkill in most cases and makes it harder to keep up with new versions of the library. Note that Transcrypt was desiged to make seamless cooperation between Transcrypt and JavaScript libraries possible without any glue code.}(hjhjubah}(h ]h"]h$]h&]h(]uh*h=hh+hKIhjubah}(h ]h"]h$]h&]h(]uh*jhjhhhh+hNubeh}(h ]h"]h$]h&]h(]enumtypearabicprefixhsuffixjuh*j~hj_hhhh+hKEubh>)}(hIn most cases this approach 2 strikes a good balance between effort and yield. As can be seen below, the effort involved is minimal.h]hIn most cases this approach 2 strikes a good balance between effort and yield. As can be seen below, the effort involved is minimal.}(hjhjhhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKKhj_hhubh^)}(h.. _code_encaps_fabric:h]h}(h ]h"]h$]h&]h(]jcode-encaps-fabricuh*h]hKMhj_hhhh+ubjK)}(hhh](jP)}(h%The encapsulation layer for fabric.jsh]h%The encapsulation layer for fabric.js}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKOhjubj`)}(hX__pragma__ ('noanno') fabric = __pragma__ ('js', ''' (function () {{ var exports = {{}}; {} // Puts fabric in exports and in global window delete window.fabric; return exports; }}) () .fabric; ''', __include__ ('com/fabricjs/fabric_downloaded.js') ) h]hX__pragma__ ('noanno') fabric = __pragma__ ('js', ''' (function () {{ var exports = {{}}; {} // Puts fabric in exports and in global window delete window.fabric; return exports; }}) () .fabric; ''', __include__ ('com/fabricjs/fabric_downloaded.js') ) }(hhhj(ubah}(h ]h"]h$]h&]h(]sourceY/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/modules/com/fabricjs/__init__.pyjqjrjsjt}jvKsuh*j_hh+hKOhjubeh}(h ](id6jeh"]j{ah$]code_encaps_fabricah&]h(] literal_blockuh*jJhj_hhhhhNj[}j>j sj]}jj subh>)}(hXNote that __pragma__ ('js', , includes = [, , ..]) is used to achieve the encapsulation. It replaces the {} by the respective contents of the files. The *fabric* module is part of the download. Note that not all facilities were included in customizing fabric.js. You can drop-in replace the *fabric.js* by another customized version without changing anything. Preferably download a development version, since that enables easy debugging. Transcryp will minify it for you on the fly.h](hNote that __pragma__ (‘js’, , includes = [, , ..]) is used to achieve the encapsulation. It replaces the {} by the respective contents of the files. The }(hNote that __pragma__ ('js', , includes = [, , ..]) is used to achieve the encapsulation. It replaces the {} by the respective contents of the files. The hjDhhhNhNubh)}(h*fabric*h]hfabric}(hhhjMubah}(h ]h"]h$]h&]h(]uh*hhjDubh module is part of the download. Note that not all facilities were included in customizing fabric.js. You can drop-in replace the }(h module is part of the download. Note that not all facilities were included in customizing fabric.js. You can drop-in replace the hjDhhhNhNubh)}(h *fabric.js*h]h fabric.js}(hhhj`ubah}(h ]h"]h$]h&]h(]uh*hhjDubh by another customized version without changing anything. Preferably download a development version, since that enables easy debugging. Transcryp will minify it for you on the fly.}(h by another customized version without changing anything. Preferably download a development version, since that enables easy debugging. Transcryp will minify it for you on the fly.hjDhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKShj_hhubeh}(h ]3three-ways-of-integration-with-javascript-librariesah"]h$]3three ways of integration with javascript librariesah&]h(]uh*h hj^hhhh+hKAubh )}(hhh](h)}(h Minificationh]h Minification}(hjhjhhhNhNubah}(h ]h"]h$]h&]h(]uh*hhjhhhh+hKVubh>)}(hMinification is currently performed by the Google closure compiler, that's also part of the distribution. Currently closures ADVANCED_OPTIMIZATIONS switch breaks the working *strict* code, however, so the SIMPLE_OPTIMIZATIONS switch is used by default.h](hMinification is currently performed by the Google closure compiler, that’s also part of the distribution. Currently closures ADVANCED_OPTIMIZATIONS switch breaks the working }(hMinification is currently performed by the Google closure compiler, that's also part of the distribution. Currently closures ADVANCED_OPTIMIZATIONS switch breaks the working hjhhhNhNubh)}(h*strict*h]hstrict}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubhF code, however, so the SIMPLE_OPTIMIZATIONS switch is used by default.}(hF code, however, so the SIMPLE_OPTIMIZATIONS switch is used by default.hjhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKXhjhhubh>)}(hXAs can be seen from the listings of the Pong example, even the non-minified *pong.js* module is only slightly larger than *pong.py*. This is despite the expensive keyword arguments mechanism that is activated for the *reset* function, using *__pragma__ ('kargs')* and *__pragma__ ('nokwargs')*. The minified but not treeshaked Transcrypt runtime is slightly above 40 kB. The *fabric.js* library on the other hand occupies 180 kB. From this example it becomes clear that Transcrypt is extremely lightweight.h](hLAs can be seen from the listings of the Pong example, even the non-minified }(hLAs can be seen from the listings of the Pong example, even the non-minified hjhhhNhNubh)}(h *pong.js*h]hpong.js}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubh% module is only slightly larger than }(h% module is only slightly larger than hjhhhNhNubh)}(h *pong.py*h]hpong.py}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubhV. This is despite the expensive keyword arguments mechanism that is activated for the }(hV. This is despite the expensive keyword arguments mechanism that is activated for the hjhhhNhNubh)}(h*reset*h]hreset}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubh function, using }(h function, using hjhhhNhNubh)}(h*__pragma__ ('kargs')*h]h__pragma__ (‘kargs’)}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubh and }(h and hjhhhNhNubh)}(h*__pragma__ ('nokwargs')*h]h__pragma__ (‘nokwargs’)}(hhhj ubah}(h ]h"]h$]h&]h(]uh*hhjubhR. The minified but not treeshaked Transcrypt runtime is slightly above 40 kB. The }(hR. The minified but not treeshaked Transcrypt runtime is slightly above 40 kB. The hjhhhNhNubh)}(h *fabric.js*h]h fabric.js}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjubhx library on the other hand occupies 180 kB. From this example it becomes clear that Transcrypt is extremely lightweight.}(hx library on the other hand occupies 180 kB. From this example it becomes clear that Transcrypt is extremely lightweight.hjhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKZhjhhubeh}(h ] minificationah"]h$] minificationah&]h(]uh*h hj^hhhh+hKVubeh}(h ] example-pongah"]h$] example: pongah&]h(]uh*h hjMhhhh+hK3ubh )}(hhh](h)}(hExample: jQueryh]hExample: jQuery}(hjJhjHhhhNhNubah}(h ]h"]h$]h&]h(]uh*hhjEhhhh+hK]ubh>)}(hXXIn contrast to the use of the *fabric.js* library in the Pong example, *jQuery* hasn't been encapsulated at all. It's just downloaded on the fly from a content delivery network and used as-is. Instead of the *$* (that is not a valid Python identifier), an *S* is used as :ref:`alias `. This might have been any character sequence.h](hIn contrast to the use of the }(hIn contrast to the use of the hjVhhhNhNubh)}(h *fabric.js*h]h fabric.js}(hhhj_ubah}(h ]h"]h$]h&]h(]uh*hhjVubh library in the Pong example, }(h library in the Pong example, hjVhhhNhNubh)}(h*jQuery*h]hjQuery}(hhhjrubah}(h ]h"]h$]h&]h(]uh*hhjVubh hasn’t been encapsulated at all. It’s just downloaded on the fly from a content delivery network and used as-is. Instead of the }(h hasn't been encapsulated at all. It's just downloaded on the fly from a content delivery network and used as-is. Instead of the hjVhhhNhNubh)}(h*$*h]h$}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjVubh- (that is not a valid Python identifier), an }(h- (that is not a valid Python identifier), an hjVhhhNhNubh)}(h*S*h]hS}(hhhjubah}(h ]h"]h$]h&]h(]uh*hhjVubh is used as }(h is used as hjVhhhNhNubh pending_xref)}(h:ref:`alias `h]h inline)}(hjh]halias}(hhhjubah}(h ]h"](xrefstdstd-refeh$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]refdocintegration_javascript refdomainjreftyperef refexplicitrefwarn reftarget pragma_aliasuh*jhh+hK_hjVubh.. This might have been any character sequence.}(h.. This might have been any character sequence.hjVhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hK_hjEhhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK)}(hXYou can write full screen iOS web apps in Transcrypt with native look and feel. As example here's an app simulating 6 dice. While this example is kept very simple, you can in fact make apps of arbitrary complexity, with fast and beautiful graphics using any JS graphics library, e.g. multiplayer games working over the Internet. If you add the app to your homescreen it will be cached, so no Internet connection is needed to use it. Web apps for iOS can obtain and use location information from the user.h]hXYou can write full screen iOS web apps in Transcrypt with native look and feel. As example here’s an app simulating 6 dice. While this example is kept very simple, you can in fact make apps of arbitrary complexity, with fast and beautiful graphics using any JS graphics library, e.g. multiplayer games working over the Internet. If you add the app to your homescreen it will be cached, so no Internet connection is needed to use it. Web apps for iOS can obtain and use location information from the user.}(hjhjhhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKjhjhhubh figure)}(hhh]h image)}(he.. figure:: ../images/ios_app.png :height: 500px :alt: A simple dice web app for iOS h]h}(h ]h"]h$]h&]h(]height500pxaltA simple dice web app for iOSuri../images/ios_app.png candidates}*jsuh*jhjhh+hNubah}(h ]h"]h$]h&]h(]uh*jhjhhhh+hNubj)}(hhh]j)}(hv.. figure:: ../images/ios_app_icon.png :height: 500px :alt: The prepacked dice icon on the homescreen h]h}(h ]h"]h$]h&]h(]height500pxalt)The prepacked dice icon on the homescreenuri../images/ios_app_icon.pngj}jjsuh*jhjhh+hNubah}(h ]h"]h$]h&]h(]uh*jhjhhhh+hNubh>)}(hsYou can install this app on your iPhone from http://www.transcrypt.org/live/transcrypt/demos/ios_app/ios_app.html .h](h-You can install this app on your iPhone from }(h-You can install this app on your iPhone from hjhhhNhNubhI)}(hDhttp://www.transcrypt.org/live/transcrypt/demos/ios_app/ios_app.htmlh]hDhttp://www.transcrypt.org/live/transcrypt/demos/ios_app/ios_app.html}(hhhjubah}(h ]h"]h$]h&]h(]refurijuh*hHhjubh .}(h .hjhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKthjhhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK4uh*jhjubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(h ios_app.pyh]h ios_app.py}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKwhjubj`)}(hX>import random class Dice: def __init__ (self): document.body.addEventListener ('touchstart', lambda event: event.preventDefault ()) document.body.addEventListener ('mousedown', lambda event: event.preventDefault ()) document.body.style.margin = 0 document.body.style.overflow = 'hidden'; self.all = document.createElement ('div') self.all.style.color = 'white' self.all.style.backgroundColor = 'black' self.all.style.height = '100%' self.all.style.width = '100%' self.all.style.padding = 0 self.all.style.margin = 0 document.body.appendChild (self.all) self.dices = [] for index in range (6): dice = document.createElement ('div') dice.normalColor = '#770000' if index < 3 else '#0000ff' dice.style.position = 'absolute' dice.style.backgroundColor = dice.normalColor dice.addEventListener ('touchstart', (lambda aDice: lambda: self.roll (aDice)) (dice)) # Returns inner lambda dice.addEventListener ('mousedown', (lambda aDice: lambda: self.roll (aDice)) (dice)) self.dices.append (dice) self.all.appendChild (dice) dice.inner = document.createElement ('div') dice.inner.setAttribute ('unselectable', 'on') dice.inner.style.fontWeight = 'bold' dice.inner.style.textAlign = 'center' dice.inner.style.position = 'absolute' dice.inner.innerHTML = '?' dice.appendChild (dice.inner) self.banner = document.createElement ('div') self.banner.style.position = 'absolute' self.banner.style.cursor = 'pointer' self.banner.addEventListener ('touchstart', self.gotoTranscryptSite) self.banner.addEventListener ('mousedown', self.gotoTranscryptSite) self.banner.style.fontFamily = 'arial' self.banner.innerHTML = ( 'www.' + 'Tran' + 'scrypt' + '.org' + ' Write your apps in Python for free!' ) self.all.appendChild (self.banner) self.bannerLarge = document.getElementById ('bannerLarge') self.bannerSmall = document.getElementById ('bannerSmall') self.audio = __new__ (Audio ('ios_app.mp3')) window.onresize = self.rightSize self.rightSize () def gotoTranscryptSite (self): document.location.href = 'http://www.transcrypt.org' def roll (self, dice): frameIndex = 10 self.audio.play () def frame (): nonlocal frameIndex frameIndex -= 1 dice.inner.innerHTML = random.randint (1, 6) if frameIndex: dice.style.color = random.choice (('red', 'green', 'blue', 'yellow')) setTimeout (frame, 100) else: dice.style.backgroundColor = dice.normalColor dice.style.color = 'white' frame () def rightSize (self): self.pageWidth = window.innerWidth self.pageHeight = window.innerHeight portrait = self.pageHeight > self.pageWidth for index, dice in enumerate (self.dices): if self.pageHeight > self.pageWidth: # Portrait dice.style.height = 0.3 * self.pageHeight dice.style.width = 0.4 * self.pageWidth dice.style.top = (0.03 + (index if index < 3 else index - 3) * 0.32) * self.pageHeight dice.style.left = (0.06 if index < 3 else 0.54) * self.pageWidth charBoxSide = 0.3 * self.pageHeight dice.inner.style.top = 0.15 * self.pageHeight - 0.6 * charBoxSide dice.inner.style.left = 0.2 * self.pageWidth - 0.5 * charBoxSide self.banner.style.top = 0.975 * self.pageHeight self.banner.style.left = 0.06 * self.pageWidth self.bannerLarge.style.fontSize = 0.017 * self.pageHeight self.bannerSmall.style.fontSize = 0.014 * self.pageHeight else: # Landscape dice.style.height = 0.4 * self.pageHeight dice.style.width = 0.3 * self.pageWidth dice.style.top = (0.06 if index < 3 else 0.54) * self.pageHeight dice.style.left = (0.03 + (index if index < 3 else index - 3) * 0.32) * self.pageWidth charBoxSide = 0.4 * self.pageHeight dice.inner.style.top = 0.2 * self.pageHeight - 0.6 * charBoxSide dice.inner.style.left = 0.15 * self.pageWidth - 0.5 * charBoxSide self.banner.style.top = 0.95 * self.pageHeight self.banner.style.left = 0.03 * self.pageWidth self.bannerLarge.style.fontSize = 0.015 * self.pageWidth self.bannerSmall.style.fontSize = 0.012 * self.pageWidth dice.inner.style.height = charBoxSide dice.inner.style.width = charBoxSide dice.inner.style.fontSize = charBoxSide dice = Dice () h]hX>import random class Dice: def __init__ (self): document.body.addEventListener ('touchstart', lambda event: event.preventDefault ()) document.body.addEventListener ('mousedown', lambda event: event.preventDefault ()) document.body.style.margin = 0 document.body.style.overflow = 'hidden'; self.all = document.createElement ('div') self.all.style.color = 'white' self.all.style.backgroundColor = 'black' self.all.style.height = '100%' self.all.style.width = '100%' self.all.style.padding = 0 self.all.style.margin = 0 document.body.appendChild (self.all) self.dices = [] for index in range (6): dice = document.createElement ('div') dice.normalColor = '#770000' if index < 3 else '#0000ff' dice.style.position = 'absolute' dice.style.backgroundColor = dice.normalColor dice.addEventListener ('touchstart', (lambda aDice: lambda: self.roll (aDice)) (dice)) # Returns inner lambda dice.addEventListener ('mousedown', (lambda aDice: lambda: self.roll (aDice)) (dice)) self.dices.append (dice) self.all.appendChild (dice) dice.inner = document.createElement ('div') dice.inner.setAttribute ('unselectable', 'on') dice.inner.style.fontWeight = 'bold' dice.inner.style.textAlign = 'center' dice.inner.style.position = 'absolute' dice.inner.innerHTML = '?' dice.appendChild (dice.inner) self.banner = document.createElement ('div') self.banner.style.position = 'absolute' self.banner.style.cursor = 'pointer' self.banner.addEventListener ('touchstart', self.gotoTranscryptSite) self.banner.addEventListener ('mousedown', self.gotoTranscryptSite) self.banner.style.fontFamily = 'arial' self.banner.innerHTML = ( 'www.' + 'Tran' + 'scrypt' + '.org' + ' Write your apps in Python for free!' ) self.all.appendChild (self.banner) self.bannerLarge = document.getElementById ('bannerLarge') self.bannerSmall = document.getElementById ('bannerSmall') self.audio = __new__ (Audio ('ios_app.mp3')) window.onresize = self.rightSize self.rightSize () def gotoTranscryptSite (self): document.location.href = 'http://www.transcrypt.org' def roll (self, dice): frameIndex = 10 self.audio.play () def frame (): nonlocal frameIndex frameIndex -= 1 dice.inner.innerHTML = random.randint (1, 6) if frameIndex: dice.style.color = random.choice (('red', 'green', 'blue', 'yellow')) setTimeout (frame, 100) else: dice.style.backgroundColor = dice.normalColor dice.style.color = 'white' frame () def rightSize (self): self.pageWidth = window.innerWidth self.pageHeight = window.innerHeight portrait = self.pageHeight > self.pageWidth for index, dice in enumerate (self.dices): if self.pageHeight > self.pageWidth: # Portrait dice.style.height = 0.3 * self.pageHeight dice.style.width = 0.4 * self.pageWidth dice.style.top = (0.03 + (index if index < 3 else index - 3) * 0.32) * self.pageHeight dice.style.left = (0.06 if index < 3 else 0.54) * self.pageWidth charBoxSide = 0.3 * self.pageHeight dice.inner.style.top = 0.15 * self.pageHeight - 0.6 * charBoxSide dice.inner.style.left = 0.2 * self.pageWidth - 0.5 * charBoxSide self.banner.style.top = 0.975 * self.pageHeight self.banner.style.left = 0.06 * self.pageWidth self.bannerLarge.style.fontSize = 0.017 * self.pageHeight self.bannerSmall.style.fontSize = 0.014 * self.pageHeight else: # Landscape dice.style.height = 0.4 * self.pageHeight dice.style.width = 0.3 * self.pageWidth dice.style.top = (0.06 if index < 3 else 0.54) * self.pageHeight dice.style.left = (0.03 + (index if index < 3 else index - 3) * 0.32) * self.pageWidth charBoxSide = 0.4 * self.pageHeight dice.inner.style.top = 0.2 * self.pageHeight - 0.6 * charBoxSide dice.inner.style.left = 0.15 * self.pageWidth - 0.5 * charBoxSide self.banner.style.top = 0.95 * self.pageHeight self.banner.style.left = 0.03 * self.pageWidth self.bannerLarge.style.fontSize = 0.015 * self.pageWidth self.bannerSmall.style.fontSize = 0.012 * self.pageWidth dice.inner.style.height = charBoxSide dice.inner.style.width = charBoxSide dice.inner.style.fontSize = charBoxSide dice = Dice () }(hhhj*ubah}(h ]h"]h$]h&]h(]sourceQ/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/ios_app/ios_app.pyjqjrjsjt}jvKsuh*j_hh+hKwhjubeh}(h ]id9ah"]j{ah$]h&]h(] literal_blockuh*jJhjubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubeh}(h ]h"]h$]h&]h(]colsKuh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjhhhNhNubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK6uh*jhjeubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(h ios_app.htmlh]h ios_app.html}(hjhj~ubah}(h ]h"]h$]h&]h(]uh*jOhh+hK}hj{ubj`)}(hXX h]hXX }(hhhjubah}(h ]h"]h$]h&]h(]sourceS/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/ios_app/ios_app.htmljqjrjsjt}jvKsuh*j_hh+hK}hj{ubeh}(h ]id10ah"]j{ah$]h&]h(] literal_blockuh*jJhjxubah}(h ]h"]h$]h&]h(]uh*jhjuubah}(h ]h"]h$]h&]h(]uh*jhjrubah}(h ]h"]h$]h&]h(]uh*jhjeubeh}(h ]h"]h$]h&]h(]colsKuh*jhjbubah}(h ]h"]h$]h&]h(]uh*jhjhhhNhNubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK8uh*jhjubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(hcache.manifesth]hcache.manifest}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhjubj`)}(hPCACHE MANIFEST # v45 CACHE: ios_app.html ios_app.mp3 __javascript__/ios_app.jsh]hPCACHE MANIFEST # v45 CACHE: ios_app.html ios_app.mp3 __javascript__/ios_app.js}(hhhjubah}(h ]h"]h$]h&]h(]sourceU/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/ios_app/cache.manifestjqjrjsjt}jvKsuh*j_hh+hKhjubeh}(h ]id11ah"]j{ah$]h&]h(] literal_blockuh*jJhjubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubeh}(h ]h"]h$]h&]h(]colsKuh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjhhhNhNubh>)}(hMN.B.1 Cache manifests have to be served with mime type *text/cache-manifest*.h](h7N.B.1 Cache manifests have to be served with mime type }(h7N.B.1 Cache manifests have to be served with mime type hj&hhhNhNubh)}(h*text/cache-manifest*h]htext/cache-manifest}(hhhj/ubah}(h ]h"]h$]h&]h(]uh*hhj&ubh.}(hjhj&hhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhjhhubh>)}(h|N.B.2 For native behaviour, e.g. no visible address bar, the app must indeed be added to the home screen of your iOS device.h]h|N.B.2 For native behaviour, e.g. no visible address bar, the app must indeed be added to the home screen of your iOS device.}(hjIhjGhhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKhjhhubeh}(h ]-example-ios-web-app-with-native-look-and-feelah"]h$].example: ios web app with native look and feelah&]h(]uh*h hjMhhhh+hKhubh )}(hhh](h)}(hExample: D3.jsh]hExample: D3.js}(hjbhj`hhhNhNubah}(h ]h"]h$]h&]h(]uh*hhj]hhhh+hKubh>)}(hThe *D3.js* graphics library offers animation by data driven DOM manipulation. It combines well with class based object oriented programming as supported by Trancrypt, leading to applications that are easy to understand and maintain.h](hThe }(hThe hjnhhhNhNubh)}(h*D3.js*h]hD3.js}(hhhjwubah}(h ]h"]h$]h&]h(]uh*hhjnubh graphics library offers animation by data driven DOM manipulation. It combines well with class based object oriented programming as supported by Trancrypt, leading to applications that are easy to understand and maintain.}(h graphics library offers animation by data driven DOM manipulation. It combines well with class based object oriented programming as supported by Trancrypt, leading to applications that are easy to understand and maintain.hjnhhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhj]hhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK8uh*jhjubj)}(hhh]h}(h ]h"]h$]h&]h(]colwidthKCuh*jhjubj)}(hhh]j)}(hhh](j)}(hhh]jK)}(hhh](jP)}(h d3js_demo.pyh]h d3js_demo.py}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhjubj`)}(hX class Spawn: def __init__ (self, width, height): self.width, self.height, self.spacing = self.fill = width, height, 100, d3.scale.category20 () self.svg = d3.select ('body' ) .append ('svg' ) .attr ('width', self.width ) .attr ('height', self.height ) .on ('mousemove', self.mousemove ) .on ('mousedown', self.mousedown) self.svg.append ('rect' ) .attr ('width', self.width ) .attr ('height', self.height) self.cursor = self.svg.append ('circle' ) .attr ('r', self.spacing ) .attr ('transform', 'translate ({}, {})' .format (self.width / 2, self.height / 2) ) .attr ('class', 'cursor') self.force = d3.layout.force ( ) .size ([self.width, self.height] ) .nodes ([{}] ) .linkDistance (self.spacing ) .charge (-1000 ) .on ('tick', self.tick) self.nodes, self.links, self.node, self.link = self.force.nodes (), self.force.links (), self.svg.selectAll ('.node'), self.svg.selectAll ('.link') self.restart () def mousemove (self): self.cursor.attr ('transform', 'translate (' + d3.mouse (self.svg.node ()) + ')') def mousedown (self): def pushLink (target): x, y = target.x - node.x, target.y - node.y if Math.sqrt (x * x + y * y) < self.spacing: spawn.links.push ({'source': node, 'target': target}) point = d3.mouse (self.svg.node ()) node = {'x': point [0], 'y': point [1]} self.nodes.push (node) self.nodes.forEach (pushLink) self.restart () def tick (self): self.link.attr ('x1', lambda d: d.source.x ) .attr ('y1', lambda d: d.source.y ) .attr ('x2', lambda d: d.target.x ) .attr ('y2', lambda d: d.target.y) self.node.attr ('cx', lambda d: d.x ) .attr ('cy', lambda d: d.y) def restart (self): self.link = self.link.data (self.links) self.link.enter ( ) .insert ('line', '.node' ) .attr('class', 'link') self.node = self.node.data (self.nodes) self.node.enter ( ) .insert ('circle', '.cursor' ) .attr ('class', 'node' ) .attr ('r', 7 ) .call (self.force.drag) self.force.start () spawn = Spawn (window.innerWidth, window.innerHeight) h]hX class Spawn: def __init__ (self, width, height): self.width, self.height, self.spacing = self.fill = width, height, 100, d3.scale.category20 () self.svg = d3.select ('body' ) .append ('svg' ) .attr ('width', self.width ) .attr ('height', self.height ) .on ('mousemove', self.mousemove ) .on ('mousedown', self.mousedown) self.svg.append ('rect' ) .attr ('width', self.width ) .attr ('height', self.height) self.cursor = self.svg.append ('circle' ) .attr ('r', self.spacing ) .attr ('transform', 'translate ({}, {})' .format (self.width / 2, self.height / 2) ) .attr ('class', 'cursor') self.force = d3.layout.force ( ) .size ([self.width, self.height] ) .nodes ([{}] ) .linkDistance (self.spacing ) .charge (-1000 ) .on ('tick', self.tick) self.nodes, self.links, self.node, self.link = self.force.nodes (), self.force.links (), self.svg.selectAll ('.node'), self.svg.selectAll ('.link') self.restart () def mousemove (self): self.cursor.attr ('transform', 'translate (' + d3.mouse (self.svg.node ()) + ')') def mousedown (self): def pushLink (target): x, y = target.x - node.x, target.y - node.y if Math.sqrt (x * x + y * y) < self.spacing: spawn.links.push ({'source': node, 'target': target}) point = d3.mouse (self.svg.node ()) node = {'x': point [0], 'y': point [1]} self.nodes.push (node) self.nodes.forEach (pushLink) self.restart () def tick (self): self.link.attr ('x1', lambda d: d.source.x ) .attr ('y1', lambda d: d.source.y ) .attr ('x2', lambda d: d.target.x ) .attr ('y2', lambda d: d.target.y) self.node.attr ('cx', lambda d: d.x ) .attr ('cy', lambda d: d.y) def restart (self): self.link = self.link.data (self.links) self.link.enter ( ) .insert ('line', '.node' ) .attr('class', 'link') self.node = self.node.data (self.nodes) self.node.enter ( ) .insert ('circle', '.cursor' ) .attr ('class', 'node' ) .attr ('r', 7 ) .call (self.force.drag) self.force.start () spawn = Spawn (window.innerWidth, window.innerHeight) }(hhhjubah}(h ]h"]h$]h&]h(]sourceU/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/d3js_demo/d3js_demo.pyjqjrjsjt}jvKsuh*j_hh+hKhjubeh}(h ]id12ah"]j{ah$]h&]h(] literal_blockuh*jJhjubah}(h ]h"]h$]h&]h(]uh*jhjubj)}(hhh]jK)}(hhh](jP)}(h d3js_demo.jsh]h d3js_demo.js}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhjubj`)}(hX// Transcrypt'ed from Python, 2021-06-01 16:18:36 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; var __name__ = '__main__'; export var Spawn = __class__ ('Spawn', [object], { __module__: __name__, get __init__ () {return __get__ (this, function (self, width, height) { var __left0__ = tuple ([width, height, 100, d3.scale.category20 ()]); self.width = __left0__ [0]; self.height = __left0__ [1]; self.spacing = __left0__ [2]; self.fill = __left0__; self.svg = d3.select ('body').append ('svg').attr ('width', self.width).attr ('height', self.height).on ('mousemove', self.mousemove).on ('mousedown', self.mousedown); self.svg.append ('rect').attr ('width', self.width).attr ('height', self.height); self.cursor = self.svg.append ('circle').attr ('r', self.spacing).attr ('transform', 'translate ({}, {})'.format (self.width / 2, self.height / 2)).attr ('class', 'cursor'); self.force = d3.layout.force ().size ([self.width, self.height]).nodes ([dict ({})]).linkDistance (self.spacing).charge (-(1000)).on ('tick', self.tick); var __left0__ = tuple ([self.force.nodes (), self.force.links (), self.svg.selectAll ('.node'), self.svg.selectAll ('.link')]); self.nodes = __left0__ [0]; self.links = __left0__ [1]; self.node = __left0__ [2]; self.link = __left0__ [3]; self.restart (); });}, get mousemove () {return __get__ (this, function (self) { self.cursor.attr ('transform', ('translate (' + d3.mouse (self.svg.node ())) + ')'); });}, get mousedown () {return __get__ (this, function (self) { var pushLink = function (target) { var __left0__ = tuple ([target.x - node.x, target.y - node.y]); var x = __left0__ [0]; var y = __left0__ [1]; if (Math.sqrt (x * x + y * y) < self.spacing) { spawn.links.push (dict ({'source': node, 'target': target})); } }; var point = d3.mouse (self.svg.node ()); var node = dict ({'x': point [0], 'y': point [1]}); self.nodes.push (node); self.nodes.forEach (pushLink); self.restart (); });}, get tick () {return __get__ (this, function (self) { self.link.attr ('x1', (function __lambda__ (d) { return d.source.x; })).attr ('y1', (function __lambda__ (d) { return d.source.y; })).attr ('x2', (function __lambda__ (d) { return d.target.x; })).attr ('y2', (function __lambda__ (d) { return d.target.y; })); self.node.attr ('cx', (function __lambda__ (d) { return d.x; })).attr ('cy', (function __lambda__ (d) { return d.y; })); });}, get restart () {return __get__ (this, function (self) { self.link = self.link.data (self.links); self.link.enter ().insert ('line', '.node').attr ('class', 'link'); self.node = self.node.data (self.nodes); self.node.enter ().insert ('circle', '.cursor').attr ('class', 'node').attr ('r', 7).call (self.force.drag); self.force.start (); });} }); export var spawn = Spawn (window.innerWidth, window.innerHeight); //# sourceMappingURL=d3js_demo.maph]hX// Transcrypt'ed from Python, 2021-06-01 16:18:36 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; var __name__ = '__main__'; export var Spawn = __class__ ('Spawn', [object], { __module__: __name__, get __init__ () {return __get__ (this, function (self, width, height) { var __left0__ = tuple ([width, height, 100, d3.scale.category20 ()]); self.width = __left0__ [0]; self.height = __left0__ [1]; self.spacing = __left0__ [2]; self.fill = __left0__; self.svg = d3.select ('body').append ('svg').attr ('width', self.width).attr ('height', self.height).on ('mousemove', self.mousemove).on ('mousedown', self.mousedown); self.svg.append ('rect').attr ('width', self.width).attr ('height', self.height); self.cursor = self.svg.append ('circle').attr ('r', self.spacing).attr ('transform', 'translate ({}, {})'.format (self.width / 2, self.height / 2)).attr ('class', 'cursor'); self.force = d3.layout.force ().size ([self.width, self.height]).nodes ([dict ({})]).linkDistance (self.spacing).charge (-(1000)).on ('tick', self.tick); var __left0__ = tuple ([self.force.nodes (), self.force.links (), self.svg.selectAll ('.node'), self.svg.selectAll ('.link')]); self.nodes = __left0__ [0]; self.links = __left0__ [1]; self.node = __left0__ [2]; self.link = __left0__ [3]; self.restart (); });}, get mousemove () {return __get__ (this, function (self) { self.cursor.attr ('transform', ('translate (' + d3.mouse (self.svg.node ())) + ')'); });}, get mousedown () {return __get__ (this, function (self) { var pushLink = function (target) { var __left0__ = tuple ([target.x - node.x, target.y - node.y]); var x = __left0__ [0]; var y = __left0__ [1]; if (Math.sqrt (x * x + y * y) < self.spacing) { spawn.links.push (dict ({'source': node, 'target': target})); } }; var point = d3.mouse (self.svg.node ()); var node = dict ({'x': point [0], 'y': point [1]}); self.nodes.push (node); self.nodes.forEach (pushLink); self.restart (); });}, get tick () {return __get__ (this, function (self) { self.link.attr ('x1', (function __lambda__ (d) { return d.source.x; })).attr ('y1', (function __lambda__ (d) { return d.source.y; })).attr ('x2', (function __lambda__ (d) { return d.target.x; })).attr ('y2', (function __lambda__ (d) { return d.target.y; })); self.node.attr ('cx', (function __lambda__ (d) { return d.x; })).attr ('cy', (function __lambda__ (d) { return d.y; })); });}, get restart () {return __get__ (this, function (self) { self.link = self.link.data (self.links); self.link.enter ().insert ('line', '.node').attr ('class', 'link'); self.node = self.node.data (self.nodes); self.node.enter ().insert ('circle', '.cursor').attr ('class', 'node').attr ('r', 7).call (self.force.drag); self.force.start (); });} }); export var spawn = Spawn (window.innerWidth, window.innerHeight); //# sourceMappingURL=d3js_demo.map}(hhhjubah}(h ]h"]h$]h&]h(]source`/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/d3js_demo/__target__/d3js_demo.jsjqjrjsjt}jvKsuh*j_hh+hKhjubeh}(h ]id13ah"]j{ah$]h&]h(] literal_blockuh*jJhjubah}(h ]h"]h$]h&]h(]uh*jhjubeh}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubeh}(h ]h"]h$]h&]h(]colsKuh*jhjubah}(h ]h"]h$]h&]h(]uh*jhj]hhhNhNubeh}(h ] example-d3-jsah"]h$]example: d3.jsah&]h(]uh*h hjMhhhh+hKubh )}(hhh](h)}(hExample: Reacth]hExample: React}(hj< hj: hhhNhNubah}(h ]h"]h$]h&]h(]uh*hhj7 hhhh+hKubh>)}(hX*React* is a JavaScript library for easy creation of interactive UI's. Changes to the UI are made by fast manipulation of a light-weight virtual DOM. The real DOM, which is much slower to manipulate, is then compared with the altered virtual DOM and updated efficiently in a minimum number of steps. This way of working leads to good performance, at the same time keeping a straightforward structure of application UI code, since the complexities of optimizing DOM updates are left to the React library. React is unintrusive and mixes well with Transcrypt, allowing creation of extensive web applications that combine maintainability with speed. This example once again clearly illustrates the philosophy behind Transcrypt: rather than confining you to a "parallel" universe that could never keep up, Transcrypt offers you direct access to the ever expanding universe of innovative JavaScript libraries.h](h)}(h*React*h]hReact}(hhhjL ubah}(h ]h"]h$]h&]h(]uh*hhjH ubhX is a JavaScript library for easy creation of interactive UI’s. Changes to the UI are made by fast manipulation of a light-weight virtual DOM. The real DOM, which is much slower to manipulate, is then compared with the altered virtual DOM and updated efficiently in a minimum number of steps. This way of working leads to good performance, at the same time keeping a straightforward structure of application UI code, since the complexities of optimizing DOM updates are left to the React library. React is unintrusive and mixes well with Transcrypt, allowing creation of extensive web applications that combine maintainability with speed. This example once again clearly illustrates the philosophy behind Transcrypt: rather than confining you to a “parallel” universe that could never keep up, Transcrypt offers you direct access to the ever expanding universe of innovative JavaScript libraries.}(hX is a JavaScript library for easy creation of interactive UI's. Changes to the UI are made by fast manipulation of a light-weight virtual DOM. The real DOM, which is much slower to manipulate, is then compared with the altered virtual DOM and updated efficiently in a minimum number of steps. This way of working leads to good performance, at the same time keeping a straightforward structure of application UI code, since the complexities of optimizing DOM updates are left to the React library. React is unintrusive and mixes well with Transcrypt, allowing creation of extensive web applications that combine maintainability with speed. This example once again clearly illustrates the philosophy behind Transcrypt: rather than confining you to a "parallel" universe that could never keep up, Transcrypt offers you direct access to the ever expanding universe of innovative JavaScript libraries.hjH hhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhj7 hhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK:uh*jhjh ubj)}(hhh]h}(h ]h"]h$]h&]h(]colwidthKEuh*jhjh ubj)}(hhh]j)}(hhh](j)}(hhh]jK)}(hhh](jP)}(h react_demo.pyh]h react_demo.py}(hj hj ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hXfrom org.reactjs import createElement, useState, useEffect, useRef from org.reactjs.dom import render as react_render # Helper functions def h(elm_type, props='', *args): return createElement(elm_type, props, *args) def render(react_element, destination_id, callback=lambda: None): container = document.getElementById(destination_id) react_render(react_element, container, callback) def useInterval(func, delay=None): # can be used as `useInterval(func, delay)` # or as `@useInterval(delay)` if delay is None: delay = func return lambda fn: useInterval(fn, delay) ref = useRef(func) ref.current = func @useEffect.withDeps(delay) def setup(): id = setInterval(lambda: ref.current(), delay) return lambda: clearInterval(id) return func # Create a component def Hello(props): count, setCount = useState(0) @useInterval(1000) def updateCounter(): setCount(count+1) return h( 'div', {'className': 'maindiv'}, h('h1', None, 'Hello ', props['name']), h('p', None, 'Lorem ipsum dolor sit ame.'), h('p', None, 'Counter: ', count), h( 'button', {'onClick': updateCounter}, 'Increment', ) ) # Render the component in a 'container' div element = React.createElement(Hello, {'name': 'React!'}) render(element, 'container') h]hXfrom org.reactjs import createElement, useState, useEffect, useRef from org.reactjs.dom import render as react_render # Helper functions def h(elm_type, props='', *args): return createElement(elm_type, props, *args) def render(react_element, destination_id, callback=lambda: None): container = document.getElementById(destination_id) react_render(react_element, container, callback) def useInterval(func, delay=None): # can be used as `useInterval(func, delay)` # or as `@useInterval(delay)` if delay is None: delay = func return lambda fn: useInterval(fn, delay) ref = useRef(func) ref.current = func @useEffect.withDeps(delay) def setup(): id = setInterval(lambda: ref.current(), delay) return lambda: clearInterval(id) return func # Create a component def Hello(props): count, setCount = useState(0) @useInterval(1000) def updateCounter(): setCount(count+1) return h( 'div', {'className': 'maindiv'}, h('h1', None, 'Hello ', props['name']), h('p', None, 'Lorem ipsum dolor sit ame.'), h('p', None, 'Counter: ', count), h( 'button', {'onClick': updateCounter}, 'Increment', ) ) # Render the component in a 'container' div element = React.createElement(Hello, {'name': 'React!'}) render(element, 'container') }(hhhj ubah}(h ]h"]h$]h&]h(]sourceW/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/react_demo/react_demo.pyjqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id14ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubj)}(hhh]jK)}(hhh](jP)}(h react_demo.jsh]h react_demo.js}(hj hj ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hX// Transcrypt'ed from Python, 2021-06-01 16:18:47 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {render as react_render} from './org.reactjs.dom.js'; import {createElement, useEffect, useRef, useState} from './org.reactjs.js'; var __name__ = '__main__'; export var h = function (elm_type, props) { if (typeof props == 'undefined' || (props != null && props.hasOwnProperty ("__kwargtrans__"))) {; var props = ''; }; var args = tuple ([].slice.apply (arguments).slice (2)); return createElement (elm_type, props, ...args); }; export var render = function (react_element, destination_id, callback) { if (typeof callback == 'undefined' || (callback != null && callback.hasOwnProperty ("__kwargtrans__"))) {; var callback = (function __lambda__ () { return null; }); }; var container = document.getElementById (destination_id); react_render (react_element, container, callback); }; export var useInterval = function (func, delay) { if (typeof delay == 'undefined' || (delay != null && delay.hasOwnProperty ("__kwargtrans__"))) {; var delay = null; }; if (delay === null) { var delay = func; return (function __lambda__ (fn) { return useInterval (fn, delay); }); } var ref = useRef (func); ref.current = func; var setup = useEffect.withDeps (delay) (function () { var id = setInterval ((function __lambda__ () { return ref.current (); }), delay); return (function __lambda__ () { return clearInterval (id); }); }); return func; }; export var Hello = function (props) { var __left0__ = useState (0); var count = __left0__ [0]; var setCount = __left0__ [1]; var updateCounter = useInterval (1000) (function () { setCount (count + 1); }); return h ('div', dict ({'className': 'maindiv'}), h ('h1', null, 'Hello ', props ['name']), h ('p', null, 'Lorem ipsum dolor sit ame.'), h ('p', null, 'Counter: ', count), h ('button', dict ({'onClick': updateCounter}), 'Increment')); }; export var element = React.createElement (Hello, dict ({'name': 'React!'})); render (element, 'container'); //# sourceMappingURL=react_demo.maph]hX// Transcrypt'ed from Python, 2021-06-01 16:18:47 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {render as react_render} from './org.reactjs.dom.js'; import {createElement, useEffect, useRef, useState} from './org.reactjs.js'; var __name__ = '__main__'; export var h = function (elm_type, props) { if (typeof props == 'undefined' || (props != null && props.hasOwnProperty ("__kwargtrans__"))) {; var props = ''; }; var args = tuple ([].slice.apply (arguments).slice (2)); return createElement (elm_type, props, ...args); }; export var render = function (react_element, destination_id, callback) { if (typeof callback == 'undefined' || (callback != null && callback.hasOwnProperty ("__kwargtrans__"))) {; var callback = (function __lambda__ () { return null; }); }; var container = document.getElementById (destination_id); react_render (react_element, container, callback); }; export var useInterval = function (func, delay) { if (typeof delay == 'undefined' || (delay != null && delay.hasOwnProperty ("__kwargtrans__"))) {; var delay = null; }; if (delay === null) { var delay = func; return (function __lambda__ (fn) { return useInterval (fn, delay); }); } var ref = useRef (func); ref.current = func; var setup = useEffect.withDeps (delay) (function () { var id = setInterval ((function __lambda__ () { return ref.current (); }), delay); return (function __lambda__ () { return clearInterval (id); }); }); return func; }; export var Hello = function (props) { var __left0__ = useState (0); var count = __left0__ [0]; var setCount = __left0__ [1]; var updateCounter = useInterval (1000) (function () { setCount (count + 1); }); return h ('div', dict ({'className': 'maindiv'}), h ('h1', null, 'Hello ', props ['name']), h ('p', null, 'Lorem ipsum dolor sit ame.'), h ('p', null, 'Counter: ', count), h ('button', dict ({'onClick': updateCounter}), 'Increment')); }; export var element = React.createElement (Hello, dict ({'name': 'React!'})); render (element, 'container'); //# sourceMappingURL=react_demo.map}(hhhj ubah}(h ]h"]h$]h&]h(]sourceb/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/react_demo/__target__/react_demo.jsjqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id15ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubeh}(h ]h"]h$]h&]h(]uh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhjh ubeh}(h ]h"]h$]h&]h(]colsKuh*jhje ubah}(h ]h"]h$]h&]h(]uh*jhj7 hhhNhNubeh}(h ] example-reactah"]h$]example: reactah&]h(]uh*h hjMhhhh+hKubh )}(hhh](h)}(h Example: Rioth]h Example: Riot}(hj hj hhhNhNubah}(h ]h"]h$]h&]h(]uh*hhj hhhh+hKubh>)}(hX*Riot* is a UI framework that combines the use of custom tags and a virtual DOM, much like the one in React. Custom tags look like ordinary HTML tags, but whereas HTML tags only define structure, Riot tags define structure, style and behaviour. Custom tags are compiled to JavaScript by a compiler that comes with Riot. With these custom tags as reusable components, web pages can be built. Riot itself is tiny, and the virtual DOM allows for fast adaptation of page content.h](h)}(h*Riot*h]hRiot}(hhhj! ubah}(h ]h"]h$]h&]h(]uh*hhj ubhX is a UI framework that combines the use of custom tags and a virtual DOM, much like the one in React. Custom tags look like ordinary HTML tags, but whereas HTML tags only define structure, Riot tags define structure, style and behaviour. Custom tags are compiled to JavaScript by a compiler that comes with Riot. With these custom tags as reusable components, web pages can be built. Riot itself is tiny, and the virtual DOM allows for fast adaptation of page content.}(hX is a UI framework that combines the use of custom tags and a virtual DOM, much like the one in React. Custom tags look like ordinary HTML tags, but whereas HTML tags only define structure, Riot tags define structure, style and behaviour. Custom tags are compiled to JavaScript by a compiler that comes with Riot. With these custom tags as reusable components, web pages can be built. Riot itself is tiny, and the virtual DOM allows for fast adaptation of page content.hj hhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK:uh*jhj= ubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(hriot_demo.htmlh]hriot_demo.html}(hjX hjV ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhjS ubj`)}(hX4 Hello PyRiot ;-) h]hX4 Hello PyRiot ;-) }(hhhjd ubah}(h ]h"]h$]h&]h(]sourceW/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/riot_demo/riot_demo.htmljqjrjsjt}jvKsuh*j_hh+hKhjS ubeh}(h ]id16ah"]j{ah$]h&]h(] literal_blockuh*jJhjP ubah}(h ]h"]h$]h&]h(]uh*jhjM ubah}(h ]h"]h$]h&]h(]uh*jhjJ ubah}(h ]h"]h$]h&]h(]uh*jhj= ubeh}(h ]h"]h$]h&]h(]colsKuh*jhj: ubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK;uh*jhj ubj)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK:uh*jhj ubj)}(hhh]j)}(hhh](j)}(hhh]jK)}(hhh](jP)}(hsample.tag, a classic Riot tagh]hsample.tag, a classic Riot tag}(hj hj ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hX// vim: ft=html

Riot Native Tag

name: {name} - counter: {this.count()}
h]hX// vim: ft=html

Riot Native Tag

name: {name} - counter: {this.count()}
}(hhhj ubah}(h ]h"]h$]h&]h(]sourceX/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/riot_demo/tags/sample.tagjqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id17ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubj)}(hhh]jK)}(hhh](jP)}(hsample.js, compiled by Rioth]hsample.js, compiled by Riot}(hj hj ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hX// vim: ft=html riot.tag2('sample', '

Riot Native Tag

name: {name} - counter: {this.count()}
', 'sample h1,[riot-tag="sample"] h1,[data-is="sample"] h1{color: red}', '', function(opts) { this.counter = 0 this.count = function() { this.counter += 1; return this.counter }.bind(this) window.native_tag = this this.on('update', function() { this.lv = [{name: 'n1'}, {'name': 'n2'}] this.update() }) }); h]hX// vim: ft=html riot.tag2('sample', '

Riot Native Tag

name: {name} - counter: {this.count()}
', 'sample h1,[riot-tag="sample"] h1,[data-is="sample"] h1{color: red}', '', function(opts) { this.counter = 0 this.count = function() { this.counter += 1; return this.counter }.bind(this) window.native_tag = this this.on('update', function() { this.lv = [{name: 'n1'}, {'name': 'n2'}] this.update() }) }); }(hhhj ubah}(h ]h"]h$]h&]h(]sourceW/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/riot_demo/tags/sample.jsjqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id18ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubeh}(h ]h"]h$]h&]h(]uh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubeh}(h ]h"]h$]h&]h(]colsKuh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthKAuh*jhj> ubj)}(hhh]h}(h ]h"]h$]h&]h(]colwidthKBuh*jhj> ubj)}(hhh]j)}(hhh](j)}(hhh]jK)}(hhh](jP)}(h2riot_tag.py, baseclass of all Transcrypt Riot tagsh]h2riot_tag.py, baseclass of all Transcrypt Riot tags}(hjc hja ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj^ ubj`)}(hXO# Parent Class for a Transcrypt Riot Tag # # This binds the namespace of a riot tag at before-mount event 100% to that of # the a transcrypt instance, except members which begin with an underscore, those # are private to the transcrypt object. # # The 4 riot lifecycle events are bound to overwritable python functions. # # Immutables (strings, ints, ...) are bound to property functions within the tag, # so the templates work, based on state in the transcrypt tag. # State can be changed in the riot tag as well but take care to not create new # references - you won't find them in the Transcrypt tag. # # # Best Practices: # - mutate state only in the transcrypt tag. # - declare all variables so they are bound into the riot tag # - IF you declare new variables to be used in templates, run # self.bind_vars(self.riot_tag) # TODO: docstring format not accepted by the transpiler, strange. __author__ = "Gunther Klessinger, gk@axiros.com, Germany" # just a minihack to get some colors, mainly to test lamdas and imports: from color import colors, cprint as col_print c = colors M, I, L, R, B = c['purple'], c['orange'], c['gray'], c['red'], c['black'] lifecycle_ev = ['before-mount', 'mount', 'update', 'unmount'] cur_tag_col = 0 class RiotTag: """ taking care for extending the riot tag obj with functions and immutable(!) properties of derivations of us See counter. """ debug = None # placeholders: template = '

it worx

' style = '' node_name = 'unmounted' opts = None def __init__(self, tag, opts): # opts into the python instance, why not: self.opts = opts self._setup_tag(tag) # giving ourselves a unique color: global cur_tag_col # working (!) cur_tag_col = (cur_tag_col + 1) % len(colors) # TODO values() on a dict self.my_col = colors.items()[cur_tag_col][1] def _setup_tag(self, tag): # keeping mutual refs tag.py_obj = self self.riot_tag = tag # making the event system call self's methods: handlers = {} for ev in lifecycle_ev: f = getattr(self, ev.replace('-', '_')) if f: # this.on('mount', function() {...}): # whats nicer? tag.on(ev, f) def pp(self, *msg): # color flash in the console. one color per tag instance. col_print( #B(self.riot_tag._riot_id), L('<', self.my_col(self.node_name, self.my_col), '/> '), M(' '.join([s for s in msg]))) def _lifecycle_ev(self, mode): if self.debug: self.pp(mode + 'ing') # overwrite these for your specific one: def update (self): self._lifecycle_ev('update') def mount (self): self._lifecycle_ev('mount') def unmount(self): self._lifecycle_ev('unmount') def before_mount(self): self._lifecycle_ev('before-mount') return self.bind_vars() def bind_vars(self): tag = self.riot_tag self.node_name = tag.root.nodeName.lower() self.debug and self.pp('binding vars') # binding self's functions into the tag instance # binding writable properties to everything else (e.g. ints, strs...) tag._immutables = im = [] lc = lifecycle_ev for k in dir(self): # private or lifecycle function? don't bind: if k[0] == '_' or k in lifecycle_ev or k == 'before_mount': continue v = getattr(self, k) # these I can't write in python. Lets use JS then. # TODO there should be, maybe some mocking facility for code # testing w/o a js runtime: __pragma__('js', '{}', ''' typeof v === "function" || typeof v === "object" ? tag[k] = self[k] : tag._immutables.push(k)''') __pragma__('js', '{}', ''' var i = tag._immutables, py = self i.forEach(function(k, j, i) { Object.defineProperty(tag, k, { get: function() { return self[k]}, set: function(v) { self[k] = v } }) })''') h]hXO# Parent Class for a Transcrypt Riot Tag # # This binds the namespace of a riot tag at before-mount event 100% to that of # the a transcrypt instance, except members which begin with an underscore, those # are private to the transcrypt object. # # The 4 riot lifecycle events are bound to overwritable python functions. # # Immutables (strings, ints, ...) are bound to property functions within the tag, # so the templates work, based on state in the transcrypt tag. # State can be changed in the riot tag as well but take care to not create new # references - you won't find them in the Transcrypt tag. # # # Best Practices: # - mutate state only in the transcrypt tag. # - declare all variables so they are bound into the riot tag # - IF you declare new variables to be used in templates, run # self.bind_vars(self.riot_tag) # TODO: docstring format not accepted by the transpiler, strange. __author__ = "Gunther Klessinger, gk@axiros.com, Germany" # just a minihack to get some colors, mainly to test lamdas and imports: from color import colors, cprint as col_print c = colors M, I, L, R, B = c['purple'], c['orange'], c['gray'], c['red'], c['black'] lifecycle_ev = ['before-mount', 'mount', 'update', 'unmount'] cur_tag_col = 0 class RiotTag: """ taking care for extending the riot tag obj with functions and immutable(!) properties of derivations of us See counter. """ debug = None # placeholders: template = '

it worx

' style = '' node_name = 'unmounted' opts = None def __init__(self, tag, opts): # opts into the python instance, why not: self.opts = opts self._setup_tag(tag) # giving ourselves a unique color: global cur_tag_col # working (!) cur_tag_col = (cur_tag_col + 1) % len(colors) # TODO values() on a dict self.my_col = colors.items()[cur_tag_col][1] def _setup_tag(self, tag): # keeping mutual refs tag.py_obj = self self.riot_tag = tag # making the event system call self's methods: handlers = {} for ev in lifecycle_ev: f = getattr(self, ev.replace('-', '_')) if f: # this.on('mount', function() {...}): # whats nicer? tag.on(ev, f) def pp(self, *msg): # color flash in the console. one color per tag instance. col_print( #B(self.riot_tag._riot_id), L('<', self.my_col(self.node_name, self.my_col), '/> '), M(' '.join([s for s in msg]))) def _lifecycle_ev(self, mode): if self.debug: self.pp(mode + 'ing') # overwrite these for your specific one: def update (self): self._lifecycle_ev('update') def mount (self): self._lifecycle_ev('mount') def unmount(self): self._lifecycle_ev('unmount') def before_mount(self): self._lifecycle_ev('before-mount') return self.bind_vars() def bind_vars(self): tag = self.riot_tag self.node_name = tag.root.nodeName.lower() self.debug and self.pp('binding vars') # binding self's functions into the tag instance # binding writable properties to everything else (e.g. ints, strs...) tag._immutables = im = [] lc = lifecycle_ev for k in dir(self): # private or lifecycle function? don't bind: if k[0] == '_' or k in lifecycle_ev or k == 'before_mount': continue v = getattr(self, k) # these I can't write in python. Lets use JS then. # TODO there should be, maybe some mocking facility for code # testing w/o a js runtime: __pragma__('js', '{}', ''' typeof v === "function" || typeof v === "object" ? tag[k] = self[k] : tag._immutables.push(k)''') __pragma__('js', '{}', ''' var i = tag._immutables, py = self i.forEach(function(k, j, i) { Object.defineProperty(tag, k, { get: function() { return self[k]}, set: function(v) { self[k] = v } }) })''') }(hhhjo ubah}(h ]h"]h$]h&]h(]sourceT/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/riot_demo/riot_tag.pyjqjrjsjt}jvKsuh*j_hh+hKhj^ ubeh}(h ]id19ah"]j{ah$]h&]h(] literal_blockuh*jJhj[ ubah}(h ]h"]h$]h&]h(]uh*jhjX ubj)}(hhh]jK)}(hhh](jP)}(h#riot_tag.js, compiled by Transcrypth]h#riot_tag.js, compiled by Transcrypt}(hj hj ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hX// Transcrypt'ed from Python, 2021-06-01 16:18:52 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {cprint as col_print, colors} from './color.js'; var __name__ = 'riot_tag'; export var __author__ = 'Gunther Klessinger, gk@axiros.com, Germany'; export var c = colors; var __left0__ = tuple ([c ['purple'], c ['orange'], c ['gray'], c ['red'], c ['black']]); export var M = __left0__ [0]; export var I = __left0__ [1]; export var L = __left0__ [2]; export var R = __left0__ [3]; export var B = __left0__ [4]; export var lifecycle_ev = ['before-mount', 'mount', 'update', 'unmount']; export var cur_tag_col = 0; export var RiotTag = __class__ ('RiotTag', [object], { __module__: __name__, debug: null, template: '

it worx

', style: '', node_name: 'unmounted', opts: null, get __init__ () {return __get__ (this, function (self, tag, opts) { self.opts = opts; self._setup_tag (tag); cur_tag_col = __mod__ (cur_tag_col + 1, len (colors)); self.my_col = colors.py_items () [cur_tag_col] [1]; });}, get _setup_tag () {return __get__ (this, function (self, tag) { tag.py_obj = self; self.riot_tag = tag; var handlers = dict ({}); for (var ev of lifecycle_ev) { var f = getattr (self, ev.py_replace ('-', '_')); if (f) { tag.on (ev, f); } } });}, get pp () {return __get__ (this, function (self) { var msg = tuple ([].slice.apply (arguments).slice (1)); col_print (L ('<', self.my_col (self.node_name, self.my_col), '/> '), M (' '.join ((function () { var __accu0__ = []; for (var s of msg) { __accu0__.append (s); } return __accu0__; }) ()))); });}, get _lifecycle_ev () {return __get__ (this, function (self, mode) { if (self.debug) { self.pp (mode + 'ing'); } });}, get py_update () {return __get__ (this, function (self) { self._lifecycle_ev ('update'); });}, get mount () {return __get__ (this, function (self) { self._lifecycle_ev ('mount'); });}, get unmount () {return __get__ (this, function (self) { self._lifecycle_ev ('unmount'); });}, get before_mount () {return __get__ (this, function (self) { self._lifecycle_ev ('before-mount'); return self.bind_vars (); });}, get bind_vars () {return __get__ (this, function (self) { var tag = self.riot_tag; self.node_name = tag.root.nodeName.lower (); self.debug && self.pp ('binding vars'); var __left0__ = []; tag._immutables = __left0__; var im = __left0__; var lc = lifecycle_ev; for (var k of dir (self)) { if (k [0] == '_' || __in__ (k, lifecycle_ev) || k == 'before_mount') { continue; } var v = getattr (self, k); typeof v === "function" || typeof v === "object" ? tag[k] = self[k] : tag._immutables.push(k) } var i = tag._immutables, py = self i.forEach(function(k, j, i) { Object.defineProperty(tag, k, { get: function() { return self[k]}, set: function(v) { self[k] = v } }) }) });} }); //# sourceMappingURL=riot_tag.maph]hX// Transcrypt'ed from Python, 2021-06-01 16:18:52 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {cprint as col_print, colors} from './color.js'; var __name__ = 'riot_tag'; export var __author__ = 'Gunther Klessinger, gk@axiros.com, Germany'; export var c = colors; var __left0__ = tuple ([c ['purple'], c ['orange'], c ['gray'], c ['red'], c ['black']]); export var M = __left0__ [0]; export var I = __left0__ [1]; export var L = __left0__ [2]; export var R = __left0__ [3]; export var B = __left0__ [4]; export var lifecycle_ev = ['before-mount', 'mount', 'update', 'unmount']; export var cur_tag_col = 0; export var RiotTag = __class__ ('RiotTag', [object], { __module__: __name__, debug: null, template: '

it worx

', style: '', node_name: 'unmounted', opts: null, get __init__ () {return __get__ (this, function (self, tag, opts) { self.opts = opts; self._setup_tag (tag); cur_tag_col = __mod__ (cur_tag_col + 1, len (colors)); self.my_col = colors.py_items () [cur_tag_col] [1]; });}, get _setup_tag () {return __get__ (this, function (self, tag) { tag.py_obj = self; self.riot_tag = tag; var handlers = dict ({}); for (var ev of lifecycle_ev) { var f = getattr (self, ev.py_replace ('-', '_')); if (f) { tag.on (ev, f); } } });}, get pp () {return __get__ (this, function (self) { var msg = tuple ([].slice.apply (arguments).slice (1)); col_print (L ('<', self.my_col (self.node_name, self.my_col), '/> '), M (' '.join ((function () { var __accu0__ = []; for (var s of msg) { __accu0__.append (s); } return __accu0__; }) ()))); });}, get _lifecycle_ev () {return __get__ (this, function (self, mode) { if (self.debug) { self.pp (mode + 'ing'); } });}, get py_update () {return __get__ (this, function (self) { self._lifecycle_ev ('update'); });}, get mount () {return __get__ (this, function (self) { self._lifecycle_ev ('mount'); });}, get unmount () {return __get__ (this, function (self) { self._lifecycle_ev ('unmount'); });}, get before_mount () {return __get__ (this, function (self) { self._lifecycle_ev ('before-mount'); return self.bind_vars (); });}, get bind_vars () {return __get__ (this, function (self) { var tag = self.riot_tag; self.node_name = tag.root.nodeName.lower (); self.debug && self.pp ('binding vars'); var __left0__ = []; tag._immutables = __left0__; var im = __left0__; var lc = lifecycle_ev; for (var k of dir (self)) { if (k [0] == '_' || __in__ (k, lifecycle_ev) || k == 'before_mount') { continue; } var v = getattr (self, k); typeof v === "function" || typeof v === "object" ? tag[k] = self[k] : tag._immutables.push(k) } var i = tag._immutables, py = self i.forEach(function(k, j, i) { Object.defineProperty(tag, k, { get: function() { return self[k]}, set: function(v) { self[k] = v } }) }) });} }); //# sourceMappingURL=riot_tag.map}(hhhj ubah}(h ]h"]h$]h&]h(]source_/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/riot_demo/__target__/riot_tag.jsjqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id20ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhjX ubeh}(h ]h"]h$]h&]h(]uh*jhjU ubah}(h ]h"]h$]h&]h(]uh*jhj> ubeh}(h ]h"]h$]h&]h(]colsKuh*jhj; ubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK@uh*jhj ubj)}(hhh]h}(h ]h"]h$]h&]h(]colwidthKCuh*jhj ubj)}(hhh]j)}(hhh](j)}(hhh]jK)}(hhh](jP)}(h1riot_demo.py, a derived Transcrypt Riot tag classh]h1riot_demo.py, a derived Transcrypt Riot tag class}(hj hj ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hX<# an example user tag, using RiotTag from riot_tag import RiotTag class P(RiotTag): debug = 1 # never do mutables on class level. this is just to check if transpiler # creates the same behaviour - and it does, a second tag instance gets # the same lv object: lv = [{'name': 'n0'}] # immuatble on class level. does a second instance start at 1? # answer: yes, perfect: counter = 1 template = '''

Riot Transcrypt Tag Instance {label}

INNER
''' def count_up(self): self.counter = self.counter + 1 self.pp('counter:', self.counter, 'len lv:', len(self.lv), 'adding one lv' ) self.lv.append({'name': 'n' + self.counter}) return self.counter # try some inheritance... class Sample2(P): # ... and change the state at every update, just for fun: template = P.template.replace('INNER', '''
name: {name} - counter: {count_up()}
''') # no scoped styles currently style = '''sample2 h5 {color: green}''' def __init__(self, tag, opts): self.label = opts.label.capitalize() # this rocks so much. # alternative to super: RiotTag.__init__(self, tag, opts) # uncomment next line and chrome will stop: # debugger self.pp('tag init', 'adding 2 lv') # mutating the lv object: self.lv.extend([{'name': 'n1'}, {'name': 'n2'}]) def update(self): self.pp('update handler in the custom tag, calling super') RiotTag.update(self) h]hX<# an example user tag, using RiotTag from riot_tag import RiotTag class P(RiotTag): debug = 1 # never do mutables on class level. this is just to check if transpiler # creates the same behaviour - and it does, a second tag instance gets # the same lv object: lv = [{'name': 'n0'}] # immuatble on class level. does a second instance start at 1? # answer: yes, perfect: counter = 1 template = '''

Riot Transcrypt Tag Instance {label}

INNER
''' def count_up(self): self.counter = self.counter + 1 self.pp('counter:', self.counter, 'len lv:', len(self.lv), 'adding one lv' ) self.lv.append({'name': 'n' + self.counter}) return self.counter # try some inheritance... class Sample2(P): # ... and change the state at every update, just for fun: template = P.template.replace('INNER', '''
name: {name} - counter: {count_up()}
''') # no scoped styles currently style = '''sample2 h5 {color: green}''' def __init__(self, tag, opts): self.label = opts.label.capitalize() # this rocks so much. # alternative to super: RiotTag.__init__(self, tag, opts) # uncomment next line and chrome will stop: # debugger self.pp('tag init', 'adding 2 lv') # mutating the lv object: self.lv.extend([{'name': 'n1'}, {'name': 'n2'}]) def update(self): self.pp('update handler in the custom tag, calling super') RiotTag.update(self) }(hhhj ubah}(h ]h"]h$]h&]h(]sourceU/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/riot_demo/riot_demo.pyjqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id21ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubj)}(hhh]jK)}(hhh](jP)}(h$riot_demo.js, compiled by Transcrypth]h$riot_demo.js, compiled by Transcrypt}(hj5 hj3 ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj0 ubj`)}(hX // Transcrypt'ed from Python, 2021-06-01 16:18:52 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {RiotTag} from './riot_tag.js'; var __name__ = '__main__'; export var P = __class__ ('P', [RiotTag], { __module__: __name__, debug: 1, lv: [dict ({'name': 'n0'})], counter: 1, template: '

Riot Transcrypt Tag Instance {label}

\n
INNER
', get count_up () {return __get__ (this, function (self) { self.counter = self.counter + 1; self.pp ('counter:', self.counter, 'len lv:', len (self.lv), 'adding one lv'); self.lv.append (dict ({'name': 'n' + self.counter})); return self.counter; });} }); export var Sample2 = __class__ ('Sample2', [P], { __module__: __name__, template: P.template.py_replace ('INNER', '\n
\n
name: {name} - counter: {count_up()}
\n
\n '), style: 'sample2 h5 {color: green}', get __init__ () {return __get__ (this, function (self, tag, opts) { self.label = opts.label.capitalize (); RiotTag.__init__ (self, tag, opts); self.pp ('tag init', 'adding 2 lv'); self.lv.extend ([dict ({'name': 'n1'}), dict ({'name': 'n2'})]); });}, get py_update () {return __get__ (this, function (self) { self.pp ('update handler in the custom tag, calling super'); RiotTag.py_update (self); });} }); //# sourceMappingURL=riot_demo.maph]hX // Transcrypt'ed from Python, 2021-06-01 16:18:52 import {AssertionError, AttributeError, BaseException, DeprecationWarning, Exception, IndexError, IterableError, KeyError, NotImplementedError, RuntimeWarning, StopIteration, UserWarning, ValueError, Warning, __JsIterator__, __PyIterator__, __Terminal__, __add__, __and__, __call__, __class__, __envir__, __eq__, __floordiv__, __ge__, __get__, __getcm__, __getitem__, __getslice__, __getsm__, __gt__, __i__, __iadd__, __iand__, __idiv__, __ijsmod__, __ilshift__, __imatmul__, __imod__, __imul__, __in__, __init__, __ior__, __ipow__, __irshift__, __isub__, __ixor__, __jsUsePyNext__, __jsmod__, __k__, __kwargtrans__, __le__, __lshift__, __lt__, __matmul__, __mergefields__, __mergekwargtrans__, __mod__, __mul__, __ne__, __neg__, __nest__, __or__, __pow__, __pragma__, __pyUseJsNext__, __rshift__, __setitem__, __setproperty__, __setslice__, __sort__, __specialattrib__, __sub__, __super__, __t__, __terminal__, __truediv__, __withblock__, __xor__, abs, all, any, assert, bool, bytearray, bytes, callable, chr, copy, deepcopy, delattr, dict, dir, divmod, enumerate, filter, float, format, getattr, hasattr, input, int, isinstance, issubclass, len, list, map, max, min, object, ord, pow, print, property, py_TypeError, py_iter, py_metatype, py_next, py_reversed, py_typeof, range, repr, round, set, setattr, sorted, str, sum, tuple, zip} from './org.transcrypt.__runtime__.js'; import {RiotTag} from './riot_tag.js'; var __name__ = '__main__'; export var P = __class__ ('P', [RiotTag], { __module__: __name__, debug: 1, lv: [dict ({'name': 'n0'})], counter: 1, template: '

Riot Transcrypt Tag Instance {label}

\n
INNER
', get count_up () {return __get__ (this, function (self) { self.counter = self.counter + 1; self.pp ('counter:', self.counter, 'len lv:', len (self.lv), 'adding one lv'); self.lv.append (dict ({'name': 'n' + self.counter})); return self.counter; });} }); export var Sample2 = __class__ ('Sample2', [P], { __module__: __name__, template: P.template.py_replace ('INNER', '\n
\n
name: {name} - counter: {count_up()}
\n
\n '), style: 'sample2 h5 {color: green}', get __init__ () {return __get__ (this, function (self, tag, opts) { self.label = opts.label.capitalize (); RiotTag.__init__ (self, tag, opts); self.pp ('tag init', 'adding 2 lv'); self.lv.extend ([dict ({'name': 'n1'}), dict ({'name': 'n2'})]); });}, get py_update () {return __get__ (this, function (self) { self.pp ('update handler in the custom tag, calling super'); RiotTag.py_update (self); });} }); //# sourceMappingURL=riot_demo.map}(hhhjA ubah}(h ]h"]h$]h&]h(]source`/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/riot_demo/__target__/riot_demo.jsjqjrjsjt}jvKsuh*j_hh+hKhj0 ubeh}(h ]id22ah"]j{ah$]h&]h(] literal_blockuh*jJhj- ubah}(h ]h"]h$]h&]h(]uh*jhj ubeh}(h ]h"]h$]h&]h(]uh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubeh}(h ]h"]h$]h&]h(]colsKuh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubeh}(h ] example-riotah"]h$] example: riotah&]h(]uh*h hjMhhhh+hKubh )}(hhh](h)}(hLExample: Using input and print in a DOM __terminal__ element in your browserh]hLExample: Using input and print in a DOM __terminal__ element in your browser}(hj hj hhhNhNubah}(h ]h"]h$]h&]h(]uh*hhj hhhh+hKubh>)}(hXmWithout special measures, Transcrypt's *print* function prints to the debugging console. However if there's an element with id *__terminal__* in your DOM tree, the *print* function prints to this element. Moreover, the *input* function also prints its prompt message to the terminal element. Input is collected using a dialog box and echoed to the terminal element.h](h)Without special measures, Transcrypt’s }(h'Without special measures, Transcrypt's hj hhhNhNubh)}(h*print*h]hprint}(hhhj ubah}(h ]h"]h$]h&]h(]uh*hhj ubhS function prints to the debugging console. However if there’s an element with id }(hQ function prints to the debugging console. However if there's an element with id hj hhhNhNubh)}(h*__terminal__*h]h __terminal__}(hhhj ubah}(h ]h"]h$]h&]h(]uh*hhj ubh in your DOM tree, the }(h in your DOM tree, the hj hhhNhNubh)}(h*print*h]hprint}(hhhj ubah}(h ]h"]h$]h&]h(]uh*hhj ubh0 function prints to this element. Moreover, the }(h0 function prints to this element. Moreover, the hj hhhNhNubh)}(h*input*h]hinput}(hhhj ubah}(h ]h"]h$]h&]h(]uh*hhj ubh function also prints its prompt message to the terminal element. Input is collected using a dialog box and echoed to the terminal element.}(h function also prints its prompt message to the terminal element. Input is collected using a dialog box and echoed to the terminal element.hj hhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubh>)}(hThis means that you can write applications with blocking I/O, rather than event driven behaviour, e.g. for simple activities or, since they are intuitively easy to comprehend, for educational purposes.h]hThis means that you can write applications with blocking I/O, rather than event driven behaviour, e.g. for simple activities or, since they are intuitively easy to comprehend, for educational purposes.}(hj hj hhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthKBuh*jhj ubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(hterminal_demo.htmlh]hterminal_demo.html}(hj hj ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hXD Leave input field blank to quit
Refresh browser window to restart
h]hXD Leave input field blank to quit
Refresh browser window to restart
}(hhhj% ubah}(h ]h"]h$]h&]h(]source_/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/terminal_demo/terminal_demo.htmljqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id23ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj ubeh}(h ]h"]h$]h&]h(]colsKuh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK@uh*jhj` ubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(hterminal_demo.pyh]hterminal_demo.py}(hj{ hjy ubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhjv ubj`)}(hXwhile True: name = input ('What''s your name? ') if name == '': break; print ('Hi', name, 'I am your computer.') age = float (input ('How old are you? ')) if age < 18: print ('Sorry', name, ',', age, 'is too young to drive a car in the Netherlands.') else: print ('OK', name, ',', age, 'is old enough to drive a car in the Netherlands.') print () h]hXwhile True: name = input ('What''s your name? ') if name == '': break; print ('Hi', name, 'I am your computer.') age = float (input ('How old are you? ')) if age < 18: print ('Sorry', name, ',', age, 'is too young to drive a car in the Netherlands.') else: print ('OK', name, ',', age, 'is old enough to drive a car in the Netherlands.') print () }(hhhj ubah}(h ]h"]h$]h&]h(]source]/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/terminal_demo/terminal_demo.pyjqjrjsjt}jvKsuh*j_hh+hKhjv ubeh}(h ]id24ah"]j{ah$]h&]h(] literal_blockuh*jJhjs ubah}(h ]h"]h$]h&]h(]uh*jhjp ubah}(h ]h"]h$]h&]h(]uh*jhjm ubah}(h ]h"]h$]h&]h(]uh*jhj` ubeh}(h ]h"]h$]h&]h(]colsKuh*jhj] ubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubeh}(h ]Gexample-using-input-and-print-in-a-dom-terminal-element-in-your-browserah"]h$]Lexample: using input and print in a dom __terminal__ element in your browserah&]h(]uh*h hjMhhhh+hKubh )}(hhh](h)}(hiExample: Using the Parcel.js bundler to package a set of modules written in diverse programming languagesh]hiExample: Using the Parcel.js bundler to package a set of modules written in diverse programming languages}(hj hj hhhNhNubah}(h ]h"]h$]h&]h(]uh*hhj hhhh+hKubh>)}(hXBundlers are increasingly popular in the world of web development. With the Parcel bundler, it is possible to integrate Transcrypt modules with modules written in other languages. Whenever the source code of any module changes, automatic recompilation and repackaging takes place. Sourcemaps are generated for all non-JavaScript modules, enabling source level debugging in the browser.h]hXBundlers are increasingly popular in the world of web development. With the Parcel bundler, it is possible to integrate Transcrypt modules with modules written in other languages. Whenever the source code of any module changes, automatic recompilation and repackaging takes place. Sourcemaps are generated for all non-JavaScript modules, enabling source level debugging in the browser.QB}(hj hj hhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubh>)}(hRIn the example, the top level file of the module hierarchy is the html file below:h]hRIn the example, the top level file of the module hierarchy is the html file below:}(hj hj hhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK@uh*jhj ubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(h index.htmlh]h index.html}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj ubj`)}(hX parcel-plugin-python

Python+Transcrypt Plugin for Parcel Bundler

[ open the console for program output ]

h]hX parcel-plugin-python

Python+Transcrypt Plugin for Parcel Bundler

[ open the console for program output ]

}(hhhjubah}(h ]h"]h$]h&]h(]source]/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/parcel_demo/example/index.htmljqjrjsjt}jvKsuh*j_hh+hKhj ubeh}(h ]id25ah"]j{ah$]h&]h(] literal_blockuh*jJhj ubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhj ubeh}(h ]h"]h$]h&]h(]colsKuh*jhj ubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubh>)}(h8The html file above refers to the JavaScript file below:h]h8The html file above refers to the JavaScript file below:}(hjXhjVhhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK>uh*jhjgubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(hindex.jsh]hindex.js}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhj}ubj`)}(h+import { main } from "./main.py"; main(); h]h+import { main } from "./main.py"; main(); }(hhhjubah}(h ]h"]h$]h&]h(]source[/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/parcel_demo/example/index.jsjqjrjsjt}jvKsuh*j_hh+hKhj}ubeh}(h ]id26ah"]j{ah$]h&]h(] literal_blockuh*jJhjzubah}(h ]h"]h$]h&]h(]uh*jhjwubah}(h ]h"]h$]h&]h(]uh*jhjtubah}(h ]h"]h$]h&]h(]uh*jhjgubeh}(h ]h"]h$]h&]h(]colsKuh*jhjdubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubh>)}(hThis top level JavaScript file in turn refers to a Python file, that makes use of many modules, some written in Python, some in JavaScript:h]hThis top level JavaScript file in turn refers to a Python file, that makes use of many modules, some written in Python, some in JavaScript:}(hjhjhhhNhNubah}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubj)}(hhh]j)}(hhh](j)}(hhh]h}(h ]h"]h$]h&]h(]colwidthK=uh*jhjubj)}(hhh]j)}(hhh]j)}(hhh]jK)}(hhh](jP)}(hmain.pyh]hmain.py}(hjhjubah}(h ]h"]h$]h&]h(]uh*jOhh+hKhjubj`)}(hXLfrom testcontext import Test def main(): '''Main function of the program (called from index.js)''' # sibling module with Test('import sibling') as test: import sibling test.result = sibling.sibling_func(test.random_num) with Test('import sibling as alias_sibling') as test: import sibling as alias_sibling test.result = alias_sibling.sibling_func(test.random_num) with Test('from sibling import sibling_func') as test: from sibling import sibling_func test.result = sibling_func(test.random_num) with Test('from sibling import sibling_func as alias_sibling_func') as test: from sibling import sibling_func as alias_sibling_func test.result = alias_sibling_func(test.random_num) # sibling2 module (using sibling2 because `import * from sibling` would overrride sibling_func above) with Test('from sibling2 import *') as test: from sibling2 import * test.result = sibling2_func(test.random_num) # siblingjs.js (Javascript file import) with Test('import siblingjs') as test: import siblingjs test.result = siblingjs.siblingjs_func(test.random_num) with Test('import siblingjs as alias_siblingjs') as test: import siblingjs as alias_siblingjs test.result = alias_siblingjs.siblingjs_func(test.random_num) with Test('from siblingjs import siblingjs_func') as test: from siblingjs import siblingjs_func test.result = siblingjs_func(test.random_num) with Test('from siblingjs import siblingjs_func as alias_siblingjs_func') as test: from siblingjs import siblingjs_func as alias_siblingjs_func test.result = alias_siblingjs_func(test.random_num) # mymod package (__init__.py file) with Test('import mymod') as test: import mymod test.result = mymod.mymod_func(test.random_num) with Test('import mymod as alias_mymod') as test: import mymod as alias_mymod test.result = alias_mymod.mymod_func(test.random_num) with Test('from mymod import mymod_func') as test: from mymod import mymod_func test.result = mymod_func(test.random_num) with Test('from mymod import mymod_func as alias_mymod_func') as test: from mymod import mymod_func as alias_mymod_func test.result = alias_mymod_func(test.random_num) # mymod.child (subdir module) with Test('import mymod.child') as test: import mymod.child test.result = mymod.child.child_func(test.random_num) with Test('alias_child.child_func') as test: import mymod.child as alias_child test.result = alias_child.child_func(test.random_num) with Test('from mymod.child import child_func') as test: from mymod.child import child_func test.result = child_func(test.random_num) with Test('from mymod.child import child_func as alias_child_func') as test: from mymod.child import child_func as alias_child_func test.result = alias_child_func(test.random_num) with Test('import mymod.grandchildmod') as test: import mymod.grandchildmod test.result = mymod.grandchildmod.grandchildmod_func(test.random_num) with Test('import mymod.grandchildmod as alias_grandchildmod') as test: import mymod.grandchildmod as alias_grandchildmod test.result = alias_grandchildmod.grandchildmod_func(test.random_num) with Test('from mymod.grandchildmod.grandchild import grandchild_func') as test: from mymod.grandchildmod.grandchild import grandchild_func test.result = grandchild_func(test.random_num) with Test('from mymod.grandchildmod.grandchild import grandchild_func as alias_grandchild_func') as test: from mymod.grandchildmod.grandchild import grandchild_func as alias_grandchild_func test.result = alias_grandchild_func(test.random_num) h]hXLfrom testcontext import Test def main(): '''Main function of the program (called from index.js)''' # sibling module with Test('import sibling') as test: import sibling test.result = sibling.sibling_func(test.random_num) with Test('import sibling as alias_sibling') as test: import sibling as alias_sibling test.result = alias_sibling.sibling_func(test.random_num) with Test('from sibling import sibling_func') as test: from sibling import sibling_func test.result = sibling_func(test.random_num) with Test('from sibling import sibling_func as alias_sibling_func') as test: from sibling import sibling_func as alias_sibling_func test.result = alias_sibling_func(test.random_num) # sibling2 module (using sibling2 because `import * from sibling` would overrride sibling_func above) with Test('from sibling2 import *') as test: from sibling2 import * test.result = sibling2_func(test.random_num) # siblingjs.js (Javascript file import) with Test('import siblingjs') as test: import siblingjs test.result = siblingjs.siblingjs_func(test.random_num) with Test('import siblingjs as alias_siblingjs') as test: import siblingjs as alias_siblingjs test.result = alias_siblingjs.siblingjs_func(test.random_num) with Test('from siblingjs import siblingjs_func') as test: from siblingjs import siblingjs_func test.result = siblingjs_func(test.random_num) with Test('from siblingjs import siblingjs_func as alias_siblingjs_func') as test: from siblingjs import siblingjs_func as alias_siblingjs_func test.result = alias_siblingjs_func(test.random_num) # mymod package (__init__.py file) with Test('import mymod') as test: import mymod test.result = mymod.mymod_func(test.random_num) with Test('import mymod as alias_mymod') as test: import mymod as alias_mymod test.result = alias_mymod.mymod_func(test.random_num) with Test('from mymod import mymod_func') as test: from mymod import mymod_func test.result = mymod_func(test.random_num) with Test('from mymod import mymod_func as alias_mymod_func') as test: from mymod import mymod_func as alias_mymod_func test.result = alias_mymod_func(test.random_num) # mymod.child (subdir module) with Test('import mymod.child') as test: import mymod.child test.result = mymod.child.child_func(test.random_num) with Test('alias_child.child_func') as test: import mymod.child as alias_child test.result = alias_child.child_func(test.random_num) with Test('from mymod.child import child_func') as test: from mymod.child import child_func test.result = child_func(test.random_num) with Test('from mymod.child import child_func as alias_child_func') as test: from mymod.child import child_func as alias_child_func test.result = alias_child_func(test.random_num) with Test('import mymod.grandchildmod') as test: import mymod.grandchildmod test.result = mymod.grandchildmod.grandchildmod_func(test.random_num) with Test('import mymod.grandchildmod as alias_grandchildmod') as test: import mymod.grandchildmod as alias_grandchildmod test.result = alias_grandchildmod.grandchildmod_func(test.random_num) with Test('from mymod.grandchildmod.grandchild import grandchild_func') as test: from mymod.grandchildmod.grandchild import grandchild_func test.result = grandchild_func(test.random_num) with Test('from mymod.grandchildmod.grandchild import grandchild_func as alias_grandchild_func') as test: from mymod.grandchildmod.grandchild import grandchild_func as alias_grandchild_func test.result = alias_grandchild_func(test.random_num) }(hhhjubah}(h ]h"]h$]h&]h(]sourceZ/home/jac/active/geatec/transcrypt/Transcrypt/transcrypt/demos/parcel_demo/example/main.pyjqjrjsjt}jvKsuh*j_hh+hKhjubeh}(h ]id27ah"]j{ah$]h&]h(] literal_blockuh*jJhjubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubah}(h ]h"]h$]h&]h(]uh*jhjubeh}(h ]h"]h$]h&]h(]colsKuh*jhjubah}(h ]h"]h$]h&]h(]uh*jhj hhhNhNubh>)}(hXWhenever a source file of this mixed bag of modules is changed, the whole module hierarchy is rebuilt and repackaged. The bundler gets its information from the *.project* file in the *__target__* directory. Consequently Transcrypt can be fully integrated in an automated build process for a project featuring an arbitrary mix of source languages. With this feature, Python has truly become a first class citizen in the browser world.h](hWhenever a source file of this mixed bag of modules is changed, the whole module hierarchy is rebuilt and repackaged. The bundler gets its information from the }(hWhenever a source file of this mixed bag of modules is changed, the whole module hierarchy is rebuilt and repackaged. The bundler gets its information from the hj6hhhNhNubh)}(h *.project*h]h.project}(hhhj?ubah}(h ]h"]h$]h&]h(]uh*hhj6ubh file in the }(h file in the hj6hhhNhNubh)}(h *__target__*h]h __target__}(hhhjRubah}(h ]h"]h$]h&]h(]uh*hhj6ubh directory. Consequently Transcrypt can be fully integrated in an automated build process for a project featuring an arbitrary mix of source languages. With this feature, Python has truly become a first class citizen in the browser world.}(h directory. Consequently Transcrypt can be fully integrated in an automated build process for a project featuring an arbitrary mix of source languages. With this feature, Python has truly become a first class citizen in the browser world.hj6hhhNhNubeh}(h ]h"]h$]h&]h(]uh*h=hh+hKhj hhubeh}(h ]hexample-using-the-parcel-js-bundler-to-package-a-set-of-modules-written-in-diverse-programming-languagesah"]h$]iexample: using the parcel.js bundler to package a set of modules written in diverse programming languagesah&]h(]uh*h hjMhhhh+hKubeh}(h ]mixed-examplesah"]h$]mixed examplesah&]h(]uh*h hhhhhh+hK0ubeh}(h ]h"]h$]h&]h(]sourceh+uh*hcurrent_sourceN current_lineNsettingsdocutils.frontendValues)}(hN generatorN datestampN source_linkN source_urlN toc_backlinksjfootnote_backlinksK sectnum_xformKstrip_commentsNstrip_elements_with_classesN strip_classesN report_levelK halt_levelKexit_status_levelKdebugNwarning_streamN tracebackinput_encoding utf-8-siginput_encoding_error_handlerstrictoutput_encodingutf-8output_encoding_error_handlerjerror_encodingutf-8error_encoding_error_handlerbackslashreplace language_codeenrecord_dependenciesNconfigN id_prefixhauto_id_prefixid dump_settingsNdump_internalsNdump_transformsNdump_pseudo_xmlNexpose_internalsNstrict_visitorN_disable_configN_sourceh+ _destinationN _config_files]pep_referencesN pep_base_url https://www.python.org/dev/peps/pep_file_url_templatepep-%04drfc_referencesN rfc_base_urlhttps://tools.ietf.org/html/ tab_widthKtrim_footnote_reference_spacefile_insertion_enabled raw_enabledKsyntax_highlightlong smart_quotessmartquotes_locales]character_level_inline_markupdoctitle_xform docinfo_xformKsectsubtitle_xformembed_stylesheetcloak_email_addressesenvNubreporterNindirect_targets]substitution_defs}substitution_names}refnames}refids}(j]jaj]j aunameids}(jJjGh}hzhhhejBj?jjjjjxjujBj?jXjj~j{j>jj:j7jj~jZjWj4 j1 j j j~ j{ j j jpjmu nametypes}(jJNh}NhhjBNjjjxNjBNjXj~Nj>j:NjNjZNj4 Nj Nj~ Nj NjpNuh }(jGh hzh,heh_j?hjjjjjujMj?j^jjj{j_jjj7jj~jEjWjj1 j]j j7 j{ j j j jmj jyjLjjj)jjjj5jj;jj$jjWj3j=jjj{jjjjj jj j j j jw jS j j j j j j^ j j j! j jT j0 j8 j j jv j1j jj}jju footnote_refs} citation_refs} autofootnotes]autofootnote_refs]symbol_footnotes]symbol_footnote_refs] footnotes] citations]autofootnote_startKsymbol_footnote_startK id_counter collectionsCounter}jKsRparse_messages]transform_messages](h system_message)}(hhh]h>)}(hhh]h/Hyperlink target "code-pong" is not referenced.}(hhhjubah}(h ]h"]h$]h&]h(]uh*h=hjubah}(h ]h"]h$]h&]h(]levelKtypeINFOsourceh+lineK7uh*jubj)}(hhh]h>)}(hhh]h8Hyperlink target "code-encaps-fabric" is not referenced.}(hhhjubah}(h ]h"]h$]h&]h(]uh*h=hjubah}(h ]h"]h$]h&]h(]levelKtypejsourceh+lineKMuh*jube transformerN decorationNhhub.