Examples

If you downloaded a source archive or cloned pySFML from github, these examples will be located in the examples subdirectory of the project’s root. A package named ‘pysfml-examples’ is also available for Debian-based Linux distributions, which allows you to run arbitrary examples by invoking a command of the following form from a terminal:

pysfml-<example name>

For example:

pysfml-sound

Ftp

  1import os
  2import sfml.network as sf
  3
  4# python 2.* compatability
  5try: input = raw_input
  6except NameError: pass
  7
  8# choose the server address
  9address = input("Enter the FTP server address: ")
 10address = sf.IpAddress.from_string(address)
 11
 12# create the server object which with you will communicate
 13server = sf.Ftp()
 14
 15# connect to the server
 16response = server.connect(address)
 17print(response)
 18if not response.ok: exit()
 19
 20# ask for user name and password
 21user = input("User name: ")
 22password = input("Password: ")
 23
 24# login to the server
 25response = server.login(user, password)
 26print(response)
 27if not response.ok: exit()
 28
 29# main menu
 30choice = 0
 31while True:
 32    print("===========================================================")
 33    print("Choose an action:")
 34    print("1. Print working directory")
 35    print("2. Print contents of working directory")
 36    print("3. Change directory")
 37    print("4. Create directory")
 38    print("5. Delete directory")
 39    print("6. Rename file")
 40    print("7. Remove file")
 41    print("8. Download file")
 42    print("9. Upload file")
 43    print("0. Disconnect\n\n")
 44
 45    choice = int(input("Your choice: "))
 46
 47    os.system('clear')
 48
 49    if choice == 1:
 50        # print the current server directory
 51        response = server.get_working_directory()
 52        print(response)
 53        print("Current directory is {0}".format(response.get_directory()))
 54    elif choice == 2:
 55        # print the contents of the current server directory
 56        response = server.get_directory_listing()
 57        print(response)
 58        for filename in response.filenames:
 59            print(filename)
 60    elif choice == 3:
 61        # change the current directory
 62        directory = input("Choose a directory: ")
 63        response = server.change_directory(directory)
 64        print(response)
 65    elif choice == 4:
 66        # create a new directory
 67        directory = input("Name of the directory to create: ")
 68        response = server.create_directory(directory)
 69        print(response)
 70    elif choice == 5:
 71        # remove an existing directory
 72        directory = input("Name of the directory to remove: ")
 73        response = server.delete_directory(directory)
 74        print(response)
 75    elif choice == 6:
 76        # rename a file
 77        source = input("Name of the file to rename: ")
 78        destination = input("New name: ")
 79        response = server.rename_file(source, destination)
 80        print(response)
 81    elif choice == 7:
 82        # remove an existing directory
 83        filename = input("Name of the file to remove: ")
 84        response = server.delete_file(filename)
 85        print(response)
 86    elif choice == 8:
 87        # download a file from server
 88        filename = input("Filename of the file to download (relative to current directory): ")
 89        directory = input("Directory to download the file to: ")
 90        response = server.download(filename, directory)
 91        print(response)
 92    elif choice == 9:
 93        # upload a file to server
 94        filename = input("Path of the file to upload (absolute or relative to working directory): ")
 95        directory = input("Directory to upload the file to (relative to current directory): ")
 96        response = server.upload(filename, directory)
 97        print(response)
 98    elif choice == 0:
 99        break
100    else:
101        # wrong choice
102        print("Invalid choice!")
103        os.system('clear')
104
105    if choice == 0:
106        break
107
108# disconnect from the server
109print("Disconnecting from server...")
110response = server.disconnect()
111
112# wait until the user presses 'enter' key
113input("Press enter to exit...")

