Never been to DZone Snippets before?

Snippets is a public source code repository. Easily build up your personal collection of code snippets, categorize them with tags / keywords, and share them with the world

« Newer Snippets
Older Snippets »
Showing 1-10 of 13 total  RSS 

PyS60 - Gallery Thumbnail Ver. 2

// Versione riveduta e corretta di Gallery Thumbnail postata da korakot ^_^

import appuifw
import e32
import graphics
import key_codes
import os

class FlickrS60Error(Exception): pass

class FlickrS60Thumb:

	def __init__(self, path):

		self.path = unicode(path)
		self.listFile = []
		self.ldivx = 0
		self.ldivy = 0
		self.lock = e32.Ao_lock()
		self.canvas = None
		self.img = graphics.Image.new((176, 144))
		self.img_tmp = graphics.Image.new((42, 36))
		self.x, self.y = 0, 0
		self.p = 0
		self.pages = 0
		self.currpages = 0
		self.mpath = 0

	def OnRun(self):

		appuifw.app.exit_key_handler = self.lock.signal
	
		self._createList()
		
		self.canvas = appuifw.Canvas(redraw_callback=self.OnUpdate)
		appuifw.app.body = self.canvas

		self.canvas.bind(key_codes.EKeyRightArrow, lambda: self.move(1, 0))
		self.canvas.bind(key_codes.EKeyLeftArrow, lambda: self.move(-1, 0))
		self.canvas.bind(key_codes.EKeyUpArrow, lambda: self.move(0, -1))
		self.canvas.bind(key_codes.EKeyDownArrow, lambda: self.move(0, 1))
		self.canvas.bind(key_codes.EKeySelect, self.IMG)

		self._drawIMG()
		
		self.lock.wait()

	def OnUpdate(self, rect):

		self.canvas.blit(self.img)
		self.canvas.rectangle([(self.p+(42*self.x), 36*self.y), (self.p+(42*self.x)+42, (36*self.y)+36)], width=2, outline=0x123456)

	def move(self, x, y):

		self.x = (self.x+x)%4
		self.y = (self.y+y)

		if x == 1: self.p = (self.p+2)%8
		if x == -1: self.p = (self.p-2)%8

		if self.y == 4:
			if self.currpages < self.pages-1:
				self.y = 0
				self.currpages += 1
				self._drawIMG(start=self.currpages)
			else:
				self.y = 3
			
		if self.y == -1:
			if self.currpages > 0:
				self.y = 3
				self.currpages -= 1
				self._drawIMG(start=self.currpages)
			else:
				self.y = 0
	
		self.mpath = (4*self.y + self.x)+(16*self.currpages)
		
		self.OnUpdate(None)
	
	def IMG(self):

		try:
			m = self.listFile[self.mpath].replace('_PalbTN\\', '')
			appuifw.Content_handler().open(m)
		except:
			pass
		
	def _drawIMG(self, start=0):

		self.img.clear(0xffffff)
		z = 0
		
		for id in range(start*16, (start+1)*16):
			j, i = divmod(id-(start*16), 4)
			try:
				self.img_tmp.load(self.listFile[id])
				self.img.blit(self.img_tmp, target=(z+(42*i)+(z+1), 36*j))
				z = (z+1)%4
			except:
				break

		self.OnUpdate(None)

	def _createList(self):

		try:
			for id in os.listdir(self.path):
				self.listFile.append(self.path + id)

			self.ldivx, self.ldivy = divmod(len(self.listFile), 16)

			self.pages = self.ldivx
			if self.ldivy <> 0: self.pages += 1
		except:
			raise FlickrS60Error('Errore nella creazione della lista.')

if __name__ == '__main__':

	FlickrS60Thumb('E:\\Images\\_PalbTN\\').OnRun()

Gallery thumbnails

from appuifw import *
from graphics import Image
from key_codes import *
#from status import *
#from e32db import format_time
import os, e32

dir = u'C:\\Nokia\\Images\\_PAlbTN\\'
os.chdir(dir)
fs = os.listdir('')
mtime = os.path.getmtime
# newest first
fs.sort(lambda a,b: cmp(mtime(b), mtime(a)))

app.body = canvas = Canvas()
# show just 16 images
for k in range(min(16, len(fs))):
    j, i = divmod(k, 4)
    im = Image.open(dir + fs[k])
    canvas.blit(im, target=(2+44*i, 2+34*j))
canvas.rectangle([(0,0), (43,33)], 0xff, width=2)  # selected

