Friday 25 July 2014

Tkinter - Random Backgrounds with Python, version 2!

Our original random background generator was rife with errors so we've restructured it to make it a little better. See if you can follow the math and where I went wrong in the last one!

Tuesday 15 July 2014

Python - Level 3 Material

Level 3 Python Topics


Tkinter

Tkinter is a python module for creating simple graphical user interfaces (windows and elements). Whilst I covered the basics of making a Tkinter canvas and drawing shapes here, I'll also mention how to add buttons and text fields etc. Here's something we might start off with:

Now to add a button:
But this button doesn't do anything. To attach some functionality to it (in this case we're going to overwrite the blue rectangle with a white one) we use the 'command='statement in the Button() method and then we write a method linked to that (in our case called doClear).
But we can also add more than buttons - for instance here's a text_field with an associated label:
And here's a dropdown menu that allows users to pick from a series of predetermined choices:

Challenge: 

Make a Tkinter GUI that allows the user to pick from a list of countries and then draws out their flags using the Tkinter canvas create_rectangle/arc/oval commands when the 'Draw' button is pushed. I suggest starting with Japan, Germany, Norway and Scotland. 

Object Oriented Programming

Object orientation is a way of re-organising your code in such a way that it makes doing lots of complicated things much easier (a bit like we did with methods in the Level 2 section). The only way I managed to wrap my head around it (and it took me ages!) is to think of an illustrative example. Imagine you were writing a simple game like pong for instance.

Essentially you need to create two paddles and a ball (ignoring scoring), remember where each is, what direction it's travelling in and at what speed, where its edges are etc. You can do this pretty easily with only 3 items (although it will require a fair few variables). But imagine what would happen if you tried to extend pong in any way; What if you decided to add 2 balls? Or 3? What if you just wanted to add in a third dimension? The number of variables and complexity gets huge! And we're just doing more of the same, so instead we write a Class for the ball and paddles and then we just say how many of each we want. Each class remembers its own set of variables, which means we only have to define each one once and every new copy already has its own variables. For instance the Ball class might be defined like this:
The full code of a ball class might look like this: and now if we want to add bouncing functionality off the walls (and generally clean up the code)

Challenge: 

First, extend the code above to have >100 balls all starting at different locations (this should only take about 5 more lines of code). Make Pong using Tkinter and a class for the GUI, paddles and ball(s).

Final Challenge:

Build a 'mosaic maker' program - a program that generates a grid of squares in a GUI canvas and allows the user to change their colour by clicking on them (example shown below). The GUI should have 2 buttons that allow the user to select either red or blue for the colour of the clicked square (the default should be black) and one that allows the user to clear the grid to white. Finally you may want to extend your program to allow the user to replace a square with a .png image of their choice or to choose particular colours by entering their numeric RGB values, and write a doctest that tests your programs ability to deal with non-RGB inputs. Finally re-structure your program so that you have a class for the GUI.

Python - Level 2 material

Level 2 Python Topics



Methods

In the Level 1 material we used a number of 'methods' already (like rantint() and range()). These were predefined by other people - but we can just as easily write our own to do what ever we want, is particular this comes in really handy when you want to do the same or similar things multiple times. Rather than copy pasting our code - we can just repeat a method with different inputs. 


Challenge: 

Construct a method that picks a random number between 2 numbers passed to the method but that DOESN'T include the numbers themselves.

Importing Text files


Importing text files and processing them is how I actually got into python, it's certainly some of the simplest functionality that allows you to do a huge amount!
As with everything we can also wrap it into a neat little method to use again later:

Lets say you're interested in global companies performance - you can get data from Wikipedia about their financial performance and turn it into a csv or txt file using Google spreadsheets (tutorial here), but in this just download this data as a csv.  

Navigating Lists

Now we've converted our text file to a list we can now navigate it's rows and columns easily


Challenge: 