Pong

  1from __future__ import division
  2
  3from math import cos, sin, fabs, pi
  4from random import randint
  5
  6from sfml import sf
  7
  8
  9# define some constants
 10game_size = sf.Vector2(800, 600)
 11paddle_size = sf.Vector2(25, 100)
 12ball_radius = 10.
 13
 14# create the window of the application
 15w, h = game_size
 16window = sf.RenderWindow(sf.VideoMode(w, h), "pySFML - Pong")
 17window.vertical_synchronization = True
 18
 19# load the sounds used in the game
 20ball_sound_buffer = sf.SoundBuffer.from_file("data/ball.wav")
 21ball_sound = sf.Sound(ball_sound_buffer)
 22
 23# create the left paddle
 24left_paddle = sf.RectangleShape()
 25left_paddle.size = paddle_size - (3, 3)
 26left_paddle.outline_thickness = 3
 27left_paddle.outline_color = sf.Color.BLACK
 28left_paddle.fill_color = sf.Color(100, 100, 200)
 29left_paddle.origin = paddle_size / 2
 30
 31# create the right paddle
 32right_paddle = sf.RectangleShape()
 33right_paddle.size = paddle_size - (3, 3)
 34right_paddle.outline_thickness = 3
 35right_paddle.outline_color = sf.Color.BLACK
 36right_paddle.fill_color = sf.Color(200, 100, 100)
 37right_paddle.origin = paddle_size / 2
 38
 39# create the ball
 40ball = sf.CircleShape()
 41ball.radius = ball_radius - 3
 42ball.outline_thickness = 3
 43ball.outline_color = sf.Color.BLACK
 44ball.fill_color = sf.Color.WHITE
 45ball.origin = (ball_radius / 2, ball_radius / 2)
 46
 47# load the font
 48font = sf.Font.from_file("data/sansation.ttf")
 49
 50# initialize the pause message
 51pause_message = sf.Text()
 52pause_message.font = font
 53pause_message.character_size = 40
 54pause_message.position = (170, 150)
 55pause_message.color = sf.Color.WHITE
 56pause_message.string = "Welcome to pySFML pong!\nPress space to start the game"
 57
 58# define the paddles properties
 59ai_timer = sf.Clock()
 60ai_time = sf.seconds(0.1)
 61paddle_speed = 400.
 62right_paddle_speed = 0.
 63ball_speed = 400.
 64ball_angle = 0. # to be changed later
 65
 66clock = sf.Clock()
 67is_playing = False
 68
 69while window.is_open:
 70
 71    # handle events
 72    for event in window.events:
 73        # window closed or escape key pressed: exit
 74        if type(event) is sf.CloseEvent:
 75            window.close()
 76
 77        # space key pressed: play
 78        if type(event) is sf.KeyEvent and event.pressed and event.code is sf.Keyboard.SPACE:
 79            if not is_playing:
 80                # (re)start the game
 81                is_playing = True
 82                clock.restart()
 83
 84                # reset the position of the paddles and ball
 85                left_paddle.position = (10 + paddle_size.x / 2, game_size.y / 2)
 86                right_paddle.position = (game_size.x - 10 - paddle_size.x / 2, game_size.y / 2)
 87                ball.position = game_size / 2
 88
 89                # reset the ball angle
 90                while True:
 91                    # make sure the ball initial angle is not too much vertical
 92                    ball_angle = (randint(0, 32767) % 360) * 2 * pi / 360
 93                    if not fabs(cos(ball_angle)) < 0.7: break
 94
 95    if is_playing:
 96        delta_time = clock.restart().seconds
 97
 98        # move the player's paddle
 99        if sf.Keyboard.is_key_pressed(sf.Keyboard.UP) and left_paddle.position.y - paddle_size.y / 2 > 5:
100            left_paddle.move((0, -paddle_speed * delta_time))
101
102        elif sf.Keyboard.is_key_pressed(sf.Keyboard.DOWN) and left_paddle.position.y + paddle_size.y / 2 < game_size.y - 5:
103            left_paddle.position += (0, paddle_speed * delta_time)
104
105        # move the computer' paddle
106        if (right_paddle_speed < 0 and right_paddle.position.y - paddle_size.x / 2 > 5) or (right_paddle_speed > 0 and right_paddle.position.y + paddle_size.y / 2 < game_size.y - 5):
107            right_paddle.position += (0, right_paddle_speed * delta_time)
108
109
110        # update the computer's paddle direction according to the ball position
111        if ai_timer.elapsed_time > ai_time:
112            ai_timer.restart()
113            if ball.position.y + ball_radius > right_paddle.position.y + paddle_size.y / 2:
114                right_paddle_speed = paddle_speed
115            elif ball.position.y - ball_radius < right_paddle.position.y - paddle_size.y / 2:
116                right_paddle_speed = - paddle_speed
117            else:
118                right_paddle_speed = 0
119
120        # move the ball
121        factor = ball_speed * delta_time
122        ball.move((cos(ball_angle) * factor, sin(ball_angle) * factor))
123
124        # check collisions between the ball and the screen
125        if ball.position.x - ball_radius < 0:
126            is_playing = False
127            pause_message.string = "You lost!\nPress space to restart or\nescape to exit"
128
129        if ball.position.x + ball_radius > game_size.x:
130            is_playing = False
131            pause_message.string = "You won !\nPress space to restart or\nescape to exit"
132
133        if ball.position.y - ball_radius < 0:
134            ball_sound.play()
135            ball_angle = - ball_angle
136            ball.position.y = ball_radius + 0.1
137
138        if ball.position.y + ball_radius > game_size.y:
139            ball_sound.play()
140            ball_angle = - ball_angle
141            ball.position.y = game_size.y - ball_radius - 0.1
142
143        # check the collisions between the ball and the paddles
144        # left paddle
145        if ball.position.x - ball_radius < left_paddle.position.x + paddle_size.x / 2 and ball.position.x - ball_radius > left_paddle.position.x and ball.position.y + ball_radius >= left_paddle.position.y - paddle_size.y / 2 and ball.position.y - ball_radius <= left_paddle.position.y + paddle_size.y / 2:
146            if ball.position.y > left_paddle.position.y:
147                ball_angle = pi - ball_angle + (randint(0, 32767) % 20) * pi / 180
148            else:
149                ball_angle = pi - ball_angle - (randint(0, 32767) % 20) * pi / 180
150
151            ball_sound.play()
152            ball.position = (left_paddle.position.x + ball_radius + paddle_size.x / 2 + 0.1, ball.position.y)
153
154        # right paddle
155        if ball.position.x + ball_radius > right_paddle.position.x - paddle_size.x / 2 and ball.position.x + ball_radius < right_paddle.position.x and ball.position.y + ball_radius >= right_paddle.position.y - paddle_size.y / 2 and ball.position.y - ball_radius <= right_paddle.position.y + paddle_size.y / 2:
156            if ball.position.y > right_paddle.position.y:
157                ball_angle = pi - ball_angle + (randint(0, 32767) % 20) * pi / 180
158            else:
159                ball_angle = pi - ball_angle - (randint(0, 32767) % 20) * pi / 180
160
161            ball_sound.play()
162            ball.position = (right_paddle.position.x - ball_radius - paddle_size.x / 2 - 0.1, ball.position.y)
163
164    window.clear(sf.Color(50, 200, 50))
165
166    if is_playing:
167        # draw the paddles and the ball
168        window.draw(left_paddle)
169        window.draw(right_paddle)
170        window.draw(ball)
171
172    else:
173        # draw the pause message
174        window.draw(pause_message)
175
176    # display things on screen
177    window.display()

