BorisS
Posts: 15
Joined: Fri Oct 11, 2013 7:08 pm

Re: Pure Python camera interface

Thu Feb 05, 2015 2:44 pm

Thank you for this info, Dave. Totally overlooked this class. I'll give it a try!

Boris

BorisS
Posts: 15
Joined: Fri Oct 11, 2013 7:08 pm

Re: Pure Python camera interface

Thu Feb 05, 2015 8:46 pm

Hi Dave,
first quick tests work really great - thanks! Following split line used in a loop over index did the trick:

Code: Select all

camera.split_recording(PtsOutput(camera, 'video_%d.h264' % index, 'timecodes_%d.txt' % index))
Due to the timestamps I've seen that my recordings are skipping 1 out of 3 frames. This behaviour disappeared when I switched off the dynamic range compression:

Code: Select all

#camera.drc_strength = 'medium'
Hmmmmm.

Boris

trevor-s
Posts: 1
Joined: Sat Feb 07, 2015 5:59 pm

Re: Pure Python camera interface

Sat Feb 07, 2015 6:13 pm

I'm new to the RPi, and I'm helping introduce them into my local primary school ...

I bought a couple of B+ boards and had no trouble with the cameras. This week I purchased some of the new 2B units and started playing with them.

When I try to use Python 2 or 3 I get:

from picamera.camera import PiCamera
File "/usr/lib/python2.7/dist-packages/picamera/camera.py", line 83, in <module>
import RPi.GPIO as GPIO
RuntimeError: This module can only be run on a Raspberry Pi!

Looking in the source of camera.py

try:
import RPi.GPIO as GPIO
GPIO_LED_PIN = {
0: 5, # compute module (XXX is this correct?)
1: 5, # model B rev 1
2: 5, # model B rev 2
3: 32, # model B+
}[GPIO.RPI_REVISION]
except ImportError:
# Can't find RPi.GPIO so just null-out the reference
GPIO = None


Do I need to add a new entry, something like:

4: 32, # model 2B

?

hydra3333
Posts: 108
Joined: Thu Jan 10, 2013 11:48 pm

Re: Pure Python camera interface

Sun Feb 08, 2015 12:56 am

Thanks for the find and the report posted.
My Pi2 is on order and I would have run into that issue ...
Looking forward to a fix from the author (new version ? :))

User avatar
DougieLawson
Posts: 35791
Joined: Sun Jun 16, 2013 11:19 pm
Location: Basingstoke, UK
Contact: Website Twitter

Re: Pure Python camera interface

Sun Feb 08, 2015 12:59 am

trevor-s wrote: Do I need to add a new entry, something like:

4: 32, # model 2B

?
You need a completely new version of RPi.GPIO.
It's not just the revision number (which has a completely new meaning and new data schema).
Note: Having anything humorous in your signature is completely banned on this forum. Wear a tin-foil hat and you'll get a ban.

Any DMs sent on Twitter will be answered next month.

This is a doctor free zone.

discomfortablynumb
Posts: 1
Joined: Sun Feb 08, 2015 11:55 am

Re: Pure Python camera interface

Sun Feb 08, 2015 12:14 pm

trevor-s wrote:I'm new to the RPi, and I'm helping introduce them into my local primary school ...


from picamera.camera import PiCamera
File "/usr/lib/python2.7/dist-packages/picamera/camera.py", line 83, in <module>
import RPi.GPIO as GPIO
RuntimeError: This module can only be run on a Raspberry Pi!

Looking in the source of camera.py

try:
import RPi.GPIO as GPIO
GPIO_LED_PIN = {
0: 5, # compute module (XXX is this correct?)
1: 5, # model B rev 1
2: 5, # model B rev 2
3: 32, # model B+
}[GPIO.RPI_REVISION]
except ImportError:
# Can't find RPi.GPIO so just null-out the reference
GPIO = None


?

Have just run into this one myself.
Being new both Raspberry PI and these forums is there somewhere I should be reporting this issue in order to expedite a fix ?

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Mon Feb 09, 2015 5:41 pm

A quick note for anyone else experiencing the issue with picamera not working on the Pi2:

First off, it's been reported as issue #190 on the picamera repo, so I am aware of it.

