Join GitHub today
GitHub is home to over 28 million developers working together to host and review code, manage projects, and build software together.Sign up
while True: led.red = pot.value #76
Would it be possible to automatically pass the value of a potentiometer directly into something like an
So that the following example:
led = RGBLED(2, 3, 4) pot = MCP3008() while True: led.red = pot.value
can be done automatically somehow?
i.e. When the pot value changes, the LED changes accordingly.
Hmmm ... it's certainly possible to come up with something, but it'll never be as simple as
How about having a
The nice thing about that is firstly that
Huh ... just realized my idea for
Well, there's a built in
Fanboi moment: OMG this is seriously cool. Right, now that's out of my system...
Current status (bear with me here): I've shifted
The base class GPIODevice now also implements the
>>> sensor = LightSensor(18) >>> for v in sensor.values: ... print v
And the console will spit out the values read from the sensor in real-time - nice for hardware debugging. However, here's the clever bit. OutputDevice now also implements a
Still doesn't sound like much? First let's fade in a PWMLED:
>>> blue = PWMLED(16) >>> blue.source = [i / 10000.0 for i in range(10000)]
Not impressed? Let's link the state of another LED to the state of this one, then do it again:
>>> red = PWMLED(12) >>> red.source = blue.values >>> blue.source = [i / 10000.0 for i in range(10000)]
Remember that all devices have
>>> btn = Button(26) >>> btn.when_pressed = blue.on >>> btn.when_released = blue.off
But hang on, we don't even need to set hooks to do this. We could do it with even fewer lines of code just by chaining the state of the button to the blue LED:
>>> btn.when_pressed = None >>> btn.when_released = None >>> blue.source = btn.values
Still works nicely! Now, we're using PWMLEDs so how about something more variable than a button. How about a light sensor?
>>> sensor = LightSensor(18) >>> blue.source = sensor.values
Now cover and uncover the light sensor: you should see both LEDs fade and brighten in response. You may note during all this that the CPU is pegged at 100%. This isn't a bug - it's entirely deliberate. It's because you've got background threads constantly reading and applying values. But with some trivial filters we can make things a lot more relaxed (and for that matter, intelligent). Firstly, let's make a filter that waits 0.1 seconds between reads from an iterable:
>>> from time import sleep >>> def read_slowly(iterable): ... for i in iterable: ... yield i ... sleep(0.1) ... >>> red.source = read_slowly(blue.values) >>> blue.source = read_slowly(sensor.values)
That's better - our CPU is now nice and idle most of the time. How about we make a time delay filter:
>>> def delayed(iterable): ... q =  ... for i in iterable: ... q.append(i) ... if len(q) > 5: ... yield q.pop(0)
Now you can wrap stuff so that the red LED will "lag" behind the changes to the blue one:
>>> red.source = delayed(read_slowly(blue.values))
Or we could make a trivial filter which inverts booleans:
>>> def inverted(iterable): ... for i in iterable: ... yield 1.0 - i
So now the red LED will do the opposite of the blue LED after a short delay:
>>> red.source = inverted(delayed(read_slowly(blue.values)))
Er, yes, I'll stop now. I might be having too much fun with this. I'll push it in a mo so you can have a play too!
Yeah - I'm actually going off our hooks now as I think this is even better and I haven't found anything I can do with hooks that I can't with this (yet). Still, I'm not actually proposing we remove hooks or anything - they still make for really nice readable code. I'm just saying this is even nicer :)
Oh, just a quick warning - when I push this don't merge it just yet. I still have a few changes to do like adding values to the AnalogInputDevice class (which doesn't descend from GPIODevice and so lacks it), and for that matter I still need to test I'm doing shutdown and stuff correctly. But it's too exciting not to push now and let people play :)
added a commit
Oct 19, 2015
Hmm, the follow-up to this is turning slightly complicated (rather than mass-duplicate the code for source and values into all the non-GPIODevice descendents that it needs to be in, I'm looking into mixin classes to reduce the duplication). Unfortunately that means I'm probably not going to finish the follow-up to this until later tonight (I've got to play baby sitter later this afternoon). That said, I know exactly how this should all look now (in concert with the tuples comment on #79 - I should've seen that earlier - it was staring me in the face when I went to implement source and values on
Then I've just got to document all this... !