Browse files

first commit

  • Loading branch information...
0 parents commit bd0676ba9647c385943e5f505005598811804d8a @mcdonc committed Aug 31, 2012
Showing with 3,313 additions and 0 deletions.
  1. +2 −0 .gitignore
  2. BIN Diagram1.png
  3. BIN as400_sign_on.gif
  4. BIN blastshield.jpg
  5. +1 −0 build.sh
  6. BIN gettingitright.jpg
  7. BIN nocontroller.jpg
  8. BIN nomagic.jpg
  9. BIN omg_wtf.jpg
  10. +690 −0 presentation.rst
  11. +92 −0 rst-directive.py
  12. BIN spellbook.jpg
  13. BIN super-computer-nerd.jpg
  14. BIN throwandcatch.jpg
  15. BIN toomuchchoice.jpg
  16. BIN ui/default/blank.gif
  17. +25 −0 ui/default/framing.css
  18. +42 −0 ui/default/iepngfix.htc
  19. +8 −0 ui/default/opera.css
  20. +16 −0 ui/default/outline.css
  21. +120 −0 ui/default/pretty.css
  22. +24 −0 ui/default/print.css
  23. +11 −0 ui/default/s5-core.css
  24. +10 −0 ui/default/slides.css
  25. +558 −0 ui/default/slides.js
  26. BIN ui/pretty/blank.gif
  27. +25 −0 ui/pretty/framing.css
  28. +42 −0 ui/pretty/iepngfix.htc
  29. +8 −0 ui/pretty/opera.css
  30. +16 −0 ui/pretty/outline.css
  31. +120 −0 ui/pretty/pretty.css
  32. +24 −0 ui/pretty/print.css
  33. +70 −0 ui/pretty/pygments.css
  34. +11 −0 ui/pretty/s5-core.css
  35. +13 −0 ui/pretty/slides.css
  36. +558 −0 ui/pretty/slides.js
  37. BIN ui/pylons/blank.gif
  38. +25 −0 ui/pylons/framing.css
  39. +42 −0 ui/pylons/iepngfix.htc
  40. +8 −0 ui/pylons/opera.css
  41. +16 −0 ui/pylons/outline.css
  42. +133 −0 ui/pylons/pretty.css
  43. +24 −0 ui/pylons/print.css
  44. BIN ui/pylons/pylons-negative-20.png
  45. BIN ui/pylons/pylons-negative-25.png
  46. BIN ui/pylons/pylons-negative-50.png
  47. BIN ui/pylons/pylons-negative.png
  48. BIN ui/pylons/pylons-positive.png
  49. +11 −0 ui/pylons/s5-core.css
  50. +10 −0 ui/pylons/slides.css
  51. +558 −0 ui/pylons/slides.js
  52. BIN urinals.jpg
  53. BIN wiring.jpg