x, y, k = 0, 0, 0
def move(dx, dy):
    global x, y, k
    canvas.rectangle([(44*x,34*y), (44*x+43,34*y+33)], 0xffffff, width=2)  
    k = 4*y + x + 4*dy + dx
    y, x = divmod(k, 4)
    canvas.rectangle([(44*x,34*y), (44*x+43,34*y+33)], 0xff, width=2)
    if 0 <= k < len(fs):
        app.title = u''+fs[k]
        #status_on(format_time(mtime(fs[k])))

# move cursor and open image
canvas.bind(EKeyUpArrow,   lambda: move(0,-1))
canvas.bind(EKeyDownArrow, lambda: move(0,1))
canvas.bind(EKeyLeftArrow, lambda: move(-1,0))
canvas.bind(EKeyRightArrow,lambda: move(1,0))
canvas.bind(EKeySelect,    lambda: Content_handler().open(dir[:-8]+fs[k]))

# standard code for non-loop app
lock = e32.Ao_lock()
app.exit_key_handler = lock.signal
lock.wait()

Wrap text to fit canvas screen

Pys60 provide you with 3 types for app.body
- Text
- ListBox
- Canvas

Sometimes you want some text and image together, you need to
use canvas. However, there's no way to calculate the length
of text and wrap them properly. Simo's dashboard provide a
solution to this using his akntextutils C++ extension.
from akntextutils import wrap_text_to_array

# long_str is a long string to be wrapped
lines = wrap_text_to_array(long_str, 'dense', 176)

x, y = 2, 0
for line in lines:
   y += 14
   canvas.text((x, y), line, font='dense')

Canvas and its callbacks in OO code

I learn to use 2 different types of Canvas callbacks
in the last snippet.

Typically, when I wrote a non-OO code, I will use
app.body = c = Canvas()
where I already had
from appuifw import *


The shortcoming is that I need to define callbacks first,
then pass it to the constructor
c = Canvas(redraw_callback, event_callback)
By using OO, the canvas is created in __init__() and it
can access other methods that come later in the code.
In this case, I use Canvas(self.update) which means that
the self.update will be used to redraw screen.

The secode way to use callback is Canvas.bind() method.
I have always been using this approach to binding any event
callback to a canvas. In some case, the event_callback in
the constructor maybe more elegant, though.

Notice my use of
self.canvas.bind(EKeySelect, self.toggle)

Here I can bind the select key to self.toggle whose definition
will follow. This is more convenient than having to define
it first. So, I think OO code is easier to write in this way.

I also use class variables instead of instance variables.
I found declaring it outside __init__() is more natural
and similar to my previous non-OO approach.
(still easy to read, with variable & def declarations)
When I write self.myvar inside __init__(), I feel the code
is somewhat bloated. The class will have only 1 instance
anyway.

Graphical Plotter //Javascript Class



[UPDATED CODE AND HELP CAN BE FOUND HERE]



An unuseful thing to draw using javascript, it's slow as hell :)

//+ Jonas Raoni Soares Silva
//@ http://jsfromhell.com/dhtml/graphical-plotter [v1.0]

Canvas = function(){
	var o = this;
	( o.penPos = { x: 0, y: 0 }, o.pixelSize = 10, o.pen = { style: "solid", size: 1, color: "#000" }, o.brush = { style: "solid", color: "#000" } );
};
with( { p: Canvas.prototype } ){
	p.pixel = function( x, y, color ) {
		var o = this, s = document.body.appendChild( document.createElement( "div" ) ).style;
		return ( s.position = "absolute", s.width = ( o.pen.size * o.pixelSize ) + "px", s.height = ( o.pen.size * o.pixelSize ) + "px", s.fontSize = "1px", s.left = ( x * o.pixelSize ) + "px", s.top = ( y * o.pixelSize ) + "px", s.backgroundColor = color || o.pen.color, o );
	};
	p.line = function( x1, y1, x2, y2 ){
		if( Math.abs( x1 - x2 ) < Math.abs( y1 - y2 ) )
			for( y = Math.min( y1, y2 ) - 1, x = Math.max( y1, y2 ); ++y <= x; canvas.pixel( ( y * ( x1 - x2 ) - x1 * y2 + y1 * x2 ) / ( y1 - y2 ), y ) );
		else
			for( x = Math.min( x1, x2 ) - 1, y = Math.max( x1, x2 ); ++x <= y; canvas.pixel( x, ( x * ( y1 - y2 ) - y1 * x2 + x1 * y2 ) / ( x1 - x2 ) ) );
		return this;
	};
	p.arc = function( x, y, raio, startAngle, degrees ) {
		for( degrees += startAngle; degrees --> startAngle; this.pixel( Math.cos( degrees * Math.PI / 180 ) * raio + x, Math.sin( degrees * Math.PI / 180 ) * raio + y ) ); return this;
	};
	p.rectangle = function( x, y, width, height, rotation ){
		return this.moveTo( x, y ).lineBy( 0, height ).lineBy( width, 0 ).lineBy( 0, -height ).lineBy( -width, 0 );
	};
	p.moveTo = function( x, y ){ var o = this; return ( o.penPos.x = x, o.penPos.y = y, o ); };
	p.moveBy = function( x, y ){ var o = this; return o.moveTo( o.penPos.x + x, o.penPos.y + y ); };
	p.lineTo = function( x, y ){ var o = this; return o.line( o.penPos.x, o.penPos.y, x, y ).moveTo( x, y ); };
	p.lineBy = function( x, y ){ var o = this; return o.lineTo( o.penPos.x + x, o.penPos.y + y ); };
	p.curveTo = function( cx, cy, x, y ){};
	p.polyBezier = function( points ){};
	p.path = function( points ){};
}