The issue is basically that RPi.GPIO doesn't (yet) work on the Pi2, and it's necessary for LED control from the picamera library. My hope was that RPi.GPIO would be updated fairly quickly and I could do very little to fix up picamera; all that would be needed is an extra entry in that dictionary lookup several people have mentioned (however, note that it's looking up a value in RPi.GPIO, so I can't update it until RPi.GPIO is updated). For those interested, the ticket for Pi2 compatibility in RPi.GPIO is here.

Anyway, it's been a week - the Pi2 is proving ridiculously popular and my mail box is beginning to fill up with people complaining about this (not to mention, my Pi2 arrived and I want to play with picamera on it!). Given that LED control is a pretty minor part of picamera I've decided to quickly implement a fix which will basically disable LED control on the Pi2 for now (attempting to access or set the led property on a Pi2 will raise an exception).

Once RPi.GPIO is updated, picamera will need another update to re-enable it (not least because I've no idea what GPIO the LED will wind up on yet), but I'll keep an eye on the RPi.GPIO ticket and get another one out shortly after it's done.

Dave.

User avatar
DougieLawson
Posts: 35791
Joined: Sun Jun 16, 2013 11:19 pm
Location: Basingstoke, UK
Contact: Website Twitter

Re: Pure Python camera interface

Mon Feb 09, 2015 7:45 pm

waveform80 wrote: Once RPi.GPIO is updated, picamera will need another update to re-enable it (not least because I've no idea what GPIO the LED will wind up on yet), but I'll keep an eye on the RPi.GPIO ticket and get another one out shortly after it's done.
Ben Croston has made a release candidate version of RPi.GPIO available for testing.
Note: Having anything humorous in your signature is completely banned on this forum. Wear a tin-foil hat and you'll get a ban.

Any DMs sent on Twitter will be answered next month.

This is a doctor free zone.

bantammenace2012
Posts: 122
Joined: Mon May 28, 2012 12:18 pm

Re: Pure Python camera interface

Mon Feb 09, 2015 8:48 pm

Here's the link to how to install a DEV version of RPi.GPIO.
I can confirm that it resolves the "module" issue and takes less than 3 minutes to do
I now have PiCamera working on my Pi2
http://sourceforge.net/p/raspberry-gpio ... i/install/

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Mon Feb 09, 2015 9:50 pm

Excellent news! In that case, on the assumption that an RPi.GPIO release isn't far off I'll hold off on picamera changes for a bit. Always best to change nothing if you can get away with it! Incidentally, from the updated code it looks as though the new RPi.GPIO will be treating the B+ and 2B as equivalent in RPI_REVISION so I'm hoping the 2B still uses GPIO 32 for camera LED control ... I'll try and confirm that soon.

Dave.

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Tue Feb 10, 2015 9:33 pm

It's just occurred to me (while twiddling my thumbs during Sourceforge's downtime) that another way to quickly get picamera working on a Pi2 is simply to (temporarily) uninstall the python-rpi.gpio package (e.g. sudo apt-get remove python-rpi.gpio). The picamera package treats it as an optional dependency so if it doesn't find it at all then it'll just press ahead happily. Of course, once RPi.GPIO gets fixed up you will need to reinstall it (sudo apt-get update && sudo apt-get install python-rpi.gpio) but until then it's a quick way to get picamera working on a Pi2.

Dave.

bootsmann
Posts: 28
Joined: Thu Jan 23, 2014 7:07 am

Re: Pure Python camera interface

Wed Feb 11, 2015 9:27 am

Hi

After flashing a new image ``2015-01-31-raspbian.img``

Code: Select all

Linux raspberrypi 3.18.6+ #754 PREEMPT Sun Feb 8 20:22:45 GMT 2015 armv6l GNU/Linux
my ``mjpg-stream-server`` crashes after a few seconds

Code: Select all

usr/lib/python2.7/dist-packages/picamera/camera.py:120: PiCameraDeprecated: Accessing framerate as a tuple is deprecated; this value is now a Fraction, so you can query the numerator and denominator properties directly, convert to an int or float, or perform arithmetic operations and comparisons directly
  'Accessing framerate as a tuple is deprecated; this value is '
mmal: mmal_vc_component_enable: failed to enable component: ENOSPC
Traceback (most recent call last):
  File "/usr/local/lib/python2.7/dist-packages/gevent/pywsgi.py", line 508, in handle_one_response
    self.run_application()
  File "/usr/local/lib/python2.7/dist-packages/gevent/pywsgi.py", line 495, in run_application
    self.process_result()
  File "/usr/local/lib/python2.7/dist-packages/gevent/pywsgi.py", line 484, in process_result
    for data in self.result:
  File "app.py", line 110, in mjpeg
    with picamera.PiCamera() as camera:
  File "/usr/lib/python2.7/dist-packages/picamera/camera.py", line 419, in __init__
    self.STEREO_MODES[stereo_mode], stereo_decimate)
  File "/usr/lib/python2.7/dist-packages/picamera/camera.py", line 551, in _init_camera
    prefix="Camera component couldn't be enabled")
  File "/usr/lib/python2.7/dist-packages/picamera/exc.py", line 133, in mmal_check
    raise PiCameraMMALError(status, prefix)