PyQt4

 1import sys, platform
 2
 3try:
 4    import sip
 5    from PyQt4.QtCore import *
 6    from PyQt4.QtGui import *
 7except ImportError:
 8    print("Install PyQt4 and sip from Riverbank.")
 9
10from sfml import sf
11
12
13class QSFMLCanvas(QWidget):
14    def __init__(self, parent, position, size, frameTime=0):
15        QWidget.__init__(self, parent)
16        self.initialized = False
17
18        w = size.width()
19        h = size.height()
20
21        self._HandledWindow = sf.HandledWindow()
22        self._HandledWindow.view.size = (w, h)
23        self.__dict__['draw'] = self._HandledWindow.draw
24        self.__dict__['clear'] = self._HandledWindow.clear
25        self.__dict__['view'] = self._HandledWindow.view
26        self.__dict__['display'] = self._HandledWindow.display
27
28        # setup some states to allow direct rendering into the widget
29        self.setAttribute(Qt.WA_PaintOnScreen)
30        self.setAttribute(Qt.WA_OpaquePaintEvent)
31        self.setAttribute(Qt.WA_NoSystemBackground)
32
33        # set strong focus to enable keyboard events to be received
34        self.setFocusPolicy(Qt.StrongFocus);
35
36        # setup the widget geometry
37        self.move(position);
38        self.resize(size);
39
40        # setup the timer
41        self.timer = QTimer()
42        self.timer.setInterval(frameTime)
43
44    def onInit(self): pass
45
46    def onUpdate(self): pass
47
48    def sizeHint(self):
49        return self.size()
50
51    def paintEngine(self):
52        # let the derived class do its specific stuff
53        self.onUpdate()
54
55        # display on screen
56        self.display()
57
58    def showEvent(self, event):
59        if not self.initialized:
60            # under X11, we need to flush the commands sent to the server
61            # to ensure that SFML will get an updated view of the windows
62            # create the SFML window with the widget handle
63            if platform.system() == 'Linux':
64                from ctypes import cdll
65                x11 = cdll.LoadLibrary("libX11.so")
66
67                display = sip.unwrapinstance(QX11Info.display())
68                x11.XFlush(display)
69
70            self._HandledWindow.create(self.winId())
71
72            # let the derived class do its specific stuff
73            self.onInit()
74
75            # setup the timer to trigger a refresh at specified framerate
76            self.connect(self.timer,SIGNAL('timeout()'), self, SLOT('repaint()'))
77            self.timer.start()
78
79            self.initialized = True
80
81    def paintEvent(self, event):
82        return None

Shader

  1from __future__ import division
  2
  3from random import randint
  4from math import cos
  5
  6from sfml import sf
  7
  8class Effect(sf.Drawable):
  9    def __init__(self, name):
 10        sf.Drawable.__init__(self)
 11
 12        self._name = name
 13        self.is_loaded = False
 14
 15    def _get_name(self):
 16        return self._name
 17
 18    def load(self):
 19        self.is_loaded = sf.Shader.is_available() and self.on_load()
 20
 21    def update(self, time, x, y):
 22        if self.is_loaded:
 23            self.on_update(time, x, y)
 24
 25    def draw(self, target, states):
 26        if self.is_loaded:
 27            self.on_draw(target, states)
 28        else:
 29            error = sf.Text("Shader not\nsupported")
 30            error.font = sf.Font.from_file("data/sansation.ttf")
 31            error.position = (320, 200)
 32            error.character_size = 36
 33            target.draw(error, states)
 34
 35    name = property(_get_name)
 36
 37class Pixelate(Effect):
 38    def __init__(self):
 39        Effect.__init__(self, 'pixelate')
 40
 41    def on_load(self):
 42        try:
 43            # load the texture and initialize the sprite
 44            self.texture = sf.Texture.from_file("data/background.jpg")
 45            self.sprite = sf.Sprite(self.texture)
 46
 47            # load the shader
 48            self.shader = sf.Shader.from_file(fragment="data/pixelate.frag")
 49            self.shader.set_parameter("texture")
 50
 51        except IOError as error:
 52            print("An error occured: {0}".format(error))
 53            exit(1)
 54
 55        return True
 56
 57    def on_update(self, time, x, y):
 58        self.shader.set_parameter("pixel_threshold", (x + y) / 30)
 59
 60    def on_draw(self, target, states):
 61        states.shader = self.shader
 62        target.draw(self.sprite, states)
 63
 64
 65class WaveBlur(Effect):
 66    def __init__(self):
 67        Effect.__init__(self, 'wave + blur')
 68
 69    def on_load(self):
 70        with open("data/text.txt") as file:
 71            self.text = sf.Text(file.read())
 72            self.text.font = sf.Font.from_file("data/sansation.ttf")
 73            self.text.character_size = 22
 74            self.text.position = (30, 20)
 75
 76        try:
 77            # load the shader
 78            self.shader = sf.Shader.from_file("data/wave.vert", "data/blur.frag")
 79
 80        except IOError as error:
 81            print("An error occured: {0}".format(error))
 82            exit(1)
 83
 84        return True
 85
 86    def on_update(self, time, x, y):
 87        self.shader.set_parameter("wave_phase", time)
 88        self.shader.set_parameter("wave_amplitude", x * 40, y * 40)
 89        self.shader.set_parameter("blur_radius", (x + y) * 0.008)
 90
 91    def on_draw(self, target, states):
 92        states.shader = self.shader
 93        target.draw(self.text, states)
 94
 95
 96class StormBlink(Effect):
 97    def __init__(self):
 98        Effect.__init__(self, 'storm + blink')
 99