Example:

canvas = new Canvas;

canvas.pen.color = "#f00";
canvas.rectangle( 30, 20, 20, 20 );
canvas.pen.color = "#080";
canvas.rectangle( 35, 25, 10, 10 );
canvas.pen.color = "#008";
canvas.arc( 50, 30, 10, 180, 270 );
canvas.arc( 30, 30, 10, 0, 270 );
canvas.pen.color = "#ff0";

Working with both Text and Canvas

In some applications, you need to write some code
in the input text, while the result is display on
a canvas display. For PC apps, you can just make
a two-pane display.

On pys60, however, the phone can display only
either a Canvas, a Text or a Listbox at the same time.
You cannot use two-pane interface.

The following code works around this by switching
between two displays.
from appuifw import *
import e32
sleep = e32.ao_sleep

t = Text()
c = Canvas()

running = 1
def quit():
    global running
    running = 0
app.exit_key_handler = quit

while running:
    app.body = t
    sleep(5)
    # show result
    app.body = c
    c.clear()
    c.text((10, 50), t.get())
    sleep(0.5)

M Clock on pys60

See this article in Guido's blog
http://www.artima.com/weblogs/viewpost.jsp?thread=122250
I then try to implement M Clock on pys60. I remove a few
things to make the code short.
from __future__ import division
from appuifw import *
import math, time, e32

app.body = c = Canvas()

radius = 72
bigsize = radius * .975
litsize = radius * .67
mx, my = 88, 72
N = 9   # 2,3,4,5,6, 32, 128

def draw(hh, mm, ss, colors=(0, 1, 2)):
    # Set bigd, litd to angles in degrees for big, little hands
    # 12 => 90, 3 => 0, etc.
    bigd = (90 - (mm*60 + ss) / 10) % 360
    litd = (90 - (hh*3600 + mm*60 + ss) / 120) % 360
    # Set bigr, litr to the same values in radians
    bigr = bigd * math.pi / 180
    litr = litd * math.pi / 180
    # Draw the background colored arcs
    drawbg(bigd, litd, colors)
    # Draw the hands
    c.line([mx, my, 
            mx + bigsize*math.cos(bigr),
            my - bigsize*math.sin(bigr)],
            0, width = radius/50)
    c.line([mx, my, 
            mx + litsize*math.cos(litr),
            my - litsize*math.sin(litr)],
            0, width = radius/33)
    # Draw the text
    c.text([5, 144-5], u"%02d:%02d:%02d" % (hh, mm, ss), 0xffffff)

def drawbg(bigd, litd, colors=(0, 1, 2)):
    c.clear(0)
    table = []
    for angle, colorindex in [(bigd - 180/N, 0),
                              (litd - 180/N, 1),
                              (  90 - 180/N, 2)]:
        angle %= 360
        for i in range(N):
            color = 255
            if colorindex in colors:
                color = (N-1-i)*color//(N-1)
            table.append((angle, color, colorindex))
            angle += 360/N
            if angle >= 360:
                angle -= 360
                table.append((0, color, colorindex))
    table.sort()
    table.append((360, None))
    fill = [0, 0, 0]
    for i in range(len(table)-1):
        angle, color, colorindex = table[i]
        fill[colorindex] = color
        if angle < 359:     # for bug when 359==360==0
            c.pieslice([mx-radius,my-radius,mx+radius,my+radius], 
                      angle * math.pi/180, 0,    # start, end
                      fill=tuple(fill), width=0)
    c.line([mx+1, my, mx+radius-1, my], tuple(fill))  # complete at 360 deg

running = 1
def quit():
    global running
    running = 0
app.exit_key_handler= quit