Using this table from Wikipedia (and a Python program), determine what's the most common starting letter for the name of one of Snow White's 7 dwarves (or just the most common name). 
(N.B. you can also use python to automatically get the data from the net for you using a module called urllib2 and the method urlopen(url) but it's far easier to start with a text file.)

Sanitising User input

Here's a few nice tricks for sanitising user input - can you figure out what each line does?

Challenge: 

Wrap the above code into a method that takes a text question and a list of acceptable responses and returns the user's answer when they give an appropriate one.

Final Challenge

Create a program that counts all the individual letters in a book and how many times each one occurs, then prints the results (I suggest a copy of Charles Dickens' 'A Tale of Two Cities' which you can get free here). Why? You might be able to use the frequency of certain letters as a sort of 'fingerprint' for the language of that book (i.e. is it in Modern English, Old English, German, French or Latin?), but also this 'frequency analysis' is the most basic method of code cracking. Lets say you receive some encoded text that has been encoded with a simple substitution cypher (i.e. one letter has just been replaced with another). A frequency analysis like this will show (roughly) which letters are which in the encoded message allowing you to start to decode it (for example in English the most common letter is 'e' so the most common character in the encrypted message is probably also 'e'). If you want to test your cracking skills find a nice long string and encode it with the command 'encode':
Then do a frequency analysis on the encoded string and see if you can figure out what character has been replaced with what (ideally you would have someone else encode the message so that you didn't know what the original message was!).

Python - Level 1 material

I've been running introductory Python sessions with students and teachers from around Wellington for the last few months looking at the material relevant to NCEA level 1, 2 and 3 digital technologies achievement standards. In the interests of discussion and improvement I'm going to post what I cover here along with the Challenges I pose to participants along the way to get people to use the knowledge I'm allegedly imparting to them over the course of the session. So without further ado here's Elf short, sweet foray into Level 1 Python (I'll cover level 2 and 3 in other posts). Feel free to copy and paste this code into ipython or a python script and run it as you go so you get a feel of what each block does.

Level 1 Python Topics


  • User information (input())
  • String editing and concatenation 
  • For Loops (for i in range():)
  • Counting (i+=1)
  • Random numbers and modules (import)
  • Conditional logic (if:)
  • While Loops (while True:)

User Information and string editing


Challenge: 

Ask the user for their name, address, phone number and the colour of their house. Then print out a description in the form of: "Your name is <name> and you live in a <colour> house at <address> and I can call you on <phone_number>".

For Loops


Challenge:

Using a for loop within a for loop print the numbers 0-10 3 times.

Counting/Iterating


Challenge:

Ask the user for a number then count down from that number.

Random and modules


Challenge:

Ask the user for a number and then print that many random numbers between 10 and 100. Hint: you will need to convert your user unput from a string to an integer using the int() command.

Conditional Statements


Challenge:

Pick a random number. If less than 10, or if equal to 30, or if it's not greater than 50 print 'Yes'.
Otherwise print 'No'.

While Loops


Challenge:

Set a while loop that picks and prints a random number that has a 1/100 chance of breaking from the loop.

Final Challenge:

I find the best way to learn these concepts is to have a challenge that uses them all. A nice simple example is creating a computer game of Rock, paper, scissors which you should be able to make using only the coding elements I've described above. You will need to ask the user for their choice of rock, paper or scissors (can you allow the user to ONLY select from these somehow?) - then get the computer to pick as well (those random commands might come in handy) - then compare the two inputs and decide who wins and (as games usually run the best of 3) you will need to count each players score and decide which player has won. And once the game has completed you might want to ask your players if they want to play again? 

Finally - if that's all too easy for you I suggest creating an 'expansion' to your game that plays rock, paper, scissors, lizard, spock following this logic:

Monday 14 July 2014

Blender 2.7 - Rigid Body simulation

Blender is great, but it's a little tricky to get anything really satisfying out of it quickly. That said, beautiful projects like QWOP or this video of collapsing barrels from the Crysis engine shows that simple designs can give us some really epic animations!

This tutorial was originally conceived by Andrew Price from Blender Guru, but we're going to expand on some of his ideas.

Ball and Chain

First off we're going to create a linked chain of rings. Open a new blender project, delete the default cube, and replace it with a torus. Rotate the torus 90 degrees from the default plane, then duplicate (Shift +D) and move the second ring to be threaded perpendicularly through the first. Duplicate these links until you're happy with the length of your chain. Be careful when placing them to ensure that each ring doesn't overlap. Then we just need to tell Blender that these are rigid body objects. Select one of the links - then head over to the Properties editor (right side of the screen), select the physics tab (the blue bouncing ball) and select "Rigid Body" and from the "Shape" field change the default from Convex Hull to Mesh (this just changes how the rigid body physics are calculated). We can easily apply this to all the links in the chain by now selecting all of them (Shift and Right click), and choosing 'Copy from Active' on the Physics tab on the left of the screen.  Now test out your animation skills by pressing Alt+A. If your chain falls down then you've done everything correctly. If it explodes (as mine did!) then check that you have changed the shape object to Mesh for each link in the chain. Add a plane and scale it up (S) to give your chain something to fall on. However, to stop the plane from just falling down you will need to set it up as a rigid body object (as we did for the chain) and simply change the type from Active to Passive. You can pin the chain at the top by selecting the top chain link and de-selecting the 'Dynamic' checkbox in the Rigid Body pane. And feel free to add a wreaking ball to the end of the chain by selecting the bottom link, going into edit mode (Tab) adding a UV sphere and overlapping the two. Now you have everything you need to make a swinging ball and chain (increase the mass of the links to increase the chain strength).

The array modifier

Now we want to generate a large number of things for our wrecking ball to slam into (or drop onto). For this we can use an array modifier (which is found on the right hand side panel in the tab with the little wrench). Create a default cube and apply the array modifier to it and as you increase the array number you will see the number of repeats increase as well. You con control the axis of the repeats by the sliders under the Relative Offset box. Add an array modifier for each axis (i.e. 3) with a number of 1.02 to each (allows a little gap between all boxes) and apply them to get a stack of boxes (this will work with any shape so go nuts with Monkey heads instead if you like). Finally, as we did above, apply an Active Rigid body element to each box, reduce the mass to 0.1 - then test with Alt+A! If you've done this correctly, your boxes should collapse and explode. What?!
We just need to correct the centre of mass for each box (currently it's all placed on the original box). We do this by selecting all the boxes, the CTRL+SHIFT+ALT+C and selecting "Origin to Geometry". Now run Alt+A again and adjust your simulation. Enjoy!

Challenge: Use your wrecking ball (or another means) to topple a tower of 30+ cylinders

References

The original reference for this idea on how to do it comes from Andrew Price's video available here:
http://www.blenderguru.com/tutorials/quick-tutorial-make-a-wrecking-ball-with-rigid-body-physics/#.U8RuZ0AW3J4. Andrew has also written a bunch of other fantastic tutorials which I highly recommend here: http://www.blenderguru.com/tutorials/

Sunday 13 July 2014

MIT app inventor - Buttons, Text to Speech, Web and Translate

We just ran this as a workshop at the association of Women in Science conference, so we though we would put it up as an online tutorial too. This will take you through the basics of writing and MIT app inventor App, downloading and installing it to your phone and then following through a few extension challenges beyond those from the standard App inventor tutorials (with a healthy dose of elvish impishness!).

Head over to http://ai2.appinventor.mit.edu/ and login with your google account (or register for one for free) then take a look at the MIT App inventor basics tutorials here: http://goo.gl/sVZMzK.

It's worth noting that you DON'T need an Android phone to test these out as if you have installation privelages to the computers you're working on then you can simply install an emulator. Unfortunately this is only currently an option for OSX and Windows, which also allow direct connecting of an Android phone to a computer with the MIT App inventor editor on by Wifi or USB cable. This awesome little feature instantly clones the app you're creating to your device allowing you to test it in real time. If you're a dedicated linux user like us though, then a nice workaround is to simply use the 'Build' functionality at the top of the page to build your program and then automatically download and install it to your phone using a QR code (however you can end up with a lot of apps installed to your phone this way!).

Our first app: Text to Speech

Aim: An app that speaks some text that the use inputs
        Instructions: Here
Challenge: Extend your app so that it screams when you shake it (check out the .shaking method in the accelerometer sensor)


Our second app: Ball bounce


Aim: An app that allows you to control an on-screen ball
        Instructions: Here
Challenge: Increase the numbers of balls to 5, and allow collisions between balls

Repeater

Aim: An app that recognises voice commands and reads them back to you.

        Instructions: 

Start a new project and set up a basic screen with a button, a label, a speech recognizer and a text-to speech-element. Using the blocks editor, set up these blocks:
Simply, when the button is pushed, the app will try and recognise what has been spoken and will print a copy to the label and then attempt to speak it outloud. Yes, the SpeechRecognizer isn't great at NZ accents. Yes it's a source of much hilarity. Convieniently MIT app inventor have just introduced some new translation functionality in the form of the YandexTranslate design element (found under the 'Media' tab). You can pass this a string of words and it will attempt to translate it into a language of your choice.

Challenge: The 'repeater' app reads back to you in Italian


If you're looking for other languages:

  • en - English
  • es - Spanish
  • de - German
  • no - Norwegian
  • fr - French
  • ru - Russian (however the altered character set will appear in the translation label but not be read out by the text to speech element)

Insulter

Aim: An app that scrapes data from a website and prints it on screen

        Instructions: 

As per usual we're going to start off with a button and a label field, but because we also need data from the internet we will also need the 'Web' element from the Connectivity tab. The set up some blocks:
The first block connects the button with retrieving the html of the website. The second block triggers when that call is complete - and contains and 'if' statement that tests is the website retrieval was successful (responseCode = 200) or not. If it was successful then the returned html is printed to the screen and then spoken by a text to speech element. Initializing the local variable isn't necessary here - but becomes useful in the next step. And yes, you're reading this code right - this will just print the entire html of the website.

So our next step is to 'parse' the website html to allow us to pull out the elements we want. To see the html I'm talking about, head over to http://insult.dream40.org/, right click and select View Page Source. If you look though it you will quickly find two lists of words that the website picks from to get its insults.We can use a 'split' block from the text tab to help us sort through it. I suggest starting by getting your program to grab one insult from the website and display it - then modify that to allow it to grab multiple elements and choose randomly between them. There IS an inbuilt Html Parser method in the Web element, but we were unable to get it working so we just did it by hand!

Challenge: Gets insults from http://insult.dream40.org/ and speaks them.


If you're interested in doing more you can follow our MIT app inventor bluetooth tutorial here: http://goo.gl/QbQhLk

References:

We've borrowed lots of this material from the MIT app inventor team of course! you can find all their wonderful tutorials here: http://appinventor.mit.edu/explore/ai2/tutorials.html and they're by FAR the best way to learn all about App inventor.
We also found this tutorial about getting Yahoo Stock prices really helpful: http://beta.appinventor.mit.edu/learn/tutorials/stockquotes/stockquotes.html
For those that want access to more Android functionality - we suggest Android studio rather than the old Eclipse plugin.