[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Commit-gnuradio] r9152 - gnuradio/branches/features/experimental-gui
From: |
jcorgan |
Subject: |
[Commit-gnuradio] r9152 - gnuradio/branches/features/experimental-gui |
Date: |
Sat, 2 Aug 2008 12:35:15 -0600 (MDT) |
Author: jcorgan
Date: 2008-08-02 12:35:13 -0600 (Sat, 02 Aug 2008)
New Revision: 9152
Removed:
gnuradio/branches/features/experimental-gui/fft_controller.py
Modified:
gnuradio/branches/features/experimental-gui/fft_top_block.py
gnuradio/branches/features/experimental-gui/usrp_fft.py
Log:
Collapse fft_controller into fft_top_block.
Deleted: gnuradio/branches/features/experimental-gui/fft_controller.py
Modified: gnuradio/branches/features/experimental-gui/fft_top_block.py
===================================================================
--- gnuradio/branches/features/experimental-gui/fft_top_block.py
2008-08-02 17:10:02 UTC (rev 9151)
+++ gnuradio/branches/features/experimental-gui/fft_top_block.py
2008-08-02 18:35:13 UTC (rev 9152)
@@ -1,3 +1,4 @@
+#!/usr/bin/env python
#
# Copyright 2008 Free Software Foundation, Inc.
#
@@ -19,17 +20,48 @@
# Boston, MA 02110-1301, USA.
#
+"""
+GNU Radio top block and controller interface to create a stream
+of FFT frames at a specified rate from a USRP.
+"""
+
from gnuradio import gr, blks2
+from prop_val import prop_val_interface
+import threading
import simple_usrp
-class fft_top_block(gr.top_block):
+class _fft_thread(threading.Thread):
+ """
+ This background thread simply reads FFT frames from the message
+ queue and sets the top block 'fft' property to their string
+ representation. External code can add one or more listeners to
+ this property to receive notification when an FFT frame comes in.
+ """
+ def __init__(self, msgq, tb):
+ threading.Thread.__init__(self)
+ self._msgq = msgq
+ self._tb = tb
+ self._keep_running = True
+ self.setDaemon(1)
+
+ def run(self):
+ while self._keep_running:
+ msg = self._msgq.delete_head()
+ self._tb['fft'] = msg.to_string()
+
+ def stop(self):
+ self._keep_running = False
+
+
+class fft_top_block(gr.top_block, prop_val_interface, threading.Thread):
"""!
GNU Radio top block to create a stream of FFT frames at a particular
- frame rate from a USRP. The frames are enqueued in a gr.msg_queue for
- external retrieval.
+ frame rate from a USRP.
+
+ Provides controller interface to dynamically set USRP decimation rate,
+ daughterboard gain, receive center frequency, and averaging.
- Provides functions to dynamically set USRP decimation rate, daughterboard
- gain, receive center frequency, and averaging.
+ Add a listener to property 'fft' to get frames.
"""
def __init__(self,
fft_size=512,
@@ -63,8 +95,13 @@
@param average Whether to implement FFT averaging [True,
False] (default is False)
"""
+ # Initialize parent classes
gr.top_block.__init__(self, "fft_top_block")
-
+ prop_val_interface.__init__(self)
+
+ """
+ Create a hierarchical flow graph
+ """
self._u = simple_usrp.source_c(which=which,
decim=decim,
width_8=width_8,
@@ -81,38 +118,79 @@
avg_alpha=avg_alpha,
average=average)
- self._msgq = gr.msg_queue(2)
+ self._msgq = gr.msg_queue(2) # OK to discard if bg thread can't keep up
self._sink = gr.message_sink(gr.sizeof_float*fft_size, self._msgq, True)
self.connect(self._u, self._fft, self._sink)
- # "Setters", which are called externally to affect flowgraph operation
- def set_gain(self, gain):
- return self._u.set_gain(gain)
+ """
+ Create controller interface
+ """
+ # Listeners are invoked when a property is set on the top block
+ self.add_listener('decim', self._set_decim)
+ self.add_listener('gain', lambda x: self._u.set_gain(x))
+ self.add_listener('freq', lambda x: self._u.set_freq(x))
+ self.add_listener('average', lambda x: self._fft.set_average(x))
+ self.add_listener('avg_alpha', lambda x: self._fft.set_avg_alpha(x))
+
+ # Providers are invoked when a property is read on the top block
+ self.set_provider('sample_rate', lambda : self._u.sample_rate())
+ self.set_provider('average', lambda : self._fft.average())
+ self.set_provider('avg_alpha', lambda : self._fft.avg_alpha())
- def set_freq(self, freq):
- return self._u.set_freq(freq)
-
- def set_decim(self, decim):
+ """
+ Create update thread. Updates property 'fft' at desired frame rate
+ """
+ self._thread = _fft_thread(self._msgq, self)
+
+ def _set_decim(self, decim):
+ """!
+ Listens to property 'decim'. Changes decimation rate and updates
'sample_rate'
+ property (which triggers listeners on that property).
+ """
self._u.set_decim(decim)
self._fft.set_sample_rate(self._u.sample_rate())
- def set_avg_alpha(self, avg_alpha):
- return self._fft.set_avg_alpha(avg_alpha)
-
- def set_average(self, average):
- return self._fft.set_average(average)
+ def on_init(self):
+ """
+ This method gets called by the external GUI or other code to start the
top block
+ operation.
+ """
+ # Start the queue runner background thread
+ self._thread.start()
- # Getters, which are called externally to get information about the
flowgraph
- def queue(self):
- return self._msgq
+ # Using gr.top_block.start() here keeps Python's SIGINT handler active,
+ # and we agree to handle SIGINT in our code if needed. We must also
call
+ # gr.top_block.stop() and .wait() to properly shut down GNU Radio
+ self.start()
- def sample_rate(self):
- return self._u.sample_rate()
+ def on_exit(self):
+ """
+ This method gets called to shutdown the top block. It stops the
background
+ thread, then calls stop() and wait() on the top block.
+ """
+ self._thread.stop()
+ self.stop()
+ self.wait()
- def average(self):
- return self._fft.average()
- def avg_alpha(self):
- return self._fft.avg_alpha()
+if __name__ == "__main__":
+ """
+ Example usage of fft_top_block. Opens a file and adds a file writer as a
listener
+ to the 'fft' property.
+ """
+ # Create the top block (uses all default parameters, needs a USRP attached)
+ tb = fft_top_block()
+
+ # Write fft frames to a file
+ f = open("fft.dat", "w")
+ tb.add_listener('fft', lambda x: f.write(x))
+
+ # Start the top block and wait for a key, then stop the top block
+ tb.on_init()
+ try:
+ raw_input("Press any key to exit.\n")
+ except KeyboardInterrupt:
+ print "Application interrupted."
+ tb.on_exit()
Modified: gnuradio/branches/features/experimental-gui/usrp_fft.py
===================================================================
--- gnuradio/branches/features/experimental-gui/usrp_fft.py 2008-08-02
17:10:02 UTC (rev 9151)
+++ gnuradio/branches/features/experimental-gui/usrp_fft.py 2008-08-02
18:35:13 UTC (rev 9152)
@@ -24,8 +24,8 @@
from gnuradio.eng_option import eng_option
import sys
-# Import the controller object
-from fft_controller import fft_controller
+# Import the top block object
+from fft_top_block import fft_top_block
# Import the GUI object
from fft_gui import fft_gui
@@ -66,31 +66,30 @@
# Applications have a 2-step initialization
- # Step 1: Create the application controller. It will create
- # the top block it manipulates. The controller implements
- # a property/value interface to allow setting, getting, and
- # listening properties that affect the application operation.
- controller = fft_controller(fft_size=512,
- frame_rate=10,
- ref_scale=50,
- which=options.which,
- decim=options.decim,
- width_8=options.width_8,
- no_hb=options.no_hb,
- subdev_spec=options.rx_subdev_spec,
- gain=options.gain,
- freq=options.freq,
- antenna=options.antenna,
- avg_alpha=options.avg_alpha,
- average=False)
+ # Step 1: Create the application top block.
+ # The top block implements a controller interface
+ # to allow setting, getting, and listening to properties
+ # that affect the application operation.
+ tb = fft_top_block(fft_size=512,
+ frame_rate=10,
+ ref_scale=50,
+ which=options.which,
+ decim=options.decim,
+ width_8=options.width_8,
+ no_hb=options.no_hb,
+ subdev_spec=options.rx_subdev_spec,
+ gain=options.gain,
+ freq=options.freq,
+ antenna=options.antenna,
+ avg_alpha=options.avg_alpha,
+ average=False)
- # Step 2: Create the GUI and pass it the controller
+ # Step 2: Create the GUI and pass it the top block
# to manipulate. The GUI code doesn't know anything about GNU
# Radio proper; it simply gets, sets, or listens to properties
- # on the controller. The 'GUI' can actually be a CLI batch
+ # on the top block. The 'GUI' can actually be a CLI batch
# program, an interactive shell, or anything that knows what to
- # do with the controller properties.
+ # do with the the top block properties.
#
- gui = fft_gui(controller)
+ gui = fft_gui(tb, 'USRP FFT')
gui.run()
-
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Commit-gnuradio] r9152 - gnuradio/branches/features/experimental-gui,
jcorgan <=