while running:  # redraw loop
    t = time.time() + time.clock()%1    # time() lack decimal precision
    hh, mm, ss = time.localtime(t)[3:6] # +7*60*60
    draw(hh, mm, ss, (0,1,2))
    e32.ao_sleep(1-t%1)

You can see the sceenshot from here.
http://flickr.com/photos/korakot/32337789/

Using Icon as Image

Pys60 1.1.3 have 2 differnt classes for graphics data.
Icon class represents icon (typically from .mbm file)
which can be put in ListBox for selection.
Image class represents a bigger image which can be
drawn upon. These 2 classes can't convert to/from
each other.

So, I create a library that read .mbm file and draw
an Image from the data there. So, you can make
an icon into an image (now only 1-bit icons).
the module can be downloaded from here
http://larndham.net/service/pys60/icon_image.py
from appuifw import *
import icon_image, e32

app.body = c = Canvas()
# choose a bitmap from plenty inside mbm (multi-bitmap)
icon = icon_image('z:\\system\\data\\avkon.mbm', 28) 
c.blit(icon)

e32.ao_sleep(10)  # 10 sec to end program

Look here for more information.
http://discussion.forum.nokia.com/forum/showthread.php?s=&threadid=63608

Camera preview

Taken (will some mod.) from
http://discussion.forum.nokia.com/forum/showthread.php?s=&threadid=63464

pys60 (the full name is python for series 60) 1.1.3
provide both camera and graphics display.
So, it is trivial to take photo and preview.
from appuifw import *
import camera

canvas=Canvas()
app.body=canvas

running=1
def quit():
    global running
    running=0
app.exit_key_handler=quit

while running:
    image = camera.take_photo(size= (160,120))
    canvas.blit(image, target=(8, 12, 168, 132))  # center it

Here I use the small size (160x120) for preview.
When the real photo is taken I can use the full (defualt)
size of (640x480) on my 6600 phone.

15-square game

py_s60 1.1.3 was released a week ago.
I wonder why there's no more people playing with it.
So, I have created a simple game as an example.

I don't know what this game is called. It has 4x4 square box
with 15 pieces (1 piece missing). You need to move all the
pieces into sorting order.

Since the program is so simple, I decided to make the
moving of a piece smoother by moving it bit by bit.
Hope this doesn't make the code to hard to read.

from appuifw import *
from key_codes import *
import e32, random

# run and break-loop type of app
sleep = e32.ao_sleep
running = 1
def set_exit():
global running
running = 0
app.exit_key_handler= set_exit

# canvas and typical colors
c = Canvas()
app.body = c
red, green, blue, gray, white = 0xff0000, 0x00ff00, 0x0000ff, 0x777777, 0xffffff

# randomize number order for pieces
seq = range(1,17)
random.shuffle(seq)
b = [seq[0:4], seq[4:8], seq[8:12], seq[12:16]]

def piece(i, j, n):
if n < 10:
c.text( (12+20*i, 20+20*j), unicode(n))
else:
c.text( (7+20*i, 20+20*j), unicode(n))

def box(i, j, color, fill=None):
c.rectangle( [5+20*i, 5+20*j, 25+20*i, 25+20*j], color, fill)

# draw board pieces
for k in range(16):
j, i = divmod(k, 4)
piece(i, j, b[j][i])

y, x = divmod(seq.index(16), 4)
box(x, y, white, white)
moving = 0 # cursor to lock if animating

# move cursor in dx, dy direction
def move(dx, dy):
global x,y, moving
if moving:
return
moving = 1
if 0 <= x-dx < 4 and 0 <= y-dy < 4:
b[y][x] = b[y-dy][x-dx]
animate(x-dx, y-dy, dx, dy, b[y][x])
x -= dx # the hole move in opposite direction
y -= dy
moving = 0

# moving a piece for x,y to dx, dy direction
def animate(x, y, dx, dy, n):
if n < 10:
px = 12
else:
px = 7
for i in range(5):
c.text( (px+20*x + 4*i*dx, 20+20*y + 4*i*dy), unicode(n))
sleep(0.05)
c.text( (px+20*x + 4*i*dx, 20+20*y + 4*i*dy), unicode(n), white)
c.text( [px+20*(x+dx), 20+20*(y+dy)], unicode(n) )

# bind arrow keys
c.bind(EKeyRightArrow,lambda:move(1, 0))
c.bind(EKeyLeftArrow,lambda:move(-1, 0))
c.bind(EKeyUpArrow,lambda:move(0, -1))
c.bind(EKeyDownArrow,lambda:move(0, 1))

# main loop, just wait
while running:
sleep(0.1)
« Newer Snippets
Older Snippets »
Showing 1-10 of 13 total  RSS