Category Archives: Code

Python – Love / Hate

Hate:

1) Really bad at managing threads.
2) All class properties require “self” keyword.
3) Inheritance is supported but can be difficult to invoke.
4) Private members are difficult to encapsulate.
5) More difficult to deploy then traditional compiled languages.
6) Default timer class is limiting.

Love:

1) Tuples.
2) Keyword parameters.
3) Everything is an object.
4) The “pass” keyword.
5) Generator objects.
6) Method objects.
7) Dynamic code insertion.
8) PEP8.

Python – No Enumerated Data Type?

In the embedded world where C/C++ are the predominantly used languages, the enum data type is heavily used. It’s quick and easy to use and understand for specifying flags and register values.  Not yet understanding that Python’s real strength is hash-able data types and that a switch statement didn’t exist, I found myself wanting to use traditional C/C++ enumerated data types when I first started learning Python.

Even though there is no “enum” keyword in Python, there are a few easy ways to create an enumerated data type. The following snippet uses the Python argument packer to create a new data type that is just a key value paired dictionary.

def enum(*args):
    enums = dict(zip(args, range(len(args))))
    return type('Enum', (), enums)

Thats it. This simple function takes a list of items and auto-completes the value. It can easily be used like the following.

alignment = enum("left","center","right")

def alignText(text, pos):
    if pos == alignment.left:
        pass

alignText("some text", alignment.left)

Another object oriented approach I came across is to overload the existing Python set( ) data type and override the __getattr__() method.

class Enum(set):
    def __getattr__(self, name):
        if name in self:
            return name
        raise AttributeError

    def __setattr__(self, name, value):
        pass

    def __delattr__(self, name):
        pass

Neither approach fully addresses all the functionality of the C/C++ enum type. The missing functionality is the ability to specify a value for an entry and having all sequential entries be incremented by one (below). However, both solutions do offer a quick enumerated data type that can be used in most scenarios.

enum alignment = {	LEFT,		// 0 
					CENTER=10,	// 10
					RIGHT		// 11 
		 		 };


PyMT Black Backdrop Widget

Over the past few PyMT applications I’ve found it very useful to have a black backdrop to place over the main application area to highlight a special area of the app. The basic widget below absorbs all the key events that would normally make it to the main app. Its easy to use, just make it visible and then raise the widgets you want above it.

class Backdrop(MTWidget):
    def __init__(self, **kwargs):
        super(Backdrop, self).__init__(**kwargs)
        self.style = {'bg-color': (0,0,0,.6), 'draw-background': 1}
        
    def on_touch_down(self, touch):
        if not self.collide_point(*touch.pos):
            return
        touch.grab(self)
        return True
    def on_touch_up(self, touch):
        if touch.grab_current != self:
            return
        return True
    def on_touch_move(self, touch):
        return
    
b = Backdrop(size=(1920,1080), pos=(0,0)) #full width of app window
b.hide()

PyMT Scatter Video Widget

For anyone contemplating writing a multi-touch application, PyMT can be a fun and easy way to see instant results. Its API offers several useful widgets that allows for fast prototyping. With that said, PyMT should not be used for a commercial or high performance applications, as it has some major limitations with its inheritance architecture and screen paint logic (plus it comes with a GPL license). Some of these issues have been addressed in the teams rewrite of PyMT called Kivy. Although Kivy appears promising, it is still in its infancy and will need a few more release iterations before being adopted by the masses.

The weakest PyMT widget is by far the video player. Its integration with gstreamer is not nearly as complete as PyQt and it doesn’t have full multi-touch support. To address the multi-touch issue I wrote the following code snippet for one of Immersive’s first early stage in store product browser. It adds a default picture when the video is at position 0 and superimposes a “play” button when paused. In addition it uses the MTScatter widget as its base class which allows the user to manipulate the video using full multi-touch gestures when playing.

class scatVid(MTScatter):
    def __init__(self, filename, image, **kwargs):
        # image is a pre-constructed Image( ) object to be used at start of video
        super(scatVid, self).__init__(**kwargs)
        self.image = MTImage(image)
        self.play = MTImage(Image('./play_button.png'))
        self._posXY = None
        self.video = MTVideo(filename=filename, eos='loop')
        self.video.hide_controls()
        self.video.player.position = 10
        self.size=self.video.size
        connect(self.video, 'on_resize', self, 'size')
        connect(self.video, 'on_resize', self.image, 'size')
        connect(self.video, 'on_resize', self.play, 'size')

        self.add_widget(self.video)
        self.add_widget(self.image)
        self.add_widget(self.play)
        self._state = ""

    def stop(self):
        self.video.player.stop()

    def play(self):
        self.video.player.play()

    def hide(self):
        self.video.player.stop()
        super(scatVid, self).hide()

    def show(self):
        self.video.player.load()
        super(scatVid, self).show()

    def _get_state(self):
        return self.video.player.state

    def _get_posXY(self):
        return self._posXY
    def _set_posXY(self, x, y):
        print "setting posXY: %dx%d" %(x,y)
        self._posXY=(x,y)
        self.pos=(x,y)

    def draw(self):
        super(scatVid, self).draw()
        if self.state != "playing":
            if self.video.player.position < 2:
                self.image.show()
            else:
                self.play.show()
        else:
            self.image.hide()
            self.play.hide()

    state = property(lambda self: self._get_state(),
            doc='Get the video playing status')