100        self.points = sf.VertexArray()
101
102    def on_load(self):
103        # create the points
104        self.points.primitive_type = sf.PrimitiveType.POINTS
105
106        for i in range(40000):
107            x = randint(0, 32767) % 800
108            y = randint(0, 32767) % 600
109            r = randint(0, 32767) % 255
110            g = randint(0, 32767) % 255
111            b = randint(0, 32767) % 255
112            self.points.append(sf.Vertex(sf.Vector2(x, y), sf.Color(r, g, b)))
113
114        try:
115            # load the shader
116            self.shader = sf.Shader.from_file("data/storm.vert", "data/blink.frag")
117
118        except IOError as error:
119            print("An error occured: {0}".format(error))
120            exit(1)
121
122        return True
123
124    def on_update(self, time, x, y):
125        radius = 200 + cos(time) * 150
126        self.shader.set_parameter("storm_position", x * 800, y * 600)
127        self.shader.set_parameter("storm_inner_radius", radius / 3)
128        self.shader.set_parameter("storm_total_radius", radius)
129        self.shader.set_parameter("blink_alpha", 0.5 + cos(time*3) * 0.25)
130
131    def on_draw(self, target, states):
132        states.shader = self.shader
133        target.draw(self.points, states)
134
135class Edge(Effect):
136    def __init__(self):
137        Effect.__init__(self, "edge post-effect")
138
139    def on_load(self):
140        # create the off-screen surface
141        self.surface = sf.RenderTexture(800, 600)
142        self.surface.smooth = True
143
144        # load the textures
145        self.background_texture = sf.Texture.from_file("data/sfml.png")
146        self.background_texture.smooth = True
147
148        self.entity_texture = sf.Texture.from_file("data/devices.png")
149        self.entity_texture.smooth = True
150
151        # initialize the background sprite
152        self.background_sprite = sf.Sprite(self.background_texture)
153        self.background_sprite.position = (135, 100)
154
155        # load the moving entities
156        self.entities = []
157
158        for i in range(6):
159            sprite = sf.Sprite(self.entity_texture, (96 * i, 0, 96, 96))
160            self.entities.append(sprite)
161
162        # load the shader
163        self.shader = sf.Shader.from_file(fragment="data/edge.frag")
164        self.shader.set_parameter("texture")
165
166        return True
167
168    def on_update(self, time, x, y):
169        self.shader.set_parameter("edge_threshold", 1 - (x + y) / 2)
170
171        # update the position of the moving entities
172        for i, entity in enumerate(self.entities):
173            x = cos(0.25 * (time * i + (len(self.entities) - i))) * 300 + 350
174            y = cos(0.25 * (time * (len(self.entities) - i) + i)) * 200 + 250
175            entity.position = (x, y)
176
177        # render the updated scene to the off-screen surface
178        self.surface.clear(sf.Color.WHITE)
179        self.surface.draw(self.background_sprite)
180
181        for entity in self.entities:
182            self.surface.draw(entity)
183
184        self.surface.display()
185
186    def on_draw(self, target, states):
187        states.shader = self.shader
188        target.draw(sf.Sprite(self.surface.texture), states)
189
190
191if __name__ == "__main__":
192    # create the main window
193    window = sf.RenderWindow(sf.VideoMode(800, 600), "pySFML - Shader")
194    window.vertical_synchronization = True
195
196    # create the effects
197    effects = (Pixelate(), WaveBlur(), StormBlink(), Edge())
198    current = 0
199
200    # initialize them
201    for effect in effects: effect.load()
202
203    # create the message background
204    try:
205        text_background_texture = sf.Texture.from_file("data/text-background.png")
206
207    except IOError as error:
208        print("An error occured: {0}".format(error))
209        exit(1)
210
211    text_background = sf.Sprite(text_background_texture)
212    text_background.position = (0, 520)
213    text_background.color = sf.Color(255, 255, 255, 200)
214
215    # load the messages font
216    try:
217        font = sf.Font.from_file("data/sansation.ttf")
218
219    except IOError as error:
220        print("An error occured: {0}".format(error))
221        exit(1)
222
223    # create the description text
224    description = sf.Text("Current effect: {0}".format(effects[current].name), font, 20)
225    description.position = (10, 530)
226    description.color = sf.Color(80, 80, 80)
227
228    # create the instructions text
229    instructions = sf.Text("Press left and right arrows to change the current shader", font, 20)
230    instructions.position = (280, 555)
231    instructions.color = sf.Color(80, 80, 80)
232
233    clock = sf.Clock()
234
235    # start the game loop
236    while window.is_open:
237
238        # update the current example
239        x, y = sf.Mouse.get_position(window) / window.size
240        effects[current].update(clock.elapsed_time.seconds, x, y)
241
242        # process events
243        for event in window.events:
244
245            # close window: exit
246            if type(event) is sf.CloseEvent:
247                window.close()
248
249            if type(event) is sf.KeyEvent and event.pressed:
250                # escapte key: exit
251                if event.code == sf.Keyboard.ESCAPE:
252                    window.close()
253
254                # left arrow key: previous shader
255                elif event.code is sf.Keyboard.LEFT:
256                    if current == 0: current = len(effects) - 1
257                    else: current -= 1
258
259                    description.string = "Current effect: {0}".format(effects[current].name)
260
261                # right arrow key: next shader
262                elif event.code is sf.Keyboard.RIGHT:
263                    if current == len(effects) - 1: current = 0
264                    else: current += 1
265
266                    description.string = "Current effect: {0}".format(effects[current].name)
267
268
269        # clear the window
270        window.clear(sf.Color(255, 128, 0))
271
272        # draw the current example
273        window.draw(effects[current])
274
275        # draw the text
276        window.draw(text_background)
277        window.draw(instructions)
278        window.draw(description)
279
280        # finally, display the rendered frame on screen
281        window.display()