PiCameraMMALError: Camera component couldn't be enabled: Out of resources (other than memory)
Only downgrade to an old image like #720 or lower works. Does anyone have an idea? The python code is a page before.

thx

EDIT
The browser made the problem respectively the Chache Killer app... Everything is ok :D
Last edited by bootsmann on Wed Feb 25, 2015 2:38 pm, edited 1 time in total.

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Mon Feb 16, 2015 6:47 pm

Just a quick note to let everyone know that picamera now works on the Pi 2. The picamera library itself doesn't require upgrading, but you should see python-rpi.gpio get upgraded when running "sudo apt-get update && sudo apt-get upgrade" which will fix the issue people have been seeing with picamera.

Apologies I haven't had much time to respond to messages on the forum - I haven't forgotten, just a bit swamped at the mo!


Dave.

pablok
Posts: 53
Joined: Thu Dec 26, 2013 4:46 pm
Location: Westerkwartier, Groningen (NL)

Re: Pure Python camera interface

Sat Mar 21, 2015 3:04 pm

Hi all,
Consistent Images (basic recipes 4.6) seemed the solution to see my surroundings getting dark during the partial solar eclipse. I tested it inside the house and it worked fine. Then changed the params for a lot of images and set the picam in the garden.
After the eclipse I took it to my study to sew the images together with ffmpeg.
Not one image to be found on the card....

Started the Pi again and tested just to see everything was working fine under these conditions.
What I suspect is that the lines:

# Wait for analog gain to settle on a higher value than 1
while camera.analog_gain <= 1:
time.sleep(0.1)

have kept the Pi under daylight conditions in the loop.

What do you think has happened?