To see the above code in action look here. You can use any play button piece of artwork, but for your convince here is the one I used.

Red Hot Pawn Gadget

I love online chess. I typically play anywhere from 10-15 games at any given time. Red Hot Pawn has a default move timeout of once every 3 days, so games can sometimes last over a month. What I hate about online chess is not knowing if its your turn without loging in or signing up to receive a bunch of email notifications.

My solution was to write a Windows Sidebar Gadget that periodically checks for pending games. When you login to your RHP account using Microsoft Internet Explorer the Gadget then uses AJAX to get the number of games where its your move. This allows me to do whatever I want on my desktop and know exactly when I can switch back to the browser and play some chess 🙂

Many of the settings are configurable in the widgets flyout panel. Basic stuff like the check interval, a count down timer, and the name size are adjustable. Oh, and during December the Red Pawn wears a Santa hat!

The code is HTML/JavaScript and can be forked on GitHub here. As a warning, this tool was very much a rapid prototype and I cared more about getting it to work fast then optimization and readability. If you want to download it and use it you can do so here.

PHP Line Counter Script

Want to know how many lines of code you wrote? Put this php script in your path and run it on the root directory of your php project and it will count the number of lines in all the *.php and *.inc files. Also takes an optional -html command line argument if you want to count html files too. Very easy to modify if you want to count other types of files like *.js and *.cpp.

<?php
$lines = 0;
$total_lines = 0;
$verbose = 0;
$file_type_html = 0;

function rglob($pattern='*', $flags=0,$path='')
{
	$paths=glob($path.'*',GLOB_MARK|GLOB_ONLYDIR|GLOB_NOSORT);
	$files=glob($path.$pattern, $flags);
	foreach($paths as $path)
	{
		$files=array_merge($files,rglob($pattern, $flags, $path));
	}
	return $files;
}

// check for command line args
if($argc > 1){
	if(in_array($argv[1],array('--help','-help','-h','-?'))){
		echo "-v	verbose\n";
		echo "-html	count html files\n";
		exit(0);
	}
	if(array_search('-v',$argv))
		$verbose = 1;
	if(array_search('-html',$argv))
		$file_type_html = 1;
}

$file_array_php = rglob('*.php');
$file_array_incs = rglob('*.inc');
if($file_type_html)
	$file_array_html = rglob('*.htm*'); // catch *.html and *.htm

if($verbose){
	var_export($file_array_php);
	var_export($file_array_incs);
	if($file_type_html)
		var_export($file_array_html);
}

foreach($file_array_php as $file)
{
	$lines = count(file($file));
	$total_lines += $lines;
	if($verbose)
	{
		echo "\n";
		echo "$lines in the file $file";
	}
}

foreach($file_array_incs as $file)
{
	$lines = count(file($file));
	$total_lines += $lines;
	if($verbose)
	{
		echo "\n";
		echo "$lines in the file $file";
	}
}

if($file_type_html)
{
	foreach($file_array_html as $file)
	{
		$lines = count(file($file));
		$total_lines += $lines;
		if($verbose)
		{
			echo "\n";
			echo "$lines in the file $file";
		}
	}
}
echo "\n\n\n";
echo "There are a total of $total_lines lines\n";

?>

PHP LAMP/WAMP File Paths

I came across some PHP code I wrote way back in 2006. At the time I was doing lots of file access on both Windows and Linux with the same code and was getting sick of fixing ‘/’ vs. ‘\\’ porting issues. Its pretty straight forward simple code but thought it might be useful to others. Basically I’m just wrapping the PHP file access methods with my own that always take a Linux ‘/’ path separator and if the method determines its running on Windows it automatically converts the path to use ‘\\’.

function isWindows()
{
	$os = php_uname('s');
	return strstr($os, 'Windows');
}

function convertPath($LinuxPathName)
{
	if(isWindows())
	{
		$basename = getcwd();
		$LinuxPathName = str_replace('/','\\',$LinuxPathName);
		$LinuxPathName = $basename . $LinuxPathName;
	}
	return $LinuxPathName;
}

/**
* my_fopen
*
* @param string $LinuxPathName Use a pathname with linux '/' convention
* @param string $Permissions Use to specify file permission, example '+w'
* @return int File handler descriptor
*/
function my_fopen($LinuxPathName, $Permissions)
{
	$ConvertedPathName = convertPath($LinuxPathName);
	$handle = fopen($ConvertedPathName, $Permissions);
	return $handle;
}

/**
* my_file_exists
*
* @param string $LinuxPathName Use a pathname with linux '/' convention
* @return bool
*/
function my_file_exists($LinuxPathName)
{
	$ConvertedPathName = convertPath($LinuxPathName);
	return file_exists($ConvertedPathName);
}

/**
* my_filesize
*
* @param LinuxPathName Use a pathname with linux '/' convention
* @return int
*/
function my_filesize($LinuxPathName)
{
	$ConvertedPathName = convertPath($LinuxPathName);
	return filesize($ConvertedPathName);
}