Sockets

  1import sfml.network as sf
  2
  3# python 2.* compatability
  4try: input = raw_input
  5except NameError: pass
  6
  7def run_tcp_server():
  8    """ Launch a server. The server waits for an incoming connection,
  9    sends a message and waits for the answer. """
 10
 11    try:
 12        # create a server socket to accept new connections
 13        listener = sf.TcpListener()
 14
 15        # listen to the given port for incoming connections
 16        listener.listen(PORT)
 17
 18        print("Server is listening to port {0}, waiting for connections...".format(PORT))
 19
 20        # wait for a connection
 21        socket = listener.accept()
 22        print("Client connected: {0}".format(socket.remote_address))
 23
 24        # send a message to the connected client
 25        message = "Hi, I'm the server"
 26        socket.send(message.encode('utf-8'))
 27        print("Message sent to the client: {0}".format(message))
 28
 29        # recieve a message back from the client
 30        answer = socket.receive(128).decode('utf-8')
 31        print("Answer received from the client: {0}".format(answer))
 32
 33    except sf.SocketException as error:
 34        print("An error occured!")
 35        print(error)
 36        return
 37
 38def run_tcp_client():
 39    """ Create a client. The client is connected to a server, displays
 40    the welcome message and sends an answer. """
 41
 42    server = input("Type the address or name of the server to connect to: ")
 43    server = sf.IpAddress.from_string(server)
 44
 45    # create a socket for communicating with the server
 46    socket = sf.TcpSocket()
 47
 48    # connect to the server
 49    try:
 50        socket.connect(server, PORT)
 51        print("Connected to server {0}".format(server))
 52
 53        # receive a message from the server
 54        message = socket.receive(128).decode('utf-8')
 55        print("Message received from the server: {0}".format(message))
 56
 57        # send an answer to the server
 58        answer = "Hi, I'm a client"
 59        socket.send(answer.encode('utf-8'))
 60        print("Message sent to the server: {0}".format(answer))
 61
 62    except sf.SocketException as error:
 63        print("An error occured!")
 64        print(error)
 65        return
 66
 67def run_udp_server():
 68    """ Launch a server. The server waits for a message then sends an
 69    answer. """
 70
 71    # create a socket to receive a message from anyone
 72    socket = sf.UdpSocket()
 73
 74    try:
 75        # listen to messages on the specified port
 76        socket.bind(PORT)
 77        print("Server is listening to port {0}, waiting for message...".format(PORT))
 78
 79        # wait for a message
 80        message, ip, port = socket.receive(128)
 81        print("Message received from client {0}: {1}".format(ip, message.decode('utf-8')))
 82
 83        # send an answer to the client
 84        answer = "Hi, I'm the server"
 85        socket.send(answer.encode('utf-8'), ip, port)
 86        print("Message sent to the client: {0}".format(answer))
 87
 88    except sf.SocketException as error:
 89        print("An error occured!")
 90        print(error)
 91        return
 92
 93def run_udp_client():
 94    """ Send a message to the server, wait for the answer. """
 95
 96    # ask for the server address
 97    server = input("Type the address or name of the server to connect to: ")
 98    server = sf.IpAddress.from_string(server)
 99