(BTW should'nt there be an import of Fractions library?)

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Sat Mar 21, 2015 3:20 pm

pablok wrote:Hi all,
Consistent Images (basic recipes 4.6) seemed the solution to see my surroundings getting dark during the partial solar eclipse. I tested it inside the house and it worked fine. Then changed the params for a lot of images and set the picam in the garden.
After the eclipse I took it to my study to sew the images together with ffmpeg.
Not one image to be found on the card....

Started the Pi again and tested just to see everything was working fine under these conditions.
What I suspect is that the lines:

# Wait for analog gain to settle on a higher value than 1
while camera.analog_gain <= 1:
time.sleep(0.1)

have kept the Pi under daylight conditions in the loop.

What do you think has happened?
I've just given this a whirl under daylight conditions (the vast majority of my picamera testing is usually done in the evenings) and it appears the analog gain will never go above one, so that particular loop will never finish. The problem with updating it to use a lower value is that with indoor/darkened conditions (which from correspondence, is the majority use-case here) the loop finishes too quickly and the subsequent shots will use insufficient gain.

I think a better alternative would be to simply use a fixed wait for a number of seconds under the assumption that the AGC ought to have found a reasonable gain after a second or two (and if it hasn't things are probably way too dark to shoot anyway). I'll update the recipe for the 1.10 release.
pablok wrote:(BTW should'nt there be an import of Fractions library?)
Only necessary if you want to construct fractions of your own to compare against the values returned by things like analog_gain.

Dave.

Gelu
Posts: 13
Joined: Tue Oct 28, 2014 2:57 pm

Re: Pure Python camera interface

Mon Mar 23, 2015 3:19 pm

Is it possible to use the video port with picamera.array?
I posted this question in another forum but it was buried in another post and did not receive much attention... (at the end of: http://www.raspberrypi.org/forums/viewt ... 52#p721252)
Sorry if it not correct to repost here.

This code demostrates my issue:

Code: Select all

import io
import time
import picamera
import cv2
import picamera.array
import numpy as np

with picamera.PiCamera() as camera:

    camera.resolution = (1296, 972)
    camera.framerate = 6
    print("Selecting adequate fixed settings")
    # Wait for analog gain to settle on a higher value than 1
    while camera.analog_gain <= 1:
        time.sleep(0.1)
    # Now fix the values
    camera.shutter_speed = camera.exposure_speed
    camera.exposure_mode = 'off'
    g = camera.awb_gains
    camera.awb_mode = 'off'
    camera.awb_gains = g

    # start and wait for camera setup
    camera.start_preview()
    time.sleep(2)



    # Capture using jpeg video port
    stream = io.BytesIO()
    start = time.time()
    camera.capture(stream, format='jpeg',use_video_port=True)
    # Construct a numpy array from the stream
    data = np.fromstring(stream.getvalue(), dtype=np.uint8)
    # "Decode" the image from the array, preserving colour
    image = cv2.imdecode(data, 1)
    cv2.imwrite('jpegVIDEO.png',image)
    print("Time with jpeg+stream+numpy = %.4f" % (time.time()-start))



    # Capture using jpeg stills port
    stream = io.BytesIO()
    start = time.time()
    camera.capture(stream, format='jpeg')
    # Construct a numpy array from the stream
    data = np.fromstring(stream.getvalue(), dtype=np.uint8)
    # "Decode" the image from the array, preserving colour
    image = cv2.imdecode(data, 1)
    cv2.imwrite('jpegSTILL.png',image)
    print("Time with jpeg+stream+numpy = %.4f" % (time.time()-start))


    # capture using picamera.array video port
    start = time.time()
    with picamera.array.PiRGBArray(camera) as stream:
        camera.capture(stream, format='bgr')
        # At this point the image is available as stream.array
        background = stream.array
    cv2.imwrite('picameraSTILL.png',background)

    print("Time with picamera.array = %.4f" % (time.time()-start))



    # capture using picamera.array video port
    start = time.time()
    with picamera.array.PiRGBArray(camera) as stream:
        camera.capture(stream, format='bgr',use_video_port=True)
        # At this point the image is available as stream.array
        background = stream.array
    cv2.imwrite('pimcameraVIDEO.png',background)

    print("Time with picamera.array = %.4f" % (time.time()-start))

All images but the last one (the one using picamera.array and the video port) seem to work well, the last one just saves a completely black image.
Am I doing something incorrectly?
Thanks,
Angel

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Mon Mar 23, 2015 4:28 pm

Gelu wrote:Is it possible to use the video port with picamera.array?
I posted this question in another forum but it was buried in another post and did not receive much attention... (at the end of: http://www.raspberrypi.org/forums/viewt ... 52#p721252)
Sorry if it not correct to repost here.

This code demostrates my issue:

Code: Select all

import io
import time
import picamera
import cv2
import picamera.array
import numpy as np

with picamera.PiCamera() as camera:

    camera.resolution = (1296, 972)
    camera.framerate = 6
    print("Selecting adequate fixed settings")
    # Wait for analog gain to settle on a higher value than 1
    while camera.analog_gain <= 1:
        time.sleep(0.1)
    # Now fix the values
    camera.shutter_speed = camera.exposure_speed
    camera.exposure_mode = 'off'
    g = camera.awb_gains
    camera.awb_mode = 'off'
    camera.awb_gains = g

    # start and wait for camera setup
    camera.start_preview()
    time.sleep(2)



    # Capture using jpeg video port
    stream = io.BytesIO()
    start = time.time()
    camera.capture(stream, format='jpeg',use_video_port=True)
    # Construct a numpy array from the stream
    data = np.fromstring(stream.getvalue(), dtype=np.uint8)
    # "Decode" the image from the array, preserving colour
    image = cv2.imdecode(data, 1)
    cv2.imwrite('jpegVIDEO.png',image)
    print("Time with jpeg+stream+numpy = %.4f" % (time.time()-start))



    # Capture using jpeg stills port
    stream = io.BytesIO()
    start = time.time()
    camera.capture(stream, format='jpeg')
    # Construct a numpy array from the stream
    data = np.fromstring(stream.getvalue(), dtype=np.uint8)
    # "Decode" the image from the array, preserving colour
    image = cv2.imdecode(data, 1)
    cv2.imwrite('jpegSTILL.png',image)
    print("Time with jpeg+stream+numpy = %.4f" % (time.time()-start))


    # capture using picamera.array video port
    start = time.time()
    with picamera.array.PiRGBArray(camera) as stream:
        camera.capture(stream, format='bgr')
        # At this point the image is available as stream.array
        background = stream.array
    cv2.imwrite('picameraSTILL.png',background)

    print("Time with picamera.array = %.4f" % (time.time()-start))



    # capture using picamera.array video port
    start = time.time()
    with picamera.array.PiRGBArray(camera) as stream:
        camera.capture(stream, format='bgr',use_video_port=True)
        # At this point the image is available as stream.array
        background = stream.array
    cv2.imwrite('pimcameraVIDEO.png',background)

    print("Time with picamera.array = %.4f" % (time.time()-start))

All images but the last one (the one using picamera.array and the video port) seem to work well, the last one just saves a completely black image.
Am I doing something incorrectly?
Thanks,
Angel
Hmm, this is a complicated one - it's an unintended side effect of a series of interactions "under the hood" that your script is making.

What's happening is that at various points in your script picamera needs to adjust port encodings to accomodate the formats you're requesting (still port from YUV to BGR). Adjusting port encodings involves disabling and re-enabling the camera. When the camera is re-enabled, under certain circumstances, the firmware resets the camera's analog and/or digital gains to zero expecting that the AGC algorithm will subsequently correct them. However, you've also disabled the AGC algorithm by setting exposure_mode to 'off' so the gains never float above zero and the subsequent captures are black.

There's various ways to work around this. The simplest is to allow AGC to work by removing exposure_mode='off' but I'm assuming you want a fixed exposure so let's look at some alternatives:

If you adjust your script to only capture BGR images from the video port (i.e. just the last bit), everything works fine because the video port encoding is never adjusted (an otherwise redundant resizer is inserted into the MMAL pipeline to handle the YUV->BGR conversion in the case of video port captures - actually it's a little more complicated than that because resizers only work with RGBA and BGRA, not RGB and BGR, but anyway...).

If you need to capture BGR images from both the still and video port in a single script then you probably want to set the still port encoding prior to disabling the AGC algorithm. This can be done in a couple of ways: either perform a redundant still port BGR capture prior to setting exposure_mode to 'off' (e.g. capture('/dev/null', 'bgr')), or directly by doing:

Code: Select all

import picamera.mmal as mmal
...
camera._still_encoding = mmal.MMAL_ENCODING_BGR24
Although beware that because that's an internal property I may change it in future without warning (the public API is fixed and subject to deprecation; the internal API is not).

You may also find that still port captures when AGC is disabled result in subsequent captures being black regardless. This is because the mode switch involved in still port captures also resets the camera and sometimes causes gains to reset to zero. In that case the only option is to re-enable AGC after a still port capture, let the gains float up again, then fix them again.

Finally, I should point out that because of all these interactions which picamera hides from view, you can't really trust individual capture timings as being representative of repeated timings. For example, the first BGR still port capture will always be longer than subsequent ones because under the hood, picamera has to adjust the port format. Subsequent BGR still port captures will find the port already has the right format and will just proceed without resetting the camera.

Dave.

Gelu
Posts: 13
Joined: Tue Oct 28, 2014 2:57 pm

Re: Pure Python camera interface

Mon Mar 23, 2015 5:41 pm

Many thanks for your explanations, I just want to use the video port, so I've tried running just the last part of the code and it works fine.

6by9
Raspberry Pi Engineer & Forum Moderator
Raspberry Pi Engineer & Forum Moderator
Posts: 7135
Joined: Wed Dec 04, 2013 11:27 am
Location: ZZ9 Plural Z Alpha, aka just outside Cambridge.

Re: Pure Python camera interface

Mon Mar 23, 2015 9:31 pm

waveform80 wrote:If you adjust your script to only capture BGR images from the video port (i.e. just the last bit), everything works fine because the video port encoding is never adjusted (an otherwise redundant resizer is inserted into the MMAL pipeline to handle the YUV->BGR conversion in the case of video port captures - actually it's a little more complicated than that because resizers only work with RGBA and BGRA, not RGB and BGR, but anyway...).
Hmm, seems odd. The camera component supports delivering MMAL encodings BGRA, BGR24, RGB24, and RGB16 (all available via the V4L2 driver). Why the need for resize to do the format conversion? Admittedly some of those formats weren't added until relatively late (ie July/August 2014), so may predate when you were adding support.
If you could ping me a graph of what components you use for different cases (message me as I don't normally follow this thread), then I'm happy to comment and advise on any optimisations.

Changing port format shouldn't actually stop the sensor unless you actually disable the camera component. Disable the port(s) only and it should keep everything running underneath.
Software Engineer at Raspberry Pi Trading. Views expressed are still personal views.
I'm not interested in doing contracts for bespoke functionality - please don't ask.

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Tue Mar 31, 2015 2:05 am

Picamera 1.10 is now out on PyPI, and should hit Raspbian in a few days time. See the changelog for the full details of the release. On a personal note, this is a slightly rushed release (don't worry, I've run the test suite!) because our first child is now imminent (a few days earlier than expected) so there probably won't be much work on picamera in the coming months (sorry!). Please feel free to continue submitting bugs/pull requests/feature requests/questions/etc. to the GitHub bug tracker though - that way I won't forget about them!

To anyone that's e-mailed me recently and I haven't replied yet - sorry - I've got quite a full inbox and I'm afraid it's likely I won't be able to get back to you in the near future. As above, please feel free to file things on GitHub so they don't get forgotten (besides which, the community might respond there too - which is why it's usually a better idea than e-mailing me anyway :)

Thanks to everyone for their support over the last few years - it's been great fun working on picamera, and I'm sure I'll get back to it in a few months once I've figured out how to sleep again!


Dave.

grats
Posts: 30
Joined: Fri Apr 25, 2014 6:51 am
Location: Colorado, USA

Re: Pure Python camera interface

Tue Mar 31, 2015 9:54 am

Is there a way to have annotate_text run and update its time while the video is recording?

is there a "while is_recording" or something? I couldn't find anything..

This is the first time I've used python as well.

Code: Select all

import picamera
import datetime as dt

#640x480 90fps
#1280x720 60fps
#1920x1080 30fps
video_length = 5
y_var   = 1920
x_var   = 1080
fps_var = 30

def videoCap():
	dt_var = dt.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
	with picamera.PiCamera() as camera:
	    camera.resolution = (y_var, x_var)
	    camera.framerate = fps_var
	    camera.annotate_text = dt_var
	    camera.start_recording('%s.h264' % dt_var, quality=35, bitrate=0)
	    print("Recording 1080p Video at 30fps for %d seconds" % video_length)
	    camera.wait_recording(video_length)
	    camera.stop_recording()


videoCap()
I'm just messing around learning, I'd like to have annotate_text trigger to update the seconds while it is recording.. we have it "wait_recording"

do I have to do something like putting a loop in there to write annotate_text every 1 second for video_length and not use wait_recording?? I read that was bad in case the drive you are writing to ran out of space etc... but I do not know now, I assume there's something I just don't know about picamera / python

User avatar
waveform80
Posts: 303
Joined: Mon Sep 23, 2013 1:28 pm
Location: Manchester, UK

Re: Pure Python camera interface

Tue Mar 31, 2015 11:01 pm

grats wrote:Is there a way to have annotate_text run and update its time while the video is recording?

is there a "while is_recording" or something? I couldn't find anything..

This is the first time I've used python as well.

Code: Select all

import picamera
import datetime as dt

#640x480 90fps
#1280x720 60fps
#1920x1080 30fps
video_length = 5
y_var   = 1920
x_var   = 1080
fps_var = 30

def videoCap():
	dt_var = dt.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
	with picamera.PiCamera() as camera:
	    camera.resolution = (y_var, x_var)
	    camera.framerate = fps_var
	    camera.annotate_text = dt_var
	    camera.start_recording('%s.h264' % dt_var, quality=35, bitrate=0)
	    print("Recording 1080p Video at 30fps for %d seconds" % video_length)
	    camera.wait_recording(video_length)
	    camera.stop_recording()


videoCap()
I'm just messing around learning, I'd like to have annotate_text trigger to update the seconds while it is recording.. we have it "wait_recording"

do I have to do something like putting a loop in there to write annotate_text every 1 second for video_length and not use wait_recording?? I read that was bad in case the drive you are writing to ran out of space etc... but I do not know now, I assume there's something I just don't know about picamera / python
I really should refine the wait_recording docs - several people have found them confusing now. The gist is as follows:

You don't *have* to call wait_recording at all. You could just use time.sleep instead, or wait on anything you like and most of the time your script would run absolutely the same. When you call start_recording, a background thread is spawned which handles recording video to the output object you've provided (a file, a stream, a network socket, whatever). Your script can continue doing whatever it likes, and the background recording thread will keep running, dumping recorded frames to your output object. Eventually, your script will (hopefully) call stop_recording, and the background recording thread will be shut down.

So what's the point of wait_recording? The purpose has to do with the scenario where something goes wrong. What happens if the output object is a file, and the destination disk runs out of space? What happens if the output object is a network socket, and the Wifi disconnects? Basically, what happens if something goes catastrophically wrong in the background recording thread? Well, firstly the background thread will terminate due to whatever exception was raised and then ... well, nothing will happen because the exception was raised in the background thread and your script (which is running in the main thread) has no way of seeing such exceptions.

This is the purpose of wait_recording. It effectively says "wait n seconds for something to go wrong in the background recording thread; if something does go wrong, raise the exception in the main thread". In other words, it's a method for determining whether the background recording thread has terminated and for transferring any exception from the background recording thread to the main thread.

Hopefully from the above you can see that while you don't *have* to call wait_recording, it's a good idea to periodically do so just to check things haven't gone wrong. That said, you can call it as many times as you like, with as shorter wait period as you like. So if you want to update annotate_text with a timestamp containing seconds I'd recommend doing something like the following after calling start_recording:

Code: Select all

...
start = dt.datetime.now()
while (dt.datetime.now() - start).total_seconds() < video_length:
   camera.wait_recording(0.1)
    camera.annotate_text = dt.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
...
There's something vaguely similar to this in the final code block of the text annotation recipe now I come to think of it.

Good luck!

Dave.

grats
Posts: 30
Joined: Fri Apr 25, 2014 6:51 am
Location: Colorado, USA

Re: Pure Python camera interface

Tue Mar 31, 2015 11:25 pm

waveform80 wrote:
grats wrote:Is there a way to have annotate_text run and update its time while the video is recording?

is there a "while is_recording" or something? I couldn't find anything..

This is the first time I've used python as well.

Code: Select all

import picamera
import datetime as dt

#640x480 90fps
#1280x720 60fps
#1920x1080 30fps
video_length = 5
y_var   = 1920
x_var   = 1080
fps_var = 30

def videoCap():
	dt_var = dt.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
	with picamera.PiCamera() as camera:
	    camera.resolution = (y_var, x_var)
	    camera.framerate = fps_var
	    camera.annotate_text = dt_var
	    camera.start_recording('%s.h264' % dt_var, quality=35, bitrate=0)
	    print("Recording 1080p Video at 30fps for %d seconds" % video_length)
	    camera.wait_recording(video_length)
	    camera.stop_recording()


videoCap()
I'm just messing around learning, I'd like to have annotate_text trigger to update the seconds while it is recording.. we have it "wait_recording"

do I have to do something like putting a loop in there to write annotate_text every 1 second for video_length and not use wait_recording?? I read that was bad in case the drive you are writing to ran out of space etc... but I do not know now, I assume there's something I just don't know about picamera / python
I really should refine the wait_recording docs - several people have found them confusing now. The gist is as follows:

You don't *have* to call wait_recording at all. You could just use time.sleep instead, or wait on anything you like and most of the time your script would run absolutely the same. When you call start_recording, a background thread is spawned which handles recording video to the output object you've provided (a file, a stream, a network socket, whatever). Your script can continue doing whatever it likes, and the background recording thread will keep running, dumping recorded frames to your output object. Eventually, your script will (hopefully) call stop_recording, and the background recording thread will be shut down.

So what's the point of wait_recording? The purpose has to do with the scenario where something goes wrong. What happens if the output object is a file, and the destination disk runs out of space? What happens if the output object is a network socket, and the Wifi disconnects? Basically, what happens if something goes catastrophically wrong in the background recording thread? Well, firstly the background thread will terminate due to whatever exception was raised and then ... well, nothing will happen because the exception was raised in the background thread and your script (which is running in the main thread) has no way of seeing such exceptions.

This is the purpose of wait_recording. It effectively says "wait n seconds for something to go wrong in the background recording thread; if something does go wrong, raise the exception in the main thread". In other words, it's a method for determining whether the background recording thread has terminated and for transferring any exception from the background recording thread to the main thread.

Hopefully from the above you can see that while you don't *have* to call wait_recording, it's a good idea to periodically do so just to check things haven't gone wrong. That said, you can call it as many times as you like, with as shorter wait period as you like. So if you want to update annotate_text with a timestamp containing seconds I'd recommend doing something like the following after calling start_recording:

Code: Select all

...
start = dt.datetime.now()
while (dt.datetime.now() - start).total_seconds() < video_length:
   camera.wait_recording(0.1)
    camera.annotate_text = dt.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
...
There's something vaguely similar to this in the final code block of the text annotation recipe now I come to think of it.

Good luck!

Dave.

Oh ok. So basically in my case of a set amount of record time

Code: Select all

#i = 0 set somewhere up here

		camera.start_recording('%s.h264' % dt_var, quality=40, bitrate=0)
		print("Recording 1080p Video at 30fps for %d seconds" % video_length)
		while i < video_length:
			i += 1
			camera.annotate_text = dt.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
			camera.wait_recording(1)
		camera.stop_recording()
and later I'll have it detect pixel movements and it'll just wait until no pixels have moved in the last 10 seconds and then stop_recording()

Thanks for your reply! & sorry I'm so unfamiliar, trying to not do stuff a bad way :D

pageauc
Posts: 224
Joined: Fri Jan 04, 2013 10:52 pm

Re: Pure Python camera interface

Sat Apr 04, 2015 8:00 pm

This is my favourite way to access the pi camera using python. It can take a while to get familiar with the various ways to use it but the recipe's help a lot. Here is an example that might be helpful for someone trying to use the interface. Probably not the best coding but it works OK for what I want to do. https://github.com/pageauc/pi-timolo PI-TIMOLO stands for pi Time lapse, Motion capture, Low Light. You can see where I used some of the recipe examples. I am currently working on a robot openCV and deep learning project that uses the picamera python interface.
Regards
Claude ...
GitHub - https://github.com/pageauc
YouTube - https://www.youtube.com/user/pageaucp

electronmage
Posts: 52
Joined: Fri Sep 27, 2013 11:40 am
Location: Columbus, Ohio

Re: Pure Python camera interface

Sun May 03, 2015 9:25 am

Good morning,

I was awakened by cats fighting outside and couldn't go back to sleep, so I thought I would work on getting my camera to work on my PI2.

raspistill -o photo.jpg works just fine, but the simplest example from picamera fails. But it has failed in two distinctly different ways.

Initially, the first example from "picamera.readthedocs.org" was starting to take the picture, but would time out. The photo file would be created, but would contain no data.

Now, same example program won't run and has the following errors.

Code: Select all

import picamera
from time import sleep

camera = picamera.PiCamera()
camera.capture('image.jpg')

camera.start_preview()
camera.vflip = True
camera.hflip = True
camera.brightness = 60

camera.start_recording('video.h264')
sleep(5)
camera.stop_recording()
The error I am getting is as follows:

Code: Select all

Traceback (most recent call last):
  File "/home/pi/picamera.py", line 1, in <module>
    import picamera
  File "/home/pi/picamera.py", line 4, in <module>
    camera = picamera.PiCamera()
AttributeError: 'module' object has no attribute 'PiCamera'
Any ideas?
Electronmage

--------------------

I like Pi!

Return to “Camera board”