2 .gitignore
@@ -0,0 +1,2 @@
+presentation.html
+*.pyc
BIN Diagram1.png
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN as400_sign_on.gif
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN blastshield.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
1 build.sh
@@ -0,0 +1 @@
+../env27/bin/python rst-directive.py --theme-url=ui/pretty presentation.rst presentation.html
BIN gettingitright.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN nocontroller.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN nomagic.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN omg_wtf.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
690 presentation.rst
@@ -0,0 +1,690 @@
+.. include:: <s5defs.txt>
+
+About Django from A Pyramid Guy
+===============================
+
+:Authors: Chris McDonough, Agendaless Consulting
+:Date: X/X/2012 (DjangoCon 2012)
+
+.. footer:: Chris McDonough, Agendaless Consulting
+
+.. terrified. django is huge part of python community i've been completely
+ isolated from. really don't know many people here. not a django sucks
+ talk, but likely to be slightly critical. don't know whose toes i'll be
+ stepping on. i'm pretty django-ignorant so please correct me in real time
+ when i'm wrong.
+
+Who Am I
+--------
+
+- BBS nerd in the 80s.
+
+.. 1985 on my Amiga. Semi-old-fart.
+
+- Bad Perl hacker until Python. Came to Python via Zope in 1999.
+ Worked at Digital Creations (aka Zope Corporation) until 2003.
+
+.. Caught the programming bug late. Came to Python through Zope so clearly I
+ have no taste. Now help run a consulting shop named Agendaless Consulting
+ in Fredericksburg. Python has been very good to me.
+
+- Primary author of: Pyramid web framework, Supervisor UNIX process control
+ system, Deform form system, Repoze collection of middleware, and other
+ unmentionables. Contributor to Zope, WebOb, and lots of other OSS
+ projects.
+
+Who Am I (Cont'd)
+-----------------
+
+- Quoting Glyph: "I've been doing IRC support for 10 years, so I'm pretty
+ much dead inside."
+
+.. truer words have never been spoken.
+
+.. image:: super-computer-nerd.jpg
+ :align: center
+
+What is a Web Framework
+-----------------------
+
+- A web framework receives a request, calls user code in order to return a
+ response. Everything else is a bonus.
+
+.. my job during this talk is mostly to regurgitate what I know about Django
+ and compare it to my expectations of what a web framework should do and
+ be and how it should do those things.
+
+.. image:: throwandcatch.jpg
+ :align: center
+
+Django Does a Lot Of Things Right
+---------------------------------
+
+- Django gets a lot of things right.
+
+.. presents a surface area of exactly the right size for many people.
+
+- If I had just come to Python, I'd probably be using it.
+
+.. if i had been in a cryogenic freeze for the past 13 years, when I woke up
+ I'd get obsessed with Django instead of getting obsessed with Zope.
+
+.. image:: gettingitright.jpg
+ :align: center
+
+Django Docs Do It Right
+-----------------------
+
+.. primary reason I'd be using it is because of the great docs.
+
+- Django docs broke the Python documentation curve.
+
+.. i devoured zope's "docs" (maillist posts printed out) with great gusto.
+ We're in such a better place today than we were then.
+
+- Great resources for multiple audiences.
+
+.. Django's not just for neckbeards like me, but for Python newbies and
+ people new to web tech. People get excited about this stuff as a result.
+ Adrian and Jacob and Simon did a wonderful job. This is so hard. Has
+ benefitted the Python community by raising people's docs expectations.
+
+.. image:: spellbook.jpg
+ :align: center
+
+Django Defaults Do It Right
+---------------------------
+
+- Django provides people with unambiguous ways to solve 80% of their web
+ development problems.
+
+.. Reducing the number of choices that people need to make by making sane
+ ones for them lets people get started quickly. Doesn't really reinvent
+ stuff: uses a relational database. Simple model for mapping URLs to code.
+ People can quickly get a mental model about how they might map their
+ requirements to it.
+
+- Doesn't prevent specialization or use of external libraries.
+
+.. No through the web code or weird sandboxing or weird execution model.
+
+Django Views Do It Right
+------------------------
+
+.. view functions have a simple model... passed a request, return a response.
+ Quibbles about how templating and dispatching is handled, but for the most
+ part it's workable. Benchmarks: surprised at how well Django does.
+
+- No magical globals or threadlocals.
+
+- Django view lookup and execution is very fast.
+
+.. image:: nomagic.jpg
+ :align: center
+
+Django Forms Do It Right
+------------------------
+
+.. Normal forms can be completely custom, help with validation. When you
+ need to just generate some CRUD stuff and you're less concerned about how
+ it looks and behaves, you can use modelforms.
+
+- Decoupling of models from forms.
+
+- Optional recoupling via modelforms.
+
+.. image:: as400_sign_on.gif
+ :align: center
+
+Django Extensibility Does It Right
+----------------------------------
+
+.. Thriving third-party plugin environment. Major quibbles about
+ extensibility, but people make this part of Django work for them.
+
+- Replaceable backends for authentication.
+
+- Replaceable backends for storage.
+
+- Encourages an environment of plugins at different levels.
+
+Django Terminology Does It Right
+--------------------------------
+
+.. no idea who first came up with the idea that request/response web
+ frameworks have anything to do with the MVC pattern defined via smalltalk
+ in the 1980s. Arguments about which web frameworks are "more MVC" than
+ others hilarious, completely miss the point. Django authors were smart
+ enough to know how crazy that was.
+
+- Arguments about how a web framework implements "MVC" are usually
+ distractions.
+
+- Views and models. No "controller".
+
+.. Pyramid uses the same terminology as Django. Zope happens to as well.
+
+.. image:: nocontroller.jpg
+ :align: center
+
+
+Django Reality Does It Right
+----------------------------
+
+.. scores of important web sites running Django. Very popular *and* it
+ works.
+
+- Can't argue with success.
+
+- Scores of very successful sites built using Django.
+
+So WTF?
+-------
+
+- Why maintain a different framework if Django is so awesome?
+
+.. remember those quibbles? I have problems with Django on a number of axes
+ that, if I didn't know better, I'd believe were almost entirely personal.
+ They really don't make much difference to folks just getting started with
+ web programming or just getting started with Python. The more you know,
+ the less satisfied you are; ignorance would be bliss. Remember I started
+ with Zope so it proves I had almost no taste. But you get pickier as time
+ goes on; you recontextualize features in the light of new knowledge and
+ things your framework did for you that you thought were so great at the
+ start sometimes start to look like liabilities. You might be able to get
+ things done more quickly if it did a little less, and what remained it did
+ better. E.g. you might not want to use a relational database, or you
+ might want to use a different templating system, or you might want to do
+ security differently, or you might not need the overhead of some
+ middleware, or you might not want to pay the price of the ORM, or you want
+ better configuration and extensibility, or whatever. Familiarity breeds
+ contempt.
+
+.. image:: omg_wtf.jpg
+ :align: center
+
+What is Pyramid
+---------------
+
+- James Bennett's PyCon 2012 "Django In Depth" tutorial: ~20 minutes out of 3
+ hours devoted to things that Pyramid actually does: low-level template API,
+ view lookup and execution, HTTP responses, middleware.
+
+- Pyramid is a corner of a corner of Django, magnified. It handles view
+ lookup and execution and provides related convenience APIs.
+
+What Is Pyramid (Cont'd)
+------------------------
+
+- Pyramid is independent of any particular peristence system. It has no
+ built-in form generation system. It does not prefer any particular
+ templating system. It does not ship with an admininstrative application.
+
+- Something like Pyramid could be used to build something like Django.
+
+How does Pyramid Relate to Pylons
+---------------------------------
+
+.. image:: Diagram1.png
+ :align: center
+
+Might As Well Be
+----------------
+
+.. image:: wiring.jpg
+ :align: center
+
+Pylons Project
+--------------
+
+- Project lead consolidation decision.
+
+- Attempt to get Pylons, TurboGears and ``repoze.bfg`` communities rowing in
+ the same direction.
+
+- Pylons 1.x web framework shifted into “legacy” status. Maintained
+ indefinitely.
+
+- New development: Pyramid and related.
+
+- Turbogears has gone their own direction.
+
+Is Pyramid a Microframework?
+----------------------------
+
+- Pyramid is sort of microframework-like. You can write a Pyramid
+ application in a single file.
+
+- Self-identifying microframeworks tend to suggest application development
+ patterns to its users which promote convenience over explicitness. Pyramid
+ for better or worse does not do this, because it needs to be useful in
+ larger systems where these patterns can lead to extensibility problems.
+
+- In reality, "microframework" is a marketing term, not a technical term, so
+ it kinda doesn't matter.
+
+Small Pyramid Program
+----------------------
+
+.. sourcecode:: python
+
+ from wsgiref.simple_server import make_server
+ from pyramid.config import Configurator
+ from pyramid.response import Response
+
+ def hello_world(request):
+ return Response('Hello %(name)s!' % request.matchdict)
+
+ if __name__ == '__main__':
+ config = Configurator()
+ config.add_route('hello', '/hello/{name}')
+ config.add_view(hello_world, route_name='hello')
+ app = config.make_wsgi_app()
+ server = make_server('0.0.0.0', 8080, app)
+ server.serve_forever()
+
+.. Django application is never going to be this small. Seen people post blog
+ entries about how you can use Django like this, but it's always just kinda
+ unsat. This is great for bug reproduction. It's also good for very tiny
+ applications, but I very rarely write those.
+
+Larger Pyramid Systems
+----------------------
+
+- Most people use "scaffolds" to generate multifile projects.
+
+- Scaffolds generate code that can generate a Python *distribution*
+ (something you can credibly upload to PyPI).
+
+Pyramid and Python 3
+--------------------
+
+- Pyramid's current release (1.3) supports Python 3.2+ (as well as Python 2.6
+ and 2.7).
+
+- Most existing add-ons already ported. When feasible, we port add-on
+ dependencies (``beaker``, ``WebOb``, ``zope.*`` packages).
+
+- We have a committment to Python 3. It involves lots of whining and
+ bitching.
+
+
+I'm No Genius
+-------------
+
+- Pyramid does things wrong. Many parts of Pyramid make me cringe.
+ https://github.com/Pylons/pyramid/wiki/Mistakes
+
+- The grass is always greener.
+
+.. image:: urinals.jpg
+ :align: center
+
+
+Pyramid Docs
+------------
+
+- Culture of documentation (if it's not documented, it's broken).
+
+- Pyramid itself has ~800 printed pages of narrative and API documentation,
+ plus a few hundred pages of "cookbook" material.
+
+- Comprehensive but pretty dry.
+
+Docs Pain
+---------
+
+- Many pain points are related to plain old bad docs: our fault. Docs are at
+ least 10X harder to write well than the associated code and take much
+ longer. Most coders hate writing docs. I write lots of documentation but
+ it's often not very good.
+
+- But other pain points people experience when trying to learn Pyramid from
+ its docs is due to poorly documented dependencies (setuptools). We need to
+ redocument subsystems "in context", for better or worse. (kill me now?)
+
+Docs Pain (cont'd)
+------------------
+
+- Some pain points are due to an audience mismatch; narrative documentation
+ assumes people know "Python" *and* "the web". They often need remedial
+ help in one or both, which the docs don't provide.
+
+- "Chipin" project raised ~$5K for documentation overhaul.
+
+Pyramid Friends
+---------------
+
+- Colander/Deform: form handling.
+
+- SQLAlchemy: SQL database connectivity and querying.
+
+- Pyramid-specific add-ons like ``pyramid_mailer``, ``pyramid_zodbconn``,
+ ``pyramid_socketio``, ``pyramid_mongodb``, and so forth.
+
+- The typical Pyramid application makes use of some combination of add-ons.
+
+Scaffolding
+-----------
+
+- A scaffold renders a project. A project is installable like any other
+ setuptools distribution (it has a ``setup.py``, etc).
+
+- The project depends on some combination of Pyramid, Pyramid plugins, and
+ other third-party libraries and frameworks.
+
+- ``zodb``, ``alchemy`` and ``starter`` scaffolds provided by Pyramid itself.
+ Others are contributed to PyPI by third parties.
+
+Bindings Packages
+-----------------
+
+A more generic package is specialized for convenient use under Pyramid via
+use of a bindings package.
+
+- ``deform`` + ``pyramid_deform``.
+
+- ``repoze.who`` + ``pyramid_who``.
+
+- 2X documentation burden: document once in general package docs, document
+ again in bindings docs. That's no fun.
+
+- But this will happen anyway if your code is popular (Celery).
+
+Higher Level Frameworks
+-----------------------
+
+- ``ptah``
+
+- ``kotti``
+
+- ``poolyx``
+
+- ``substanced``
+
+Packaging Is Like a Blast Shield
+--------------------------------
+
+- A blast shield helps keep shrapnel out.
+
+- It can also help keep shrapnel *in*.
+
+.. image:: blastshield.jpg
+ :align: center
+
+Packaging / Blast Shield (Cont'd)
+---------------------------------
+
+- Shrapnel tends to penetrate anything not within a blast shield.
+
+- Every piece of software eventually blows up.
+
+- The more blast shields you have, the more the damage is contained.
+
+Packaging / Blast Shield (Cont'd)
+---------------------------------
+
+- But blast shields obscure the landscape. More work required for users.
+
+- More packages add more documentation and conceptual overhead, and more
+ unwanted choice.
+
+.. image:: toomuchchoice.jpg
+ :align: center
+
+Django Avoids Setuptools
+------------------------
+
+- Setup.py develop of django doesn't work.
+
+- Avoidance of setuptools also prevents use of console scripts
+ (e.g. django-admin).
+
+- Django recreates some of the patterns that setuptools provides (i.e. test
+ discovery hooks).
+
+- Developers whom are ignorant of distribution issues are very confused when
+ inevitably faced with them.
+
+Django Avoids Setuptools (2)
+----------------------------
+
+- Django's defacto avoidance of setuptools is understandable. But it's not
+ helping to improve Python packaging. Python packaging and distribution
+ needs you very badly.
+
+- Fewer documentation issues to cope with, but contributing to docs for
+ setuptools would float all boats.
+
+Subclassing Is Convenient
+-------------------------
+
+- You don't have to explain a protocol (the protocol is Python).
+
+- But offering extensibility via subclassing is often a poorer choice than
+ offering extensibility via composition and very explicit interfaces.
+
+Subclassing Is Convenient (Cont'd)
+----------------------------------
+
+- Why? People begin depending upon the implementation details of the classes
+ you tell them to subclass. Unless you're extremely clear about what the
+ API of the superclass is, and the social contract to use nothing else but
+ the documented API exists, you'll be pressured into making retroactive
+ APIs. Impossible to recover from without breaking b/w compat.
+
+- Not uncommon to see a subclass of a subclass of a subclass of a subclass;
+ figuting out how the thing works can be an exercise in pain and multiple
+ editor windows.
+
+Globals are Convenient
+----------------------
+
+- You don't have to explain a protocol for obtaining a value (the protocol is
+ ``import``).
+
+- But the development of circular imports is inevitable.
+
+- Global registries make it impossible to embed more than one application
+ into the same Python process.
+
+Module-Scope Work Is Convenient
+-------------------------------
+
+From Django tutorial, at module scope:
+
+.. sourcecode:: python
+
+ from django.contrib import admin
+ admin.autodiscover()
+
+Module-Scope Work Is Convenient (2)
+-----------------------------------
+
+- These things can be done at module scope without concern:
+
+ * An import of another module or global.
+
+ * Assignment of a variable name in the module to some constant value.
+
+ * The addition of a function via a def statement.
+
+ * The addition of a class via a class statement.
+
+ * Control flow which may handles conditionals for platform-specific
+ handling or failure handling of the above.
+
+Module Scope Work Is Convenient (3)
+-----------------------------------
+
+- Everything else is at least suspect. Test runners and other code scanners
+ can import with abandon, and side effects are often undesirable.
+
+Pluggable Apps / Reusable Apps
+------------------------------
+
+- Pluggable apps probably aren't really that pluggable, reusable apps
+ probably aren't as reusable as you might like.
+
+- IMO, even a framework as high-level as Django can't really offer such a
+ feature without stretching the truth just a little bit.
+
+- The only thing that can truly offer pluggable apps: another app. No
+ general-purpose framework can do a great job here. (Examples: Wordpress,
+ Jenkins, Plone).
+
+Rendering Is Meta-View
+----------------------
+
+- ``render_to_response`` using template in view is no fun to test.
+
+- Returning a dict from a view callable is more fun to test.
+
+Unit Tests
+----------
+
+- Exclusive use of Django test client for tests will cause test suite to run
+ more slowly than necessary.
+
+- A slow enough test suite won't be run before commit.
+
+- Testers who don't understand any type of testing other than "system" or
+ "integration" testing tend to bring poor testing practices to unrelated
+ systems.
+
+- Using setuptools provides nice hooks for test discovery and execution.
+
+Static Files
+------------
+
+- Python WSGI servers are getting better at serving static files.
+ E.g. Gunicorn supports ``sendfile`` on UNIX.
+
+- Might be time to reconsider offloading media to a dedicated non-Python
+ server and make use of what's available in WSGI-land.
+
+Community
+---------
+
+- Pyramid community is maybe 5%-10% the size of the Django community.
+
+- It's growing.
+
+- Your success is our success. I'd be very pleased to have Pyramid be
+ considered the #2 Python web framework (at least for "Python people")
+ forever.
+
+Collaboration (Low-Level)
+-------------------------
+
+- Create adapter for WebOb or Werkzeug that implements the Django request
+ API?
+
+- Create an adapter for SQLAlchemy that implements the Django ORM API?
+
+Collaboration (Low-Level)
+-------------------------
+
+- These are likely losers. They are "30 year plans". Things change so fast.
+ Who will pay immediately? Who will benefit immediately?
+
+- Might be better to try to use common non-domain-specific dependencies
+ (e.g. setuptools, virtualenv, WSGI middleware, etc). It would be a great
+ win to share documentation burden, even if we had to "fork" it for our
+ own contextual requirements.
+
+Collaboration (High-Level)
+--------------------------
+
+- Django is limited by backwards compatibility concerns. It's impractical to
+ make large architectural changes now. Your users would kill you.
+
+- But I could imagine somebody from the Django community creating a
+ "Django-NG" or a Django-like system from whole cloth. Or break Django
+ apart into something that isn't quite bw compatible.
+
+Collaboration (High-Level)
+--------------------------
+
+- It might make sense to consider Pyramid or another smaller framework as a
+ base for such an effort. If you used Pyramid, you'd get URL routing,
+ internationalization, template bindings, configuration extensibility,
+ flexible view lookup and execution, an event system, security,
+ documentation, Python 3 compatibility, and other things.
+
+- Pyramid community is very enthusiastic, friendly, helpful, and experienced.
+
+Promoting Python
+----------------
+
+- I challenge you to not be complacent.
+
+- I challenge you to investigate how other frameworks work.
+
+- I challenge you to embrace existing Python packaging and distribution
+ tools.
+
+Promoting Python
+-----------------
+
+- I challenge you to finish Python 3 porting quickly. Commit to supporting
+ it in your add-ons and helping folks who have existing add-ons port.
+
+- I challenge you to speak out when folks bash competitors. Haters are
+ everywhere, and when someone bashes Pyramid, Flask, Bottle, or Zope, and
+ nobody defends against it, the hate will eventually come back to harm you.
+
+Unknowns
+--------
+
+- Django Class-Based Views Might Not Do It Right. ``as_view``. Hmm. All
+ views in Pyramid are potentially generic. They have a context passed to
+ them. Class-based views in Pyramid are not things handed down from "good
+ devs" to reuse, they're just normal things.
+
+- How does Django allow for configuration extensibility? Conflict detection?
+
+- Event system
+
+- Alternate templating languages
+
+- Exception views
+
+- View predicates
+
+- Transaction management
+
+Images
+------
+
+Super Simple Throw and Catch: http://www.abdopub.com/shop/pc/configurePrd.asp?idproduct=29321
+
+Spellbook: http://alteredroute.blogspot.com/2008/10/potions-and-spells.html
+
+Computer nerd: http://noscope.com/photostream/various/super-computer-nerd.jpg/view
+
+Getting it right: http://sluggerotoole.com/2011/03/29/looking-back-at-the-dups-2007-manifesto/dup-getting-it-right-logo/
+
+Images (Cont'd)
+---------------
+
+Urinals: http://www.businessblunder.com/2011/01/bad-architecture-examples/
+
+No controller: http://www.pwnordie.com/2009/12/30/2009-gaming-in-retrospect/project_natal_no_controller/
+
+No magic: http://gordonscruton.blogspot.com/2011/06/no-magic-please-part-1-learning.html
+
+Images (Cont'd)
+---------------
+
+AS/400 Sign On: http://forums.speedguide.net/showthread.php?229405-AS400-question
+
+OMG WTF: http://www.graphicshunt.com/funny/images/omg_wtf-12875.htm
+
+Wiring: http://www.advrider.com/forums/showthread.php?t=415263&page=9
+
+
+Images (Cont'd)
+---------------
+
+Mustard aisle: http://dangerousintersection.org/2008/02/18/experiencing-the-paradox-of-choice-at-the-local-schnucks-grocery-store/
92 rst-directive.py
@@ -0,0 +1,92 @@
+# -*- coding: utf-8 -*-
+"""
+ The Pygments reStructuredText directive
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+ This fragment is a Docutils_ 0.5 directive that renders source code
+ (to HTML only, currently) via Pygments.
+
+ To use it, adjust the options below and copy the code into a module
+ that you import on initialization. The code then automatically
+ registers a ``sourcecode`` directive that you can use instead of
+ normal code blocks like this::
+
+ .. sourcecode:: python
+
+ My code goes here.
+
+ If you want to have different code styles, e.g. one with line numbers
+ and one without, add formatters with their names in the VARIANTS dict
+ below. You can invoke them instead of the DEFAULT one by using a
+ directive option::
+
+ .. sourcecode:: python
+ :linenos:
+
+ My code goes here.
+
+ Look at the `directive documentation`_ to get all the gory details.
+
+ .. _Docutils: http://docutils.sf.net/
+ .. _directive documentation:
+ http://docutils.sourceforge.net/docs/howto/rst-directives.html
+
+ :copyright: Copyright 2006-2009 by the Pygments team, see AUTHORS.
+ :license: BSD, see LICENSE for details.
+"""
+
+# Options
+# ~~~~~~~
+
+# Set to True if you want inline CSS styles instead of classes
+INLINESTYLES = False
+STYLE = "fruity"
+
+from pygments.formatters import HtmlFormatter
+
+# The default formatter
+DEFAULT = HtmlFormatter(noclasses=INLINESTYLES, style=STYLE)
+
+# Add name -> formatter pairs for every variant you want to use
+VARIANTS = {
+ # 'linenos': HtmlFormatter(noclasses=INLINESTYLES, linenos=True),
+}
+
+
+from docutils import nodes
+from docutils.parsers.rst import directives, Directive
+
+from pygments import highlight
+from pygments.lexers import get_lexer_by_name, TextLexer
+
+class Pygments(Directive):
+ """ Source code syntax hightlighting.
+ """
+ required_arguments = 1
+ optional_arguments = 0
+ final_argument_whitespace = True
+ option_spec = dict([(key, directives.flag) for key in VARIANTS])
+ has_content = True
+
+ def run(self):
+ self.assert_has_content()
+ try:
+ lexer = get_lexer_by_name(self.arguments[0])
+ except ValueError:
+ # no lexer found - use the text one instead of an exception
+ lexer = TextLexer()
+ # take an arbitrary option if more than one is given
+ formatter = self.options and VARIANTS[self.options.keys()[0]] or DEFAULT
+
+ #print >>open('pygments.css', 'w'), formatter.get_style_defs('.highlight')
+ parsed = highlight(u'\n'.join(self.content), lexer, formatter)
+ return [nodes.raw('', parsed, format='html')]
+
+directives.register_directive('sourcecode', Pygments)
+
+from docutils.core import publish_cmdline, default_description
+
+description = ('Generates S5 (X)HTML slideshow documents from standalone '
+ 'reStructuredText sources. ' + default_description)
+
+publish_cmdline(writer_name='s5', description=description)
BIN spellbook.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN super-computer-nerd.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN throwandcatch.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN toomuchchoice.jpg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
BIN ui/default/blank.gif
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
25 ui/default/framing.css
@@ -0,0 +1,25 @@
+/* This file has been placed in the public domain. */
+/* The following styles size, place, and layer the slide components.
+ Edit these if you want to change the overall slide layout.
+ The commented lines can be uncommented (and modified, if necessary)
+ to help you with the rearrangement process. */
+
+/* target = 1024x768 */
+
+div#header, div#footer, .slide {width: 100%; top: 0; left: 0;}
+div#header {position: fixed; top: 0; height: 3em; z-index: 1;}
+div#footer {top: auto; bottom: 0; height: 2.5em; z-index: 5;}
+.slide {top: 0; width: 92%; padding: 2.5em 4% 4%; z-index: 2;}
+div#controls {left: 50%; bottom: 0; width: 50%; z-index: 100;}
+div#controls form {position: absolute; bottom: 0; right: 0; width: 100%;
+ margin: 0;}
+#currentSlide {position: absolute; width: 10%; left: 45%; bottom: 1em;
+ z-index: 10;}
+html>body #currentSlide {position: fixed;}
+
+/*
+div#header {background: #FCC;}
+div#footer {background: #CCF;}
+div#controls {background: #BBD;}
+div#currentSlide {background: #FFC;}
+*/
42 ui/default/iepngfix.htc
@@ -0,0 +1,42 @@
+<public:component>
+<public:attach event="onpropertychange" onevent="doFix()" />
+
+<script>
+
+// IE5.5+ PNG Alpha Fix v1.0 by Angus Turnbull http://www.twinhelix.com
+// Free usage permitted as long as this notice remains intact.
+
+// This must be a path to a blank image. That's all the configuration you need here.
+var blankImg = 'ui/default/blank.gif';
+
+var f = 'DXImageTransform.Microsoft.AlphaImageLoader';
+
+function filt(s, m) {
+ if (filters[f]) {
+ filters[f].enabled = s ? true : false;
+ if (s) with (filters[f]) { src = s; sizingMethod = m }
+ } else if (s) style.filter = 'progid:'+f+'(src="'+s+'",sizingMethod="'+m+'")';
+}
+
+function doFix() {
+ if ((parseFloat(navigator.userAgent.match(/MSIE (\S+)/)[1]) < 5.5) ||
+ (event && !/(background|src)/.test(event.propertyName))) return;
+
+ if (tagName == 'IMG') {
+ if ((/\.png$/i).test(src)) {
+ filt(src, 'image'); // was 'scale'
+ src = blankImg;
+ } else if (src.indexOf(blankImg) < 0) filt();
+ } else if (style.backgroundImage) {
+ if (style.backgroundImage.match(/^url[("']+(.*\.png)[)"']+$/i)) {
+ var s = RegExp.$1;
+ style.backgroundImage = '';
+ filt(s, 'crop');
+ } else filt();
+ }
+}
+
+doFix();
+
+</script>
+</public:component>
8 ui/default/opera.css
@@ -0,0 +1,8 @@
+/* This file has been placed in the public domain. */
+/* DO NOT CHANGE THESE unless you really want to break Opera Show */
+.slide {
+ visibility: visible !important;
+ position: static !important;
+ page-break-before: always;
+}
+#slide0 {page-break-before: avoid;}
16 ui/default/outline.css
@@ -0,0 +1,16 @@
+/* This file has been placed in the public domain. */
+/* Don't change this unless you want the layout stuff to show up in the
+ outline view! */
+
+.layout div, #footer *, #controlForm * {display: none;}
+#footer, #controls, #controlForm, #navLinks, #toggle {
+ display: block; visibility: visible; margin: 0; padding: 0;}
+#toggle {float: right; padding: 0.5em;}
+html>body #toggle {position: fixed; top: 0; right: 0;}
+
+/* making the outline look pretty-ish */
+
+#slide0 h1, #slide0 h2, #slide0 h3, #slide0 h4 {border: none; margin: 0;}
+#toggle {border: 1px solid; border-width: 0 0 1px 1px; background: #FFF;}
+
+.outline {display: inline ! important;}
120 ui/default/pretty.css
@@ -0,0 +1,120 @@
+/* This file has been placed in the public domain. */
+/* Following are the presentation styles -- edit away! */
+
+html, body {margin: 0; padding: 0;}
+body {background: white; color: black;}
+/* Replace the background style above with the style below (and again for
+ div#header) for a graphic: */
+/* background: white url(bodybg.gif) -16px 0 no-repeat; */
+:link, :visited {text-decoration: none; color: #00C;}
+#controls :active {color: #88A !important;}
+#controls :focus {outline: 1px dotted #227;}
+h1, h2, h3, h4 {font-size: 100%; margin: 0; padding: 0; font-weight: inherit;}
+
+blockquote {padding: 0 2em 0.5em; margin: 0 1.5em 0.5em;}
+blockquote p {margin: 0;}
+
+kbd {font-weight: bold; font-size: 1em;}
+sup {font-size: smaller; line-height: 1px;}
+
+.slide pre {padding: 0; margin-left: 0; margin-right: 0; font-size: 90%;}
+.slide ul ul li {list-style: square;}
+.slide img.leader {display: block; margin: 0 auto;}
+.slide tt {font-size: 90%;}
+
+div#header, div#footer {background: #005; color: #AAB; font-family: sans-serif;}
+/* background: #005 url(bodybg.gif) -16px 0 no-repeat; */
+div#footer {font-size: 0.5em; font-weight: bold; padding: 1em 0;}
+#footer h1 {display: block; padding: 0 1em;}
+#footer h2 {display: block; padding: 0.8em 1em 0;}
+
+.slide {font-size: 1.2em;}
+.slide h1 {position: absolute; top: 0.45em; z-index: 1;
+ margin: 0; padding-left: 0.7em; white-space: nowrap;
+ font: bold 150% sans-serif; color: #DDE; background: #005;}
+.slide h2 {font: bold 120%/1em sans-serif; padding-top: 0.5em;}
+.slide h3 {font: bold 100% sans-serif; padding-top: 0.5em;}
+h1 abbr {font-variant: small-caps;}
+
+div#controls {position: absolute; left: 50%; bottom: 0;
+ width: 50%; text-align: right; font: bold 0.9em sans-serif;}
+html>body div#controls {position: fixed; padding: 0 0 1em 0; top: auto;}
+div#controls form {position: absolute; bottom: 0; right: 0; width: 100%;
+ margin: 0; padding: 0;}
+#controls #navLinks a {padding: 0; margin: 0 0.5em;
+ background: #005; border: none; color: #779; cursor: pointer;}
+#controls #navList {height: 1em;}
+#controls #navList #jumplist {position: absolute; bottom: 0; right: 0;
+ background: #DDD; color: #227;}
+
+#currentSlide {text-align: center; font-size: 0.5em; color: #449;
+ font-family: sans-serif; font-weight: bold;}
+
+#slide0 {padding-top: 1.5em}
+#slide0 h1 {position: static; margin: 1em 0 0; padding: 0; color: #000;
+ font: bold 2em sans-serif; white-space: normal; background: transparent;}
+#slide0 h2 {font: bold italic 1em sans-serif; margin: 0.25em;}
+#slide0 h3 {margin-top: 1.5em; font-size: 1.5em;}
+#slide0 h4 {margin-top: 0; font-size: 1em;}
+
+ul.urls {list-style: none; display: inline; margin: 0;}
+.urls li {display: inline; margin: 0;}
+.external {border-bottom: 1px dotted gray;}
+html>body .external {border-bottom: none;}
+.external:after {content: " \274F"; font-size: smaller; color: #77B;}
+
+.incremental, .incremental *, .incremental *:after {visibility: visible;
+ color: white; border: 0;}
+img.incremental {visibility: hidden;}
+.slide .current {color: green;}
+
+.slide-display {display: inline ! important;}
+
+.huge {font-family: sans-serif; font-weight: bold; font-size: 150%;}
+.big {font-family: sans-serif; font-weight: bold; font-size: 120%;}
+.small {font-size: 75%;}
+.tiny {font-size: 50%;}
+.huge tt, .big tt, .small tt, .tiny tt {font-size: 115%;}
+.huge pre, .big pre, .small pre, .tiny pre {font-size: 115%;}
+
+.maroon {color: maroon;}
+.red {color: red;}
+.magenta {color: magenta;}
+.fuchsia {color: fuchsia;}
+.pink {color: #FAA;}
+.orange {color: orange;}
+.yellow {color: yellow;}
+.lime {color: lime;}
+.green {color: green;}
+.olive {color: olive;}
+.teal {color: teal;}
+.cyan {color: cyan;}
+.aqua {color: aqua;}
+.blue {color: blue;}
+.navy {color: navy;}
+.purple {color: purple;}
+.black {color: black;}
+.gray {color: gray;}
+.silver {color: silver;}
+.white {color: white;}
+
+.left {text-align: left ! important;}
+.center {text-align: center ! important;}
+.right {text-align: right ! important;}
+
+.animation {position: relative; margin: 1em 0; padding: 0;}
+.animation img {position: absolute;}
+
+/* Docutils-specific overrides */
+
+.slide table.docinfo {margin: 1em 0 0.5em 2em;}
+
+pre.literal-block, pre.doctest-block {background-color: white;}
+
+tt.docutils {background-color: white;}
+
+/* diagnostics */
+/*
+li:after {content: " [" attr(class) "]"; color: #F88;}
+div:before {content: "[" attr(class) "]"; color: #F88;}
+*/
24 ui/default/print.css
@@ -0,0 +1,24 @@
+/* This file has been placed in the public domain. */
+/* The following rule is necessary to have all slides appear in print!
+ DO NOT REMOVE IT! */
+.slide, ul {page-break-inside: avoid; visibility: visible !important;}
+h1 {page-break-after: avoid;}
+
+body {font-size: 12pt; background: white;}
+* {color: black;}
+
+#slide0 h1 {font-size: 200%; border: none; margin: 0.5em 0 0.25em;}
+#slide0 h3 {margin: 0; padding: 0;}
+#slide0 h4 {margin: 0 0 0.5em; padding: 0;}
+#slide0 {margin-bottom: 3em;}
+
+#header {display: none;}
+#footer h1 {margin: 0; border-bottom: 1px solid; color: gray;
+ font-style: italic;}
+#footer h2, #controls {display: none;}
+
+.print {display: inline ! important;}
+
+/* The following rule keeps the layout stuff out of print.
+ Remove at your own risk! */
+.layout, .layout * {display: none !important;}
11 ui/default/s5-core.css
@@ -0,0 +1,11 @@
+/* This file has been placed in the public domain. */
+/* Do not edit or override these styles!
+ The system will likely break if you do. */
+
+div#header, div#footer, div#controls, .slide {position: absolute;}
+html>body div#header, html>body div#footer,
+ html>body div#controls, html>body .slide {position: fixed;}
+.handout {display: none;}
+.layout {display: block;}
+.slide, .hideme, .incremental {visibility: hidden;}
+#slide0 {visibility: visible;}
10 ui/default/slides.css
@@ -0,0 +1,10 @@
+/* This file has been placed in the public domain. */
+
+/* required to make the slide show run at all */
+@import url(s5-core.css);
+
+/* sets basic placement and size of slide components */
+@import url(framing.css);
+
+/* styles that make the slides look good */
+@import url(pretty.css);
558 ui/default/slides.js
@@ -0,0 +1,558 @@
+// S5 v1.1 slides.js -- released into the Public Domain
+// Modified for Docutils (http://docutils.sf.net) by David Goodger
+//
+// Please see http://www.meyerweb.com/eric/tools/s5/credits.html for
+// information about all the wonderful and talented contributors to this code!
+
+var undef;
+var slideCSS = '';
+var snum = 0;
+var smax = 1;
+var slideIDs = new Array();
+var incpos = 0;
+var number = undef;
+var s5mode = true;
+var defaultView = 'slideshow';
+var controlVis = 'visible';
+
+var isIE = navigator.appName == 'Microsoft Internet Explorer' ? 1 : 0;
+var isOp = navigator.userAgent.indexOf('Opera') > -1 ? 1 : 0;
+var isGe = navigator.userAgent.indexOf('Gecko') > -1 && navigator.userAgent.indexOf('Safari') < 1 ? 1 : 0;
+
+function hasClass(object, className) {
+ if (!object.className) return false;
+ return (object.className.search('(^|\\s)' + className + '(\\s|$)') != -1);
+}
+
+function hasValue(object, value) {
+ if (!object) return false;
+ return (object.search('(^|\\s)' + value + '(\\s|$)') != -1);
+}
+
+function removeClass(object,className) {
+ if (!object) return;
+ object.className = object.className.replace(new RegExp('(^|\\s)'+className+'(\\s|$)'), RegExp.$1+RegExp.$2);
+}
+
+function addClass(object,className) {
+ if (!object || hasClass(object, className)) return;
+ if (object.className) {
+ object.className += ' '+className;
+ } else {
+ object.className = className;
+ }
+}
+
+function GetElementsWithClassName(elementName,className) {
+ var allElements = document.getElementsByTagName(elementName);
+ var elemColl = new Array();
+ for (var i = 0; i< allElements.length; i++) {
+ if (hasClass(allElements[i], className)) {
+ elemColl[elemColl.length] = allElements[i];
+ }
+ }
+ return elemColl;
+}
+
+function isParentOrSelf(element, id) {
+ if (element == null || element.nodeName=='BODY') return false;
+ else if (element.id == id) return true;
+ else return isParentOrSelf(element.parentNode, id);
+}
+
+function nodeValue(node) {
+ var result = "";
+ if (node.nodeType == 1) {
+ var children = node.childNodes;
+ for (var i = 0; i < children.length; ++i) {
+ result += nodeValue(children[i]);
+ }
+ }
+ else if (node.nodeType == 3) {
+ result = node.nodeValue;
+ }
+ return(result);
+}
+
+function slideLabel() {
+ var slideColl = GetElementsWithClassName('*','slide');
+ var list = document.getElementById('jumplist');
+ smax = slideColl.length;
+ for (var n = 0; n < smax; n++) {
+ var obj = slideColl[n];
+
+ var did = 'slide' + n.toString();
+ if (obj.getAttribute('id')) {
+ slideIDs[n] = obj.getAttribute('id');
+ }
+ else {
+ obj.setAttribute('id',did);
+ slideIDs[n] = did;
+ }
+ if (isOp) continue;
+
+ var otext = '';
+ var menu = obj.firstChild;
+ if (!menu) continue; // to cope with empty slides
+ while (menu && menu.nodeType == 3) {
+ menu = menu.nextSibling;
+ }
+ if (!menu) continue; // to cope with slides with only text nodes
+
+ var menunodes = menu.childNodes;
+ for (var o = 0; o < menunodes.length; o++) {
+ otext += nodeValue(menunodes[o]);
+ }
+ list.options[list.length] = new Option(n + ' : ' + otext, n);
+ }
+}
+
+function currentSlide() {
+ var cs;
+ var footer_nodes;
+ var vis = 'visible';
+ if (document.getElementById) {
+ cs = document.getElementById('currentSlide');
+ footer_nodes = document.getElementById('footer').childNodes;
+ } else {
+ cs = document.currentSlide;
+ footer = document.footer.childNodes;
+ }
+ cs.innerHTML = '<span id="csHere">' + snum + '<\/span> ' +
+ '<span id="csSep">\/<\/span> ' +
+ '<span id="csTotal">' + (smax-1) + '<\/span>';
+ if (snum == 0) {
+ vis = 'hidden';
+ }
+ cs.style.visibility = vis;
+ for (var i = 0; i < footer_nodes.length; i++) {
+ if (footer_nodes[i].nodeType == 1) {
+ footer_nodes[i].style.visibility = vis;
+ }
+ }
+}
+
+function go(step) {
+ if (document.getElementById('slideProj').disabled || step == 0) return;
+ var jl = document.getElementById('jumplist');
+ var cid = slideIDs[snum];
+ var ce = document.getElementById(cid);
+ if (incrementals[snum].length > 0) {
+ for (var i = 0; i < incrementals[snum].length; i++) {
+ removeClass(incrementals[snum][i], 'current');
+ removeClass(incrementals[snum][i], 'incremental');
+ }
+ }
+ if (step != 'j') {
+ snum += step;
+ lmax = smax - 1;
+ if (snum > lmax) snum = lmax;
+ if (snum < 0) snum = 0;
+ } else
+ snum = parseInt(jl.value);
+ var nid = slideIDs[snum];
+ var ne = document.getElementById(nid);
+ if (!ne) {
+ ne = document.getElementById(slideIDs[0]);
+ snum = 0;
+ }
+ if (step < 0) {incpos = incrementals[snum].length} else {incpos = 0;}
+ if (incrementals[snum].length > 0 && incpos == 0) {
+ for (var i = 0; i < incrementals[snum].length; i++) {
+ if (hasClass(incrementals[snum][i], 'current'))
+ incpos = i + 1;
+ else
+ addClass(incrementals[snum][i], 'incremental');
+ }
+ }
+ if (incrementals[snum].length > 0 && incpos > 0)
+ addClass(incrementals[snum][incpos - 1], 'current');
+ ce.style.visibility = 'hidden';
+ ne.style.visibility = 'visible';
+ jl.selectedIndex = snum;
+ currentSlide();
+ number = 0;
+}
+
+function goTo(target) {
+ if (target >= smax || target == snum) return;
+ go(target - snum);
+}
+
+function subgo(step) {
+ if (step > 0) {
+ removeClass(incrementals[snum][incpos - 1],'current');
+ removeClass(incrementals[snum][incpos], 'incremental');
+ addClass(incrementals[snum][incpos],'current');
+ incpos++;
+ } else {
+ incpos--;
+ removeClass(incrementals[snum][incpos],'current');
+ addClass(incrementals[snum][incpos], 'incremental');
+ addClass(incrementals[snum][incpos - 1],'current');
+ }
+}
+
+function toggle() {
+ var slideColl = GetElementsWithClassName('*','slide');
+ var slides = document.getElementById('slideProj');
+ var outline = document.getElementById('outlineStyle');
+ if (!slides.disabled) {
+ slides.disabled = true;
+ outline.disabled = false;
+ s5mode = false;
+ fontSize('1em');
+ for (var n = 0; n < smax; n++) {
+ var slide = slideColl[n];
+ slide.style.visibility = 'visible';
+ }
+ } else {
+ slides.disabled = false;
+ outline.disabled = true;
+ s5mode = true;
+ fontScale();
+ for (var n = 0; n < smax; n++) {
+ var slide = slideColl[n];
+ slide.style.visibility = 'hidden';
+ }
+ slideColl[snum].style.visibility = 'visible';
+ }
+}
+
+function showHide(action) {
+ var obj = GetElementsWithClassName('*','hideme')[0];
+ switch (action) {
+ case 's': obj.style.visibility = 'visible'; break;
+ case 'h': obj.style.visibility = 'hidden'; break;
+ case 'k':
+ if (obj.style.visibility != 'visible') {
+ obj.style.visibility = 'visible';
+ } else {
+ obj.style.visibility = 'hidden';
+ }
+ break;
+ }
+}
+
+// 'keys' code adapted from MozPoint (http://mozpoint.mozdev.org/)
+function keys(key) {
+ if (!key) {
+ key = event;
+ key.which = key.keyCode;
+ }
+ if (key.which == 84) {
+ toggle();
+ return;
+ }
+ if (s5mode) {
+ switch (key.which) {
+ case 10: // return
+ case 13: // enter
+ if (window.event && isParentOrSelf(window.event.srcElement, 'controls')) return;
+ if (key.target && isParentOrSelf(key.target, 'controls')) return;
+ if(number != undef) {
+ goTo(number);
+ break;
+ }
+ case 32: // spacebar
+ case 34: // page down
+ case 39: // rightkey
+ case 40: // downkey
+ if(number != undef) {
+ go(number);
+ } else if (!incrementals[snum] || incpos >= incrementals[snum].length) {
+ go(1);
+ } else {
+ subgo(1);
+ }
+ break;
+ case 33: // page up
+ case 37: // leftkey
+ case 38: // upkey
+ if(number != undef) {
+ go(-1 * number);
+ } else if (!incrementals[snum] || incpos <= 0) {
+ go(-1);
+ } else {
+ subgo(-1);
+ }
+ break;
+ case 36: // home
+ goTo(0);
+ break;
+ case 35: // end
+ goTo(smax-1);
+ break;
+ case 67: // c
+ showHide('k');
+ break;
+ }
+ if (key.which < 48 || key.which > 57) {
+ number = undef;
+ } else {
+ if (window.event && isParentOrSelf(window.event.srcElement, 'controls')) return;
+ if (key.target && isParentOrSelf(key.target, 'controls')) return;
+ number = (((number != undef) ? number : 0) * 10) + (key.which - 48);
+ }
+ }
+ return false;
+}
+
+function clicker(e) {
+ number = undef;
+ var target;
+ if (window.event) {
+ target = window.event.srcElement;
+ e = window.event;
+ } else target = e.target;
+ if (target.href != null || hasValue(target.rel, 'external') || isParentOrSelf(target, 'controls') || isParentOrSelf(target,'embed') || isParentOrSelf(target, 'object')) return true;
+ if (!e.which || e.which == 1) {
+ if (!incrementals[snum] || incpos >= incrementals[snum].length) {
+ go(1);
+ } else {
+ subgo(1);
+ }
+ }
+}
+
+function findSlide(hash) {
+ var target = document.getElementById(hash);
+ if (target) {
+ for (var i = 0; i < slideIDs.length; i++) {
+ if (target.id == slideIDs[i]) return i;
+ }
+ }
+ return null;
+}
+
+function slideJump() {
+ if (window.location.hash == null || window.location.hash == '') {
+ currentSlide();
+ return;
+ }
+ if (window.location.hash == null) return;
+ var dest = null;
+ dest = findSlide(window.location.hash.slice(1));
+ if (dest == null) {
+ dest = 0;
+ }
+ go(dest - snum);
+}
+
+function fixLinks() {
+ var thisUri = window.location.href;
+ thisUri = thisUri.slice(0, thisUri.length - window.location.hash.length);
+ var aelements = document.getElementsByTagName('A');
+ for (var i = 0; i < aelements.length; i++) {
+ var a = aelements[i].href;
+ var slideID = a.match('\#.+');
+ if ((slideID) && (slideID[0].slice(0,1) == '#')) {
+ var dest = findSlide(slideID[0].slice(1));
+ if (dest != null) {
+ if (aelements[i].addEventListener) {
+ aelements[i].addEventListener("click", new Function("e",
+ "if (document.getElementById('slideProj').disabled) return;" +
+ "go("+dest+" - snum); " +
+ "if (e.preventDefault) e.preventDefault();"), true);
+ } else if (aelements[i].attachEvent) {
+ aelements[i].attachEvent("onclick", new Function("",
+ "if (document.getElementById('slideProj').disabled) return;" +
+ "go("+dest+" - snum); " +
+ "event.returnValue = false;"));
+ }
+ }
+ }
+ }
+}
+
+function externalLinks() {
+ if (!document.getElementsByTagName) return;
+ var anchors = document.getElementsByTagName('a');
+ for (var i=0; i<anchors.length; i++) {
+ var anchor = anchors[i];
+ if (anchor.getAttribute('href') && hasValue(anchor.rel, 'external')) {
+ anchor.target = '_blank';
+ addClass(anchor,'external');
+ }
+ }
+}
+
+function createControls() {
+ var controlsDiv = document.getElementById("controls");
+ if (!controlsDiv) return;
+ var hider = ' onmouseover="showHide(\'s\');" onmouseout="showHide(\'h\');"';
+ var hideDiv, hideList = '';
+ if (controlVis == 'hidden') {
+ hideDiv = hider;
+ } else {
+ hideList = hider;
+ }
+ controlsDiv.innerHTML = '<form action="#" id="controlForm"' + hideDiv + '>' +
+ '<div id="navLinks">' +
+ '<a accesskey="t" id="toggle" href="javascript:toggle();">&#216;<\/a>' +
+ '<a accesskey="z" id="prev" href="javascript:go(-1);">&laquo;<\/a>' +
+ '<a accesskey="x" id="next" href="javascript:go(1);">&raquo;<\/a>' +
+ '<div id="navList"' + hideList + '><select id="jumplist" onchange="go(\'j\');"><\/select><\/div>' +
+ '<\/div><\/form>';
+ if (controlVis == 'hidden') {
+ var hidden = document.getElementById('navLinks');
+ } else {
+ var hidden = document.getElementById('jumplist');
+ }
+ addClass(hidden,'hideme');
+}
+
+function fontScale() { // causes layout problems in FireFox that get fixed if browser's Reload is used; same may be true of other Gecko-based browsers
+ if (!s5mode) return false;
+ var vScale = 22; // both yield 32 (after rounding) at 1024x768
+ var hScale = 32; // perhaps should auto-calculate based on theme's declared value?
+ if (window.innerHeight) {
+ var vSize = window.innerHeight;
+ var hSize = window.innerWidth;
+ } else if (document.documentElement.clientHeight) {
+ var vSize = document.documentElement.clientHeight;
+ var hSize = document.documentElement.clientWidth;
+ } else if (document.body.clientHeight) {
+ var vSize = document.body.clientHeight;
+ var hSize = document.body.clientWidth;
+ } else {
+ var vSize = 700; // assuming 1024x768, minus chrome and such
+ var hSize = 1024; // these do not account for kiosk mode or Opera Show
+ }
+ var newSize = Math.min(Math.round(vSize/vScale),Math.round(hSize/hScale));
+ fontSize(newSize + 'px');
+ if (isGe) { // hack to counter incremental reflow bugs
+ var obj = document.getElementsByTagName('body')[0];
+ obj.style.display = 'none';
+ obj.style.display = 'block';
+ }
+}
+
+function fontSize(value) {
+ if (!(s5ss = document.getElementById('s5ss'))) {
+ if (!isIE) {
+ document.getElementsByTagName('head')[0].appendChild(s5ss = document.createElement('style'));
+ s5ss.setAttribute('media','screen, projection');
+ s5ss.setAttribute('id','s5ss');
+ } else {
+ document.createStyleSheet();
+ document.s5ss = document.styleSheets[document.styleSheets.length - 1];
+ }
+ }
+ if (!isIE) {
+ while (s5ss.lastChild) s5ss.removeChild(s5ss.lastChild);
+ s5ss.appendChild(document.createTextNode('body {font-size: ' + value + ' !important;}'));
+ } else {
+ document.s5ss.addRule('body','font-size: ' + value + ' !important;');
+ }
+}
+
+function notOperaFix() {
+ slideCSS = document.getElementById('slideProj').href;
+ var slides = document.getElementById('slideProj');
+ var outline = document.getElementById('outlineStyle');
+ slides.setAttribute('media','screen');
+ outline.disabled = true;
+ if (isGe) {
+ slides.setAttribute('href','null'); // Gecko fix
+ slides.setAttribute('href',slideCSS); // Gecko fix
+ }
+ if (isIE && document.styleSheets && document.styleSheets[0]) {
+ document.styleSheets[0].addRule('img', 'behavior: url(ui/default/iepngfix.htc)');
+ document.styleSheets[0].addRule('div', 'behavior: url(ui/default/iepngfix.htc)');
+ document.styleSheets[0].addRule('.slide', 'behavior: url(ui/default/iepngfix.htc)');
+ }
+}
+
+function getIncrementals(obj) {
+ var incrementals = new Array();
+ if (!obj)
+ return incrementals;
+ var children = obj.childNodes;
+ for (var i = 0; i < children.length; i++) {
+ var child = children[i];
+ if (hasClass(child, 'incremental')) {
+ if (child.nodeName == 'OL' || child.nodeName == 'UL') {
+ removeClass(child, 'incremental');
+ for (var j = 0; j < child.childNodes.length; j++) {
+ if (child.childNodes[j].nodeType == 1) {
+ addClass(child.childNodes[j], 'incremental');
+ }
+ }
+ } else {
+ incrementals[incrementals.length] = child;
+ removeClass(child,'incremental');
+ }
+ }
+ if (hasClass(child, 'show-first')) {
+ if (child.nodeName == 'OL' || child.nodeName == 'UL') {
+ removeClass(child, 'show-first');
+ if (child.childNodes[isGe].nodeType == 1) {
+ removeClass(child.childNodes[isGe], 'incremental');
+ }
+ } else {
+ incrementals[incrementals.length] = child;
+ }
+ }
+ incrementals = incrementals.concat(getIncrementals(child));
+ }
+ return incrementals;
+}
+
+function createIncrementals() {
+ var incrementals = new Array();
+ for (var i = 0; i < smax; i++) {
+ incrementals[i] = getIncrementals(document.getElementById(slideIDs[i]));
+ }
+ return incrementals;
+}
+
+function defaultCheck() {
+ var allMetas = document.getElementsByTagName('meta');
+ for (var i = 0; i< allMetas.length; i++) {
+ if (allMetas[i].name == 'defaultView') {
+ defaultView = allMetas[i].content;
+ }
+ if (allMetas[i].name == 'controlVis') {
+ controlVis = allMetas[i].content;
+ }
+ }
+}
+
+// Key trap fix, new function body for trap()
+function trap(e) {
+ if (!e) {
+ e = event;
+ e.which = e.keyCode;
+ }
+ try {
+ modifierKey = e.ctrlKey || e.altKey || e.metaKey;
+ }
+ catch(e) {
+ modifierKey = false;
+ }
+ return modifierKey || e.which == 0;
+}
+
+function startup() {
+ defaultCheck();
+ if (!isOp) createControls();
+ slideLabel();
+ fixLinks();
+ externalLinks();
+ fontScale();
+ if (!isOp) {
+ notOperaFix();
+ incrementals = createIncrementals();
+ slideJump();
+ if (defaultView == 'outline') {
+ toggle();
+ }
+ document.onkeyup = keys;
+ document.onkeypress = trap;
+ document.onclick = clicker;
+ }
+}
+
+window.onload = startup;
+window.onresize = function(){setTimeout('fontScale()', 50);}
BIN ui/pretty/blank.gif
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
25 ui/pretty/framing.css
@@ -0,0 +1,25 @@
+/* This file has been placed in the public domain. */
+/* The following styles size, place, and layer the slide components.
+ Edit these if you want to change the overall slide layout.
+ The commented lines can be uncommented (and modified, if necessary)
+ to help you with the rearrangement process. */
+
+/* target = 1024x768 */
+
+div#header, div#footer, .slide {width: 100%; top: 0; left: 0;}
+div#header {position: fixed; top: 0; height: 3em; z-index: 1;}
+div#footer {top: auto; bottom: 0; height: 2.5em; z-index: 5;}
+.slide {top: 0; width: 92%; padding: 2.5em 4% 4%; z-index: 2;}
+div#controls {left: 50%; bottom: 0; width: 50%; z-index: 100;}
+div#controls form {position: absolute; bottom: 0; right: 0; width: 100%;
+ margin: 0;}
+#currentSlide {position: absolute; width: 10%; left: 45%; bottom: 1em;
+ z-index: 10;}
+html>body #currentSlide {position: fixed;}
+
+/*
+div#header {background: #FCC;}
+div#footer {background: #CCF;}
+div#controls {background: #BBD;}
+div#currentSlide {background: #FFC;}
+*/
42 ui/pretty/iepngfix.htc
@@ -0,0 +1,42 @@
+<public:component>
+<public:attach event="onpropertychange" onevent="doFix()" />
+
+<script>
+
+// IE5.5+ PNG Alpha Fix v1.0 by Angus Turnbull http://www.twinhelix.com
+// Free usage permitted as long as this notice remains intact.
+
+// This must be a path to a blank image. That's all the configuration you need here.
+var blankImg = 'ui/default/blank.gif';
+
+var f = 'DXImageTransform.Microsoft.AlphaImageLoader';
+
+function filt(s, m) {
+ if (filters[f]) {
+ filters[f].enabled = s ? true : false;
+ if (s) with (filters[f]) { src = s; sizingMethod = m }
+ } else if (s) style.filter = 'progid:'+f+'(src="'+s+'",sizingMethod="'+m+'")';
+}
+
+function doFix() {
+ if ((parseFloat(navigator.userAgent.match(/MSIE (\S+)/)[1]) < 5.5) ||
+ (event && !/(background|src)/.test(event.propertyName))) return;
+
+ if (tagName == 'IMG') {
+ if ((/\.png$/i).test(src)) {
+ filt(src, 'image'); // was 'scale'
+ src = blankImg;
+ } else if (src.indexOf(blankImg) < 0) filt();
+ } else if (style.backgroundImage) {
+ if (style.backgroundImage.match(/^url[("']+(.*\.png)[)"']+$/i)) {
+ var s = RegExp.$1;
+ style.backgroundImage = '';
+ filt(s, 'crop');
+ } else filt();
+ }
+}
+
+doFix();
+
+</script>
+</public:component>
8 ui/pretty/opera.css
@@ -0,0 +1,8 @@
+/* This file has been placed in the public domain. */
+/* DO NOT CHANGE THESE unless you really want to break Opera Show */
+.slide {
+ visibility: visible !important;
+ position: static !important;
+ page-break-before: always;
+}
+#slide0 {page-break-before: avoid;}
16 ui/pretty/outline.css
@@ -0,0 +1,16 @@
+/* This file has been placed in the public domain. */
+/* Don't change this unless you want the layout stuff to show up in the
+ outline view! */
+
+.layout div, #footer *, #controlForm * {display: none;}
+#footer, #controls, #controlForm, #navLinks, #toggle {
+ display: block; visibility: visible; margin: 0; padding: 0;}
+#toggle {float: right; padding: 0.5em;}
+html>body #toggle {position: fixed; top: 0; right: 0;}
+
+/* making the outline look pretty-ish */
+
+#slide0 h1, #slide0 h2, #slide0 h3, #slide0 h4 {border: none; margin: 0;}
+#toggle {border: 1px solid; border-width: 0 0 1px 1px; background: #FFF;}
+
+.outline {display: inline ! important;}
120 ui/pretty/pretty.css
@@ -0,0 +1,120 @@
+/* This file has been placed in the public domain. */
+/* Following are the presentation styles -- edit away! */
+
+html, body {margin: 0; padding: 0;}
+body {background: white; color: black;}
+/* Replace the background style above with the style below (and again for
+ div#header) for a graphic: */
+/* background: white url(bodybg.gif) -16px 0 no-repeat; */
+:link, :visited {text-decoration: none; color: #00C;}
+#controls :active {color: #88A !important;}
+#controls :focus {outline: 1px dotted #227;}
+h1, h2, h3, h4 {font-size: 100%; margin: 0; padding: 0; font-weight: inherit;}
+
+blockquote {padding: 0 2em 0.5em; margin: 0 1.5em 0.5em;}
+blockquote p {margin: 0;}
+
+kbd {font-weight: bold; font-size: 1em;}
+sup {font-size: smaller; line-height: 1px;}
+
+.slide pre {padding: 0; margin-left: 0; margin-right: 0; font-size: 70%; color: black;}
+.slide ul ul li {list-style: square;}
+.slide img.leader {display: block; margin: 0 auto;}
+.slide tt {font-size: 90%;}
+
+div#header, div#footer {background: #005; color: #AAB; font-family: sans-serif;}
+/* background: #005 url(bodybg.gif) -16px 0 no-repeat; */
+div#footer {font-size: 0.5em; font-weight: bold; padding: 1em 0;}
+#footer h1 {display: block; padding: 0 1em;}
+#footer h2 {display: block; padding: 0.8em 1em 0;}
+
+.slide {font-size: 1.2em;}
+.slide h1 {position: absolute; top: 0.45em; z-index: 1;
+ margin: 0; padding-left: 0.7em; white-space: nowrap;
+ font: bold 150% sans-serif; color: #DDE; background: #005;}
+.slide h2 {font: bold 120%/1em sans-serif; padding-top: 0.5em;}
+.slide h3 {font: bold 100% sans-serif; padding-top: 0.5em;}
+h1 abbr {font-variant: small-caps;}
+
+div#controls {position: absolute; left: 50%; bottom: 0;
+ width: 50%; text-align: right; font: bold 0.9em sans-serif;}
+html>body div#controls {position: fixed; padding: 0 0 1em 0; top: auto;}
+div#controls form {position: absolute; bottom: 0; right: 0; width: 100%;
+ margin: 0; padding: 0;}
+#controls #navLinks a {padding: 0; margin: 0 0.5em;
+ background: #005; border: none; color: #779; cursor: pointer;}
+#controls #navList {height: 1em;}
+#controls #navList #jumplist {position: absolute; bottom: 0; right: 0;
+ background: #DDD; color: #227;}
+
+#currentSlide {text-align: center; font-size: 0.5em; color: #449;
+ font-family: sans-serif; font-weight: bold;}
+
+#slide0 {padding-top: 1.5em}
+#slide0 h1 {position: static; margin: 1em 0 0; padding: 0; color: #000;
+ font: bold 2em sans-serif; white-space: normal; background: transparent;}
+#slide0 h2 {font: bold italic 1em sans-serif; margin: 0.25em;}
+#slide0 h3 {margin-top: 1.5em; font-size: 1.5em;}
+#slide0 h4 {margin-top: 0; font-size: 1em;}
+
+ul.urls {list-style: none; display: inline; margin: 0;}
+.urls li {display: inline; margin: 0;}
+.external {border-bottom: 1px dotted gray;}
+html>body .external {border-bottom: none;}
+.external:after {content: " \274F"; font-size: smaller; color: #77B;}
+
+.incremental, .incremental *, .incremental *:after {visibility: visible;
+ color: white; border: 0;}
+img.incremental {visibility: hidden;}
+.slide .current {color: green;}
+
+.slide-display {display: inline ! important;}
+
+.huge {font-family: sans-serif; font-weight: bold; font-size: 150%;}
+.big {font-family: sans-serif; font-weight: bold; font-size: 120%;}
+.small {font-size: 75%;}
+.tiny {font-size: 50%;}
+.huge tt, .big tt, .small tt, .tiny tt {font-size: 115%;}
+.huge pre, .big pre, .small pre, .tiny pre {font-size: 115%;}
+
+.maroon {color: maroon;}
+.red {color: red;}
+.magenta {color: magenta;}
+.fuchsia {color: fuchsia;}
+.pink {color: #FAA;}
+.orange {color: orange;}
+.yellow {color: yellow;}
+.lime {color: lime;}
+.green {color: green;}
+.olive {color: olive;}
+.teal {color: teal;}
+.cyan {color: cyan;}
+.aqua {color: aqua;}
+.blue {color: blue;}
+.navy {color: navy;}
+.purple {color: purple;}
+.black {color: black;}
+.gray {color: gray;}
+.silver {color: silver;}
+.white {color: white;}
+
+.left {text-align: left ! important;}
+.center {text-align: center ! important;}
+.right {text-align: right ! important;}
+
+.animation {position: relative; margin: 1em 0; padding: 0;}
+.animation img {position: absolute;}
+
+/* Docutils-specific overrides */
+
+.slide table.docinfo {margin: 1em 0 0.5em 2em;}
+
+pre.literal-block, pre.doctest-block {background-color: white;}
+
+tt.docutils {background-color: white;}
+
+/* diagnostics */
+/*
+li:after {content: " [" attr(class) "]"; color: #F88;}
+div:before {content: "[" attr(class) "]"; color: #F88;}
+*/
24 ui/pretty/print.css
@@ -0,0 +1,24 @@
+/* This file has been placed in the public domain. */
+/* The following rule is necessary to have all slides appear in print!
+ DO NOT REMOVE IT! */
+.slide, ul {page-break-inside: avoid; visibility: visible !important;}
+h1 {page-break-after: avoid;}
+
+body {font-size: 12pt; background: white;}
+* {color: black;}
+
+#slide0 h1 {font-size: 200%; border: none; margin: 0.5em 0 0.25em;}
+#slide0 h3 {margin: 0; padding: 0;}
+#slide0 h4 {margin: 0 0 0.5em; padding: 0;}
+#slide0 {margin-bottom: 3em;}
+
+#header {display: none;}
+#footer h1 {margin: 0; border-bottom: 1px solid; color: gray;
+ font-style: italic;}
+#footer h2, #controls {display: none;}
+
+.print {display: inline ! important;}
+
+/* The following rule keeps the layout stuff out of print.
+ Remove at your own risk! */
+.layout, .layout * {display: none !important;}
70 ui/pretty/pygments.css
@@ -0,0 +1,70 @@
+.highlight .hll { background-color: #FFFFFF }
+.highlight { background: #FFFFFF; color: #FFFFFF }
+.highlight .c { color: #008800; font-style: italic; background-color: #FFFFFF } /* Comment */
+.highlight .err { color: #000000 } /* Error */
+.highlight .g { color: #000000 } /* Generic */
+.highlight .k { color: #fb660a; font-weight: bold } /* Keyword */
+.highlight .l { color: #000000 } /* Literal */
+.highlight .n { color: #000000 } /* Name */
+.highlight .o { color: #000000 } /* Operator */
+.highlight .x { color: #000000 } /* Other */
+.highlight .p { color: #000000 } /* Punctuation */
+.highlight .cm { color: #008800; font-style: italic; background-color: #0f140f } /* Comment.Multiline */
+.highlight .cp { color: #ff0007; font-weight: bold; font-style: italic; background-color: #0f140f } /* Comment.Preproc */
+.highlight .c1 { color: #008800; font-style: italic; background-color: #0f140f } /* Comment.Single */
+.highlight .cs { color: #008800; font-style: italic; background-color: #0f140f } /* Comment.Special */
+.highlight .gd { color: #000000 } /* Generic.Deleted */
+.highlight .ge { color: #000000 } /* Generic.Emph */
+.highlight .gr { color: #000000 } /* Generic.Error */
+.highlight .gh { color: #000000; font-weight: bold } /* Generic.Heading */
+.highlight .gi { color: #000000 } /* Generic.Inserted */
+.highlight .go { color: #444444; background-color: #222222 } /* Generic.Output */
+.highlight .gp { color: #000000 } /* Generic.Prompt */
+.highlight .gs { color: #000000 } /* Generic.Strong */
+.highlight .gu { color: #000000; font-weight: bold } /* Generic.Subheading */
+.highlight .gt { color: #000000 } /* Generic.Traceback */
+.highlight .kc { color: #fb660a; font-weight: bold } /* Keyword.Constant */
+.highlight .kd { color: #fb660a; font-weight: bold } /* Keyword.Declaration */
+.highlight .kn { color: #fb660a; font-weight: bold } /* Keyword.Namespace */
+.highlight .kp { color: #fb660a } /* Keyword.Pseudo */
+.highlight .kr { color: #fb660a; font-weight: bold } /* Keyword.Reserved */
+.highlight .kt { color: #cdcaa9; font-weight: bold } /* Keyword.Type */
+.highlight .ld { color: #000000 } /* Literal.Date */
+.highlight .m { color: #0086f7; font-weight: bold } /* Literal.Number */
+.highlight .s { color: #0086d2 } /* Literal.String */
+.highlight .na { color: #ff0086; font-weight: bold } /* Name.Attribute */
+.highlight .nb { color: #000000 } /* Name.Builtin */
+.highlight .nc { color: #000000 } /* Name.Class */
+.highlight .no { color: #0086d2 } /* Name.Constant */
+.highlight .nd { color: #000000 } /* Name.Decorator */
+.highlight .ni { color: #000000 } /* Name.Entity */
+.highlight .ne { color: #000000 } /* Name.Exception */
+.highlight .nf { color: #ff0086; font-weight: bold } /* Name.Function */
+.highlight .nl { color: #000000 } /* Name.Label */
+.highlight .nn { color: #000000 } /* Name.Namespace */
+.highlight .nx { color: #000000 } /* Name.Other */
+.highlight .py { color: #000000 } /* Name.Property */
+.highlight .nt { color: #fb660a; font-weight: bold } /* Name.Tag */
+.highlight .nv { color: #fb660a } /* Name.Variable */
+.highlight .ow { color: #000000 } /* Operator.Word */
+.highlight .w { color: #888888 } /* Text.Whitespace */
+.highlight .mf { color: #0086f7; font-weight: bold } /* Literal.Number.Float */
+.highlight .mh { color: #0086f7; font-weight: bold } /* Literal.Number.Hex */
+.highlight .mi { color: #0086f7; font-weight: bold } /* Literal.Number.Integer */
+.highlight .mo { color: #0086f7; font-weight: bold } /* Literal.Number.Oct */
+.highlight .sb { color: #0086d2 } /* Literal.String.Backtick */
+.highlight .sc { color: #0086d2 } /* Literal.String.Char */
+.highlight .sd { color: #0086d2 } /* Literal.String.Doc */
+.highlight .s2 { color: #0086d2 } /* Literal.String.Double */
+.highlight .se { color: #0086d2 } /* Literal.String.Escape */
+.highlight .sh { color: #0086d2 } /* Literal.String.Heredoc */
+.highlight .si { color: #0086d2 } /* Literal.String.Interpol */
+.highlight .sx { color: #0086d2 } /* Literal.String.Other */
+.highlight .sr { color: #0086d2 } /* Literal.String.Regex */
+.highlight .s1 { color: #0086d2 } /* Literal.String.Single */
+.highlight .ss { color: #0086d2 } /* Literal.String.Symbol */
+.highlight .bp { color: #000000 } /* Name.Builtin.Pseudo */
+.highlight .vc { color: #fb660a } /* Name.Variable.Class */
+.highlight .vg { color: #fb660a } /* Name.Variable.Global */
+.highlight .vi { color: #fb660a } /* Name.Variable.Instance */
+.highlight .il { color: #0086f7; font-weight: bold } /* Literal.Number.Integer.Long */
11 ui/pretty/s5-core.css
@@ -0,0 +1,11 @@
+/* This file has been placed in the public domain. */
+/* Do not edit or override these styles!
+ The system will likely break if you do. */
+
+div#header, div#footer, div#controls, .slide {position: absolute;}
+html>body div#header, html>body div#footer,
+ html>body div#controls, html>body .slide {position: fixed;}
+.handout {display: none;}
+.layout {display: block;}
+.slide, .hideme, .incremental {visibility: hidden;}
+#slide0 {visibility: visible;}
13 ui/pretty/slides.css
@@ -0,0 +1,13 @@
+/* This file has been placed in the public domain. */
+
+/* required to make the slide show run at all */
+@import url(s5-core.css);
+
+/* sets basic placement and size of slide components */
+@import url(framing.css);
+
+/* styles that make the slides look good */
+@import url(pretty.css);
+
+/* styles that make the slides look good */
+@import url(pygments.css);
558 ui/pretty/slides.js
@@ -0,0 +1,558 @@
+// S5 v1.1 slides.js -- released into the Public Domain
+// Modified for Docutils (http://docutils.sf.net) by David Goodger
+//
+// Please see http://www.meyerweb.com/eric/tools/s5/credits.html for
+// information about all the wonderful and talented contributors to this code!
+
+var undef;
+var slideCSS = '';
+var snum = 0;
+var smax = 1;
+var slideIDs = new Array();
+var incpos = 0;
+var number = undef;
+var s5mode = true;
+var defaultView = 'slideshow';
+var controlVis = 'visible';
+
+var isIE = navigator.appName == 'Microsoft Internet Explorer' ? 1 : 0;
+var isOp = navigator.userAgent.indexOf('Opera') > -1 ? 1 : 0;
+var isGe = navigator.userAgent.indexOf('Gecko') > -1 && navigator.userAgent.indexOf('Safari') < 1 ? 1 : 0;
+
+function hasClass(object, className) {
+ if (!object.className) return false;
+ return (object.className.search('(^|\\s)' + className + '(\\s|$)') != -1);
+}
+
+function hasValue(object, value) {
+ if (!object) return false;
+ return (object.search('(^|\\s)' + value + '(\\s|$)') != -1);
+}
+
+function removeClass(object,className) {
+ if (!object) return;
+ object.className = object.className.replace(new RegExp('(^|\\s)'+className+'(\\s|$)'), RegExp.$1+RegExp.$2);
+}
+
+function addClass(object,className) {
+ if (!object || hasClass(object, className)) return;
+ if (object.className) {
+ object.className += ' '+className;
+ } else {
+ object.className = className;
+ }
+}
+
+function GetElementsWithClassName(elementName,className) {
+ var allElements = document.getElementsByTagName(elementName);
+ var elemColl = new Array();
+ for (var i = 0; i< allElements.length; i++) {
+ if (hasClass(allElements[i], className)) {
+ elemColl[elemColl.length] = allElements[i];
+ }
+ }
+ return elemColl;
+}
+
+function isParentOrSelf(element, id) {
+ if (element == null || element.nodeName=='BODY') return false;
+ else if (element.id == id) return true;
+ else return isParentOrSelf(element.parentNode, id);
+}
+
+function nodeValue(node) {
+ var result = "";
+ if (node.nodeType == 1) {
+ var children = node.childNodes;
+ for (var i = 0; i < children.length; ++i) {
+ result += nodeValue(children[i]);
+ }
+ }
+ else if (node.nodeType == 3) {
+ result = node.nodeValue;
+ }
+ return(result);
+}
+
+function slideLabel() {
+ var slideColl = GetElementsWithClassName('*','slide');
+ var list = document.getElementById('jumplist');
+ smax = slideColl.length;
+ for (var n = 0; n < smax; n++) {
+ var obj = slideColl[n];
+
+ var did = 'slide' + n.toString();
+ if (obj.getAttribute('id')) {
+ slideIDs[n] = obj.getAttribute('id');
+ }
+ else {
+ obj.setAttribute('id',did);
+ slideIDs[n] = did;
+ }
+ if (isOp) continue;
+
+ var otext = '';
+ var menu = obj.firstChild;
+ if (!menu) continue; // to cope with empty slides
+ while (menu && menu.nodeType == 3) {
+ menu = menu.nextSibling;
+ }
+ if (!menu) continue; // to cope with slides with only text nodes
+
+ var menunodes = menu.childNodes;
+ for (var o = 0; o < menunodes.length; o++) {
+ otext += nodeValue(menunodes[o]);
+ }
+ list.options[list.length] = new Option(n + ' : ' + otext, n);
+ }
+}
+
+function currentSlide() {
+ var cs;
+ var footer_nodes;
+ var vis = 'visible';
+ if (document.getElementById) {
+ cs = document.getElementById('currentSlide');
+ footer_nodes = document.getElementById('footer').childNodes;
+ } else {
+ cs = document.currentSlide;
+ footer = document.footer.childNodes;
+ }
+ cs.innerHTML = '<span id="csHere">' + snum + '<\/span> ' +
+ '<span id="csSep">\/<\/span> ' +
+ '<span id="csTotal">' + (smax-1) + '<\/span>';
+ if (snum == 0) {
+ vis = 'hidden';
+ }
+ cs.style.visibility = vis;
+ for (var i = 0; i < footer_nodes.length; i++) {
+ if (footer_nodes[i].nodeType == 1) {
+ footer_nodes[i].style.visibility = vis;
+ }
+ }
+}
+
+function go(step) {
+ if (document.getElementById('slideProj').disabled || step == 0) return;
+ var jl = document.getElementById('jumplist');
+ var cid = slideIDs[snum];
+ var ce = document.getElementById(cid);
+ if (incrementals[snum].length > 0) {
+ for (var i = 0; i < incrementals[snum].length; i++) {
+ removeClass(incrementals[snum][i], 'current');
+ removeClass(incrementals[snum][i], 'incremental');
+ }
+ }
+ if (step != 'j') {
+ snum += step;
+ lmax = smax - 1;
+ if (snum > lmax) snum = lmax;
+ if (snum < 0) snum = 0;
+ } else
+ snum = parseInt(jl.value);
+ var nid = slideIDs[snum];
+ var ne = document.getElementById(nid);
+ if (!ne) {
+ ne = document.getElementById(slideIDs[0]);
+ snum = 0;
+ }
+ if (step < 0) {incpos = incrementals[snum].length} else {incpos = 0;}