100    # create a socket for communicating with the server
101    socket = sf.UdpSocket()
102
103    try:
104        # send a message to the server
105        message = "Hi, I'm a client"
106        socket.send(message.encode('utf-8'), server, PORT)
107        print("Message sent to the server: {0}".format(message))
108
109        # receive an answer from anyone (but most likely from the server)
110        answer, ip, port = socket.receive(128)
111        print("Message received from {0}: {1}".format(ip, answer.decode('utf-8')))
112
113    except sf.SocketException as error:
114        print("An error occured!")
115        print(error)
116        return
117
118if __name__ == "__main__":
119    # choose an arbitrary port for opening sockets
120    PORT = 50001
121
122    # TCP or UDP ?
123    print("Do you want to use TCP (t) or UDP (u) ?")
124    protocol = input()
125
126    # client or server ?
127    print("Do you want to be a server (s) or a client (c) ?")
128    who = input()
129
130    if protocol == 't':
131        if who == 's': run_tcp_server()
132        else: run_tcp_client()
133    else:
134        if who == 's': run_udp_server()
135        else: run_udp_client()
136
137    input("Press any key to exit...")

Sound capture

 1from sfml import sf
 2
 3# python 2.* compatability
 4try: input = raw_input
 5except NameError: pass
 6
 7def main():
 8    # check that the device can capture audio
 9    if not sf.SoundRecorder.is_available():
10        print("Sorry, audio capture is not supported by your system")
11        return
12
13    # choose the sample rate
14    sample_rate = int(input("Please choose the sample rate for sound capture (44100 is CD quality): "))
15
16    # wait for user input...
17    input("Press enter to start recording audio")
18
19    # here we'll use an integrated custom recorder, which saves the captured data into a sf.SoundBuffer
20    recorder = sf.SoundBufferRecorder()
21
22    # audio capture is done in a separate thread, so we can block the main thread while it is capturing
23    recorder.start(sample_rate)
24    input("Recording... press enter to stop")
25    recorder.stop()
26
27    # get the buffer containing the captured data
28    buffer = recorder.buffer
29
30    # display captured sound informations
31    print("Sound information:")
32    print("{0} seconds".format(buffer.duration))
33    print("{0} samples / seconds".format(buffer.sample_rate))
34    print("{0} channels".format(buffer.channel_count))
35
36    # choose what to do with the recorded sound data
37    choice = input("What do you want to do with captured sound (p = play, s = save) ? ")
38
39    if choice == 's':
40        # choose the filename
41        filename = input("Choose the file to create: ")
42
43        # save the buffer
44        buffer.to_file(filename);
45    else:
46        # create a sound instance and play it
47        sound = sf.Sound(buffer)
48        sound.play();
49
50        # wait until finished
51        while sound.status == sf.Sound.PLAYING:
52            # leave some CPU time for other threads
53            sf.sleep(sf.milliseconds(100))
54
55    # finished !
56    print("Done !")
57
58    # wait until the user presses 'enter' key
59    input("Press enter to exit...")
60
61if __name__ == "__main__":
62    main()

Sound

 1from sfml import sf
 2
 3def play_sound():
 4    # load a sound buffer from a wav file
 5    buffer = sf.SoundBuffer.from_file("data/canary.wav")
 6
 7    # display sound informations
 8    print("canary.wav:")
 9    print("{0} seconds".format(buffer.duration))
10    print("{0} samples / sec".format(buffer.sample_rate))
11    print("{0} channels".format(buffer.channel_count))
12
13    # create a sound instance and play it
14    sound = sf.Sound(buffer)
15    sound.play();
16
17    # loop while the sound is playing
18    while sound.status == sf.Sound.PLAYING:
19        # leave some CPU time for other processes
20        sf.sleep(sf.milliseconds(100))
21
22def play_music():
23    # load an ogg music file
24    music = sf.Music.from_file("data/orchestral.ogg")
25
26    # display music informations
27    print("orchestral.ogg:")
28    print("{0} seconds".format(music.duration))
29    print("{0} samples / sec".format(music.sample_rate))
30    print("{0} channels".format(music.channel_count))
31
32    # play it
33    music.play();
34
35    # loop while the music is playing
36    while music.status == sf.Music.PLAYING:
37        # leave some CPU time for other processes
38        sf.sleep(sf.milliseconds(100))
39
40if __name__ == "__main__":
41    play_sound()
42    play_music()
43
44    input("Press enter to exit...")

Voip

 1from sfml import sf
 2import client, server
 3
 4# python 2.* compatability
 5try: input = raw_input
 6except NameError: pass
 7
 8# choose a random port for opening sockets (ports < 1024 are reserved)
 9PORT = 2435
10
11# client or server ?
12print("Do you want to be a server (s) or a client (c) ?")
13who = input()
14
15if who == 's':
16    server.do_server(PORT)
17else:
18    client.do_client(PORT)
19
20input("Press any key to exit...")
 1from sfml import sf
 2from struct import pack
 3from random import randint
 4
 5# python 2.* compatability
 6try: input = raw_input
 7except NameError: pass
 8
 9AUDIO_DATA, END_OF_STREAM = list(range(1, 3))
10
11class NetworkRecorder(sf.SoundRecorder):
12    def __init__(self, host, port):
13        sf.SoundRecorder.__init__(self)
14
15        self.host = host # address of the remote host
16        self.port = port # remote port
17        self.socket = sf.TcpSocket() # socket used to communicate with the server
18
19    def on_start(self):
20        try: self.socket.connect(self.host, self.port)
21        except sf.SocketException as error: return False
22
23        return True
24
25    def on_process_samples(self, chunk):
26        # pack the audio samples
27        data = pack("B", AUDIO_DATA)
28        data += pack("I", len(chunk.data))
29        data += chunk.data
30
31        # send the audio packet
32        try: self.socket.send(data)
33        except sf.SocketException: return False
34
35        return True
36
37    def on_stop(self):
38        # send a "end-of-stream" signal
39        self.socket.send(bytes(END_OF_STREAM))
40
41        # close the socket
42        self.socket.disconnect()
43
44def do_client(port):
45    # check that the device can capture audio
46    if not sf.SoundRecorder.is_available():
47        print("Sorry, audio capture is not supported by your system")
48        return
49
50    # ask for server address
51    server = input("Type address or name of the server to connect to: ")
52    server = sf.IpAddress.from_string(server)
53
54    # create an instance of our custom recorder
55    recorder = NetworkRecorder(server, port)
56
57    # wait for the user input...
58    input("Press enter to start recording audio")
59
60    # start capturing audio data
61    recorder.start(44100)
62    input("Recording... press enter to stop")
63    recorder.stop()
  1import threading
  2from time import sleep
  3from sfml import sf
  4from struct import unpack
  5
  6# python 2.* compatability
  7try: input = raw_input
  8except NameError: pass
  9
 10AUDIO_DATA, END_OF_STREAM = list(range(1, 3))
 11
 12class NetworkAudioStream(sf.SoundStream):
 13    def __init__(self):
 14        sf.SoundStream.__init__(self)
 15
 16        self.offset = 0
 17        self.has_finished = False
 18        self.listener = sf.TcpListener()
 19        self.samples = sf.Chunk()
 20
 21        # set the sound parameters
 22        self.initialize(1, 44100)
 23
 24    def start(self, port):
 25        if not self.has_finished:
 26            try:
 27                # listen to the given port for incoming connections
 28                self.listener.listen(port)
 29                print("Server is listening to port {0}, waiting for connections... ".format(port))
 30
 31                # wait for a connection
 32                self.client = self.listener.accept()
 33                print("Client connected: {0}".format(self.client.remote_address))
 34
 35            except sf.SocketException: return
 36
 37            # start playback
 38            self.play()
 39
 40            # start receiving audio data
 41            self.receive_loop()
 42
 43        else:
 44            # start playback
 45            self.play()
 46
 47    def on_get_data(self, chunk):
 48        # we have reached the end of the buffer and all audio data have been played : we can stop playback
 49        if self.offset >= len(self.samples) and self.has_finished:
 50            return False
 51
 52        # no new data has arrived since last update : wait until we get some
 53        while self.offset >= len(self.samples) and not self.has_finished:
 54            sf.sleep(sf.milliseconds(10))
 55
 56        # don't forget to lock as we run in two separate threads
 57        lock = threading.Lock()
 58        lock.acquire()
 59
 60        # fill audio data to pass to the stream
 61        chunk.data = self.samples.data[self.offset*2:]
 62
 63        # update the playing offset
 64        self.offset += len(chunk)
 65
 66        lock.release()
 67
 68        return True
 69
 70    def on_seek(self, time_offset):
 71        self.offset = time_offset.milliseconds * self.sample_rate * self.channel_count // 1000
 72
 73    def receive_loop(self):
 74        lock = threading.RLock()
 75
 76        while not self.has_finished:
 77            # get waiting audio data from the network
 78            data = self.client.receive(1)
 79
 80            # extract the id message
 81            id = unpack("B", data)[0]
 82
 83            if id == AUDIO_DATA:
 84                # extract audio samples from the packet, and append it to our samples buffer
 85                data = self.client.receive(4)
 86                sample_count = unpack("I", data)[0]
 87
 88                samples = self.client.receive(sample_count)
 89
 90                # don't forget the other thread can access the sample array at any time
 91                lock.acquire()
 92                self.samples.data += samples
 93                lock.release()
 94
 95            elif id == END_OF_STREAM:
 96                # end of stream reached : we stop receiving audio data
 97                print("Audio data has been 100% received!")
 98                self.has_finished = True
 99
100            else:
101                # something's wrong...
102                print("Invalid data received...")
103                self.has_finished = True
104
105def do_server(port):
106    # build an audio stream to play sound data as it is received through the network
107    audio_stream = NetworkAudioStream()
108    audio_stream.start(port)
109
110    # loop until the sound playback is finished
111    while audio_stream.status != sf.SoundStream.STOPPED:
112        # leave some CPU time for other threads
113        sf.sleep(sf.milliseconds(100))
114
115
116    # wait until the user presses 'enter' key
117    input("Press enter to replay the sound...")
118
119    # replay the sound (just to make sure replaying the received data is OK)
120    audio_stream.play();
121
122    # loop until the sound playback is finished
123    while audio_stream.status != sf.SoundStream.STOPPED:
124        sf.sleep(sf.milliseconds(100))

Embedding

 1// Including Python.h first is mandatory!
 2#include <Python.h>
 3
 4#include <unistd.h>
 5#include <iostream>
 6
 7// Make sure to include the SFML headers before the pySFML ones
 8#include <SFML/Graphics.hpp>
 9#include <pysfml/graphics_api.h>
10
11int main(int argc, char *argv[])
12{
13    // Initialization (mandatory stuff)
14    Py_SetProgramName(argv[0]);
15    Py_Initialize();
16
17    // Add the current path to sys.path to find our script
18    char cwd[1024];
19    if (!getcwd(cwd, sizeof(cwd))) {
20        std::cout << "Couldn't get the current path" << std::endl;
21        return EXIT_FAILURE; }
22    PyObject *sys = PyImport_ImportModule("sys");
23    PyObject *path = PyObject_GetAttrString(sys, "path");
24    PyList_Append(path, PyString_FromString(cwd));
25
26    // Import our script that creates a texture
27    PyObject* script = PyImport_ImportModule("script");
28    if(!script)
29        PyErr_Print();
30
31    // Retrieve the texture
32    PyTextureObject *texture;
33    texture = (PyTextureObject*)PyObject_GetAttrString(script, "texture");
34
35    // Create a window and display the texture for five seconds
36    sf::RenderWindow window(sf::VideoMode(640, 480), "pySFMl - Embedding Python");
37
38    window.clear();
39    window.draw(sf::Sprite(*texture->p_this));
40    window.display();
41
42    sf::sleep(sf::seconds(5));
43
44    // Then, terminate properly...
45    Py_Finalize();
46
47    return EXIT_SUCCESS;
48}
1from sfml import sf
2
3texture = sf.Texture.from_file("image.jpg")

Extending

1cimport libcpp.sfml as sf
2from pysfml.graphics cimport Image
3
4def flip_image(Image image):
5    image.p_this.flipHorizontally()
6    image.p_this.flipVertically()
 1from sfml import sf
 2
 3import pyximport; pyximport.install()
 4import extension
 5
 6window = sf.RenderWindow(sf.VideoMode(640, 480), "sfml")
 7
 8image = sf.Image.from_file("image.jpg")
 9extension.flip_image(image)
10
11texture = sf.Texture.from_image(image)
12
13window.clear()
14window.draw(sf.Sprite(texture))
15window.display()
16
17sf.sleep(sf.seconds(5))

Spacial Music

  1from sfml import sf
  2
  3def main(song):
  4	window = sf.RenderWindow(sf.VideoMode(600, 600), "pySFML - Spacial Music")
  5	window.framerate_limit = 60
  6
  7	# load one font, one song and two textures
  8	try:
  9		font = sf.Font.from_file("data/sansation.ttf")
 10		music = sf.Music.from_file(song)
 11
 12		texture = sf.Texture.from_file("data/speaker.gif")
 13		speaker = sf.Sprite(texture)
 14		speaker.position = -texture.size // 2
 15
 16		texture = sf.Texture.from_file("data/head_kid.png")
 17		hears = sf.Sprite(texture)
 18		hears.origin = texture.size // 2
 19
 20	except IOError:
 21		exit(1)
 22
 23	# create a text that display instructions
 24	instructions = "Up/Down        Move hears along Y axis\n"
 25	instructions += "Left/Right       Move hears along X axis\n"
 26	instructions += "Plus/Minus     Move hears along Z axis"
 27	instructions = sf.Text(instructions, font, 12)
 28	instructions.position = (70, 250)
 29	instructions.color = sf.Color.BLACK
 30
 31	# make sure the song is monothread so it can be spacialized
 32	if music.channel_count != 1:
 33		print("Only sounds with one channel (mono sounds) can be spatialized.")
 34		print("This song ({0}) has {1} channels.".format(SONG, music.channels_count))
 35		exit(1)
 36
 37	# setup the music properties
 38	music.relative_to_listener = False
 39	music.min_distance = 200
 40	music.attenuation = 1
 41
 42	# initialize some values before entering the main loop
 43	position = sf.Vector3(-250, -250, 0)
 44	sf.Listener.set_position(position)
 45
 46	x, y, _ = position
 47	hears.position = (x, y)
 48
 49	running = True
 50
 51	# move the view to make coord (0, 0) appears on the center of the screen
 52	window.default_view.move(-300, -300)
 53
 54	# start the music before entering the main loop
 55	music.loop = True
 56	music.play()
 57
 58	# start the main loop
 59	while running:
 60		for event in window.events:
 61			if type(event) is sf.CloseEvent:
 62				running = False
 63
 64			elif type(event) is sf.KeyEvent and event.pressed:
 65				if event.code is sf.Keyboard.UP:
 66					position.y -= 5
 67
 68				elif event.code is sf.Keyboard.DOWN:
 69					position.y += 5
 70
 71				elif event.code is sf.Keyboard.LEFT:
 72					position.x -= 5
 73
 74				elif event.code is sf.Keyboard.RIGHT:
 75					position.x += 5
 76
 77				elif event.code is sf.Keyboard.ADD:
 78					if position.z < 400:
 79						position.z += 5
 80
 81				elif event.code is sf.Keyboard.SUBTRACT:
 82					if position.z > -400:
 83						position.z -= 5
 84
 85				# update the listener and the hears position
 86				sf.Listener.set_position(position)
 87
 88				x, y, z = position
 89				hears.position = (x, y)
 90				hears.ratio = (1, 1) + sf.Vector2(z, z)/400.
 91
 92		# clear screen, draw images and text and display them
 93		window.clear(sf.Color.WHITE)
 94
 95		if position.z >= 0:
 96			window.draw(speaker)
 97			window.draw(hears)
 98		else:
 99			window.draw(hears)
100			window.draw(speaker)
101
102		window.draw(instructions)
103		window.display()
104
105	window.close()
106
107
108if __name__ == "__main__":
109    main("data/mario.flac")