There is an examples in the top of the multicam.lua source fileCode: [Select]experimental code for shooting with multiple cameras
not optimized for best sync, lots of loose ends
usage:
!mc=require('multicam')
!mc:connect()
!mc:start()
!return mc:cmdwait('rec')
!return mc:cmdwait('preshoot')
!return mc:cmdwait('shoot')
!return mc:cmdwait('play')
!mc:cmd('exit')
!mc:testshots{tv=96,sv=411,nshots=2}
would take 2 shots with a 1/2 second exposure at about ISO 100.
If you want to the CLI mdownload command instead of figuring out the API parameters, you could do it like thisCode: [Select]!for i,lcon in ipairs(mc.cams) do con=lcon cli:print_status(cli:execute('mdl A/DCIM /some/path -fmatch=%.JPG$')) end
Some day I'd like to integrate shoot and download into multicam, but I haven't got to it yet.
- The use of mc:download_images() to retrieve the images and have them separated to different folders with the camera name (or serial), to keep them organizedoptions for download_images are a lua array, like
!mc:download_images({dst='${id}/${subdir}/${name}',pretend=true})
The pretend=true above makes it print out what it would do, instead of doing it.help imdl
in the chdkptp prompt to see substitution strings like this. You can also include normal text in dst, like dst='c:/myfiles/camera-${id}/${name}'- Naming the cameras, in order to make it easier to debug possible errors or send individual commands. And somehow, make these names persistent from session to session. Optional (making groups of cameras)multicam doesn't let you name cameras, but they have a number, which can be saved across sessions if the cameras report a serial number (very old cameras don't).
- Setting a few basic parameters on cameras (or groups of cameras), like exposure or focus. I've used testshots for this, but couldn't figure out how APEX96 units work.First, I'd suggest using mc:shoot() rather than mc:testshots(). It provides more controls and doesn't spam the screen with test output.
mc:shoot({tv=exp.shutter_to_tv96(1/100)})
For ISO, use iso_to_sv96, and for aperture use f_to_av96!mc:cmdwait('call <some CHDK lua code>')
with the script functions listed at https://chdk.fandom.com/wiki/CHDK_Scripting_Cross_Reference_Page
- mc:cmd('id') turned out to be really handy, I saw a similar thing by waterwingz (number and status in the display) and wanted to ask for a similar thing. This does it, but... First time I used it, the list numbered 3 cameras as 1, 2 &3, but in the display the cameras were offset by one number (2,3,&4). I unplugged my mouse (only usb thing I had connected to the laptop aside from cameras) tried again and numbers showed up correctly. Now tried again, with mouse plugged and it's working fine too...?? Are these numbers persistent? I suppose not, any way to make them persistent from session to session?You can make them persistent using the camera list function I mentioned in the previous post.
!mc:save_list('cams.txt')
If you want to make a list of only some of the cameras, you can use mc:sel() to select them first. -- select all available cameras
mc:sel('all')
-- select camera ID 1
mc:sel(1)
-- select cameras 1,3 ,5
mc:sel({1,3,5})
-- select cameras 3 through 9
mc:sel({min=3,max=9})
mc functions like mc:shoot and mc:cmdwait operate on all the selected cameras.mc:connect({list='cams.txt'})
-I'd like to dig deeper into the variables for mc:shoot, where can I check them?The major multicam functions are usually documented in multicam.lua. Find "function mc:shoot" and then look at the part above between --[[ and --]]
I've tried !mc:cmdwait('call <get_focus_ok>') but nothing happened, why do mc:shoot variables syntax differ from the cross reference page you linked? I think I'm not using this correctly :(Because they're different things ;)
!mc:print_cmd_status(mc:cmdwait('call return get_focus_ok()'))
That outputs a verbose structure like1: {
done=true,
failed=false,
status={
status={
[1]=false,
},
cmd="call",
},
}
2: {
...
The outer 1 means the stuff in the following { } is for camera ID 1!status,r=mc:cmdwait('call return get_focus_ok()') if status then for id,v in ipairs(r) do if v.failed then printf('%d: failed\n',id) else printf('%d %s\n',id,tostring(v.status.status[1])) end end end
(note above is all one line)And finally, once i get the code properly set up, I'd like to create BAT executables with groups of orders sent to camera (one to initialize, one to set focus and lock it, one to set exposure, one to shoot in sync, and last one to download and delete images) instead of sending lines of code one by one.I'd suggest using Lua files you can run from the chdkptp prompt rather than bat files for most of this, because if you quit chdkptp in between you'd need to re-connect and re-initialize between each one.
mc=require'multicam'
mc:connect()
mc:start()
mc:rec()
And then in the chdkptp prompt, use!dofile('myinit.lua')
Note that inside the myinit.lua file, the mc: commands do NOT have an ! in front of them. The ! in chdkptp is what tell chdkptp that the thing following it should be treated as chdkptp Lua code.chdkptp -e"exec dofile('myinit.lua')"
!mc:shoot({tv=exp.shutter_to_tv96(1/100).iso_to_sv96(100})
ERROR: compile failed:[string "mc:shoot({tv=exp.shutter_to_tv96(1/100).iso_t..."]:1: ')' expected near '}'
!mc:cmdwait('call <reboot>')
Ok, been doing a bit of testing. Seems like it's starting to work. A couple of doubts...Yes. Each thing you want to set is like tv=..., separated by commas. like
Can I specify multiple shooting variables? F=4, shutter 1/100, iso 80 all at the same time? I've tried different combinations, this is one of them, there must be an obvious syntax error :(
!mc:shoot({tv=exp.shutter_to_tv96(1/100), sv=exp.iso_to_sv96(100),av=exp.f_to_av96(4)})
One thing to note on ISO, if you use the above, the value that gets set won't be exactly what you'd get setting ISO 100 in the Canon UI. The firmware uses two kinds of ISO values, which we refer to as "market" and "real". The difference is depends on the model.!mc:cmdwait('call set_iso_mode(100)')
And, is there a command to reboot all the cameras? I see it useful when the whole bunch of them needs to be rebooted... Tried this, but to no avail :(First, the <> in my example were just to say something goes there, it should not be part of the actual code.Code: [Select]!mc:cmdwait('call <reboot>')
!mc:cmd('call reboot()')
Note you do not want to use cmdwait with reboot: cmdwait means chdkptp sits around asking the cameras for a response, but reboot will break the connection so you'll get a bunch of errors. In fact, you probably want a delay like!mc:cmd('call sleep(1000) reboot()') mc:disconnect()
which tells the camera side code to wait one second, while the chdkptp side code disconnects immediately.chdkptp -e"exec dofile('start.lua')"
And the matching LUA:mc=require'multicam'
mc:connect({list='cams.txt'})
mc:start()
mc:cmd('id')
mc:cmdwait('rec')
Something like: Press 1 to start, 2 to intialize sync, 3 to set focus, 4 to set exposure, 5 to shoot, 6 to download images and 7 to shutdown and exit. Is this the correct/advisable way to do it? (I'm having a friend write that .bat, that's why i'd like to know in advance)!mc:cmd('call get_focus_ok()')
--- or less verbose!status,r=mc:cmdwait('call return get_focus_ok()') if status then for id,v in ipairs(r) do if v.failed then printf('%d: failed\n',id) else printf('%d %s\n',id,tostring(v.status.status[1])) end end end
---and!mc:cmd('call get_focus_state()')
First two are always false, third one does nothing. I see get_focus() needs and input value to set focus on a given distance, so... Which one is the command to tell the camera just to autofocus? Suppose I'll have to use it with cmdwait and then issue a set_aflock(1). I can´t seem to get this to work. :( 1 - In order to have the same filename for each shot across all cameras, you suggested using a dummy file. I suppose this is a "read-only" jpg inside DCIM?On startup, the camera will set the image number based on the highest numbered image that matches the camera naming convention. So if you create a file called IMG_0001.JPG in the current image directory, the first shot after reboot should be IMG_0002.JPG and so on.
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_0001.JPG","wb") fh:close()')
(edit: the above assumes you've deleted all other images, the camera looks at the highest numbered image)2 - I have to install CHDK in the remaining 27 cameras, and would like them to have the same CHDK startup configuration. Which is the file that holds this info? Can't seem to find it.You can copy all the .CFG files from the CHDK directory.
3 - As suggested I've started to create a few different lua files with batches of commands. My goal is to create a single .bat executable that invokes these different lua files as in a menu usingAs I mentioned in the earlier post, if you quit chdkptp between actions (as would be required if your UI is in the batch file), you will need to re-initialize and reconnect for each of these options. So you'd be better off prompting for the option 1, 2 etc inside chdkptp. If you are using chdkptp in CLI mode, you could do something likeCode: [Select]chdkptp -e"exec dofile('start.lua')"
Something like: Press 1 to start, 2 to intialize sync, 3 to set focus, 4 to set exposure, 5 to shoot, 6 to download images and 7 to shutdown and exit. Is this the correct/advisable way to do it? (I'm having a friend write that .bat, that's why i'd like to know in advance)
repeat
print('1) start, 2) intialize sync, 3) set focus, 4) set exposure, 5) shoot, 6) download images 7) shutdown and exit')
local option = cli.readline('mc> ')
if option == '1' then
mc:connect({list='cams.txt'})
mc:connect()
mc:start()
mc:cmd('id')
mc:cmdwait('rec')
elseif option == '2' then
mc:init_sync()
elseif ... other options go here ...
elseif option == '7' then
mc:cmdwait('play')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
end
until option=='7'
If you use the GUI, these could be done with IUP buttons instead. However, using the GUI introduces a lot of additional complexity and room for possible issues with multicam.4 - I'm not understanding well the procedure for the cameras to focus, and then lock focus. I've triedFirst, get_focus_ok() just reports whether the camera thinks auto focus was successful, meaning it found *something* to focus on. It is only updated when the shutter is half pressed and get_shooting becomes true.
Which one is the command to tell the camera just to autofocus? Suppose I'll have to use it with cmdwait and then issue a set_aflock(1). I can´t seem to get this to work. :(You could do it after preshoot. Whether set_aflock works and does what you want in half shoot may depend on the camera. If it doesn't, you could try using key presses to enable AF lock instead of set_aflock(). This should work in preshoot, like
!mc:cmdwait('preshoot')
!mc:cmdwait('call click"left" sleep(100) release"shoot_half"')
The key(s) to enable canon AF lock may vary depending on your camera. On cameras with native MF, it may just put you in MF mode, with SET required to dismiss the focus UI.!mc:cmdwait('preshoot')
!mc:cmdwait('call local sd=get_focus() release"shoot_half" sleep(500) set_mf(true) set_focus(sd)')
This will only work on models that support set_mf and have working focus override in MF. The sleep may be needed to prevent crashes that happen when set_mf is called before the camera is fully done leaving half shoot.5- Ideally in the future (completely optional), once the cameras are on their final placement, I think it'd be great to have each camera's focus point saved in an external file, and recall it at the start of every session. But this is just dreamland material for me right now. Better focus on the other stuff :)This would definitely be a good feature, I may be able to add support for it in multicam at some point.
!dofile('MENU.lua')
This is MENU.luarepeat
print('1) start, 2) intialize sync, 3) set focus, 4) set exposure, 5) shoot, 6) download images 7) shutdown and exit')
local option = cli.readline('mc> ')
if option == '1' then
mc:connect({list='cams.txt'})
mc:connect()
mc:start()
mc:cmd('id')
mc:cmdwait('rec')
elseif option == '2' then
mc:init_sync()
elseif == '3' then
mc:shoot()
elseif == '4' then
mc:shoot()
elseif == '5' then
mc:shoot()
elseif == '6' then
mc:download_images({dst='c:/download/TEST01/Camera${id}/${name}',delete=true})
elseif option == '7' then
mc:cmdwait('play')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
end
until option=='7'
This is what I get in CLIERROR: call failed:MENU.lua:12: unexpected symbol near '=='
stack traceback:
[string "dofile('MENU.lua')"]:1: in main chunk
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:733: in function <C:\CHDKPTP\lua\cli.lua:724>
(...tail calls...)
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:285: in function 'execute'
C:\CHDKPTP\lua\gui.lua:683: in function 'action'
C:\CHDKPTP\lua\gui.lua:642: in function <C:\CHDKPTP\lua\gui.lua:640>
(...tail calls...)
[C]: in function 'MainLoop'
C:\CHDKPTP\lua\gui.lua:758: in function <C:\CHDKPTP\lua\gui.lua:731>
(...tail calls...)
C:\CHDKPTP\lua\main.lua:286: in main chunk
[C]: in function 'require'
[string "require('main')"]:1: in main chunk
Any help? There seems to be something either missing or wrong :( repeat
print('1) start, 2) intialize sync, 3) set focus, 4) set exposure, 5) shoot, 6) download images 7) shutdown and exit')
local option = cli.readline('mc> ')
mc=require('multicam') -- took the liberty of adding this just in case
if option == '1' then
mc:connect({list='cams.txt'})
mc:connect()
mc:start()
mc:cmd('id')
mc:cmdwait('rec')
elseif option == '2' then
mc:init_sync()
elseif option == '3' then --added 'option' after elseif as it was missing
mc:shoot()
elseif option == '4' then --added 'option' after elseif as it was missing
mc:shoot()
elseif option == '5' then --added 'option' after elseif as it was missing
mc:shoot()
elseif option == '6' then
mc:download_images({dst='c:/download/TEST01/Camera${id}/${name}',delete=true})
elseif option == '7' then
mc:cmdwait('play')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
end
until option=='7'
ERROR: call failed:attempt to yield from outside a coroutine
stack traceback:
C:\CHDKPTP\lua\gui.lua:675: in function 'readline'
MENU.lua:3: in main chunk
[C]: in function 'dofile'
[string "dofile('MENU.lua')"]:1: in main chunk
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:733: in function <C:\CHDKPTP\lua\cli.lua:724>
(...tail calls...)
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:285: in function 'execute'
C:\CHDKPTP\lua\gui.lua:683: in function 'action'
C:\CHDKPTP\lua\gui.lua:642: in function <C:\CHDKPTP\lua\gui.lua:640>
(...tail calls...)
[C]: in function 'MainLoop'
C:\CHDKPTP\lua\gui.lua:758: in function <C:\CHDKPTP\lua\gui.lua:731>
(...tail calls...)
C:\CHDKPTP\lua\main.lua:286: in main chunk
[C]: in function 'require'
[string "require('main')"]:1: in main chunk
Any ideas? Thanks! :)
Hi!The first line of the error message should identify the line where the problem is. In this case
Did my first test with the menu, and seems like there's something wrong.
Any help? There seems to be something either missing or wrong :(
ERROR: call failed:MENU.lua:12: unexpected symbol near '=='
Looking at line 12 of MENU.lua: elseif == '3' then
"option" is missing in the elseif statement. It should be like the ones above, checking if option is equal to the value, like elseif option == '3' then
The same is true in some of the following ones.Yeah, got that. Check reply#10 as i added 'option' just before you pointed it out :)The new error looks like it's related to using "readline" in the gui.
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
(before the 'repeat' loop, and into option 1) but had little success. Will keep trying to debug what's causing the problem.I redid the shutdown process, since issuing a mc:cmdwait('play') before the shut_down gave me a couple of errors and some cameras would turn off with the lens out, and some others would retract the lens but not turn off.Some cameras will crash if you delete images in rec mode.
I removed the line and now they all shut down properly (despite some errors showing up on the CLI)What kind of errors?
- Image numbering: I've inserted a read-only jpg in the DCIM folder, tried the line you suggested in different waysI didn't suggest the file should be read-only. The camera looks for files called IMG_nnnn.JPG, and sets the counter to the highest numbered image on startup.
Since the effect is based on what the camera sees at startup it should be done as the last part of your shooting session (i.e. in your shutdown option) rather than at startup, and all higher number images must have been deleted from the card.Code: [Select]mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
(before the 'repeat' loop, and into option 1) but had little success. Will keep trying to debug what's causing the problem.
- Some cameras (they're all second hand) seem to have the internal clock battery gone (or whatever keeps date and time when off). Maybe this is somehow related to the numbering issue??Unlikely. Generally, saved settings are saved in the cameras onboard flash, not volatile memory powered by the clock battery.
Anyway, I'd like to add a line at startup to set the current date and time (or anything that matches between all cameras), but couldn't find anything except get_time command. Any ideas?The module in lua/extras/syntime.lua can set the camera clock from PC clock.
local lt=os.date("*t")
mc:print_cmd_status(mc:cmdwait(string.format([[
call
if call_event_proc('FA.Create') == -1 then
return 'FA.Create failed'
end
if call_event_proc('InitializeAdjustmentFunction') == -1 then
return 'InitializeAdjustmentFunction failed'
end
if call_event_proc('SetYear',%d) == -1
or call_event_proc('SetMonth',%d) == -1
or call_event_proc('SetDay',%d) == -1
or call_event_proc('SetHour',%d) == -1
or call_event_proc('SetMinute',%d) == -1
or call_event_proc('SetSecond',%d) == -1 then
return 'set failed'
end
return true
]],lt.year,lt.month,lt.day,lt.hour,lt.min,lt.sec),{libs='serialize_msgs'}))
mc:cmdwait('call click"set"')
to make it go away
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
Thought it was meant to be at startup, like resetting the image counter. Will try to implement it tomorrow prior to shutting down, and report back.Ok, thanks for the info! I'll try to grab the shutdown errors tomorrow, in case there's something problematic. Luckily I didn't get any crashes when downloading/deleting images while in rec mode, but perhaps I should add mc:cmdwait('play') before downloading?The crash I mentioned doesn't happen during the download/delete, it happens when you attempt to switch to play, or shut down, after having deleted images in rec mode.
I'll spend some time learning the options in download_images during the next couple of days.Two that might be useful
!mc:download_images({dst='./${id}_IMG_${shotseq}${ext}'})
would give you names, identified by camera, with each cameras images being number 0001, 0002 etc, regardless of the canon image counter.set_aflock 0
sleep 200
press "shoot_half"
do
sleep 200
until not get_shooting
set_aflock 1
release "shoot_half"
x=get_focus
mc:cmdwait('call set_aflock=0 sleep(500)')
mc:cmdwait('call press "shoot_half" sleep(200)')
Not sure how to do the rest... mc>7
call sleep(2000) shut_down()
ERROR: call failed:MENU3.lua:25: attempt to call method 'disconnect' (a nil valu
e)
stack traceback:
[C]: in function 'dofile'
[string "dofile('MENU3.lua')"]:1: in main chunk
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:733: in function <C:\CHDKPTP\lua\cli.lua:724>
(...tail calls...)
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:285: in function 'execute'
C:\CHDKPTP\lua\main.lua:210: in function 'do_execute_option'
C:\CHDKPTP\lua\main.lua:247: in function 'do_no_gui_startup'
C:\CHDKPTP\lua\main.lua:282: in main chunk
[C]: in function 'require'
[string "require('main')"]:1: in main chunk
elseif option == '6' then
mc:cmdwait('play')
mc:download_images({dst='c:/download/TEST01/${id}/_IMG_${shotseq}${ext}',delete=true})
--mc:download_images({dst='c:/download/TEST01/Camera${id}/${name}',delete=true})
elseif option == '7' then
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
end
until option=='7'
And got thismc>7
call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()
call sleep(2000) shut_down()
ERROR: call failed:MENU4.lua:35: attempt to call method 'disconnect' (a nil valu
e)
stack traceback:
[C]: in function 'dofile'
[string "dofile('MENU4.lua')"]:1: in main chunk
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:733: in function <C:\CHDKPTP\lua\cli.lua:724>
(...tail calls...)
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:285: in function 'execute'
C:\CHDKPTP\lua\main.lua:210: in function 'do_execute_option'
C:\CHDKPTP\lua\main.lua:247: in function 'do_no_gui_startup'
C:\CHDKPTP\lua\main.lua:282: in main chunk
[C]: in function 'require'
[string "require('main')"]:1: in main chunk
Line 35 is mc:disconnect(), should I change it to mc:disconnect(1) ???
Note set_aflock is function, so the correct Lua syntax is set_aflock(0)Code: [Select]mc:cmdwait('call set_aflock=0 sleep(500)')
Not sure how to do the rest...
mc:cmdwait('call press "shoot_half" sleep(200)')
Reyalp, regarding the crash after downloading/deleting images in rec mode. This is the error I got. I'm about to try a new version of the script with cmdwait('play') before downloading.Looks like you are using a version of multicam from before when I added disconnect, builds in the download section are a bit old. If you want to use the latest Lua files, you can go to https://app.assembla.com/spaces/chdkptp/subversion/source/HEAD/trunk/lua and click the download button next to "checkout" and use the contents of that zip to replace everything in chdkptp lua folder.Code: [Select]ERROR: call failed:MENU3.lua:25: attempt to call method 'disconnect' (a nil value)
mc:cmdwait('call set_aflock=0 sleep(500)')
mc:cmdwait('call press "shoot_half" sleep(200)')
With those two lines I got the AF to jiggle a bit and enter Half press mode. It's not what I really wanted, but at least if I send this afterwards: status,r=mc:cmdwait('call return get_focus_ok()') if status then for id,v in ipairs(r) do if v.failed then printf('%d: failed\n',id) else printf('%d %s\n',id,tostring(v.status.status[1])) end end end
I get focus confirmation, which is not bad. As I said not what I really wanted, but it somehow did the job :) I'll keep testing, thanks a million.Quote5- Ideally in the future (completely optional), once the cameras are on their final placement, I think it'd be great to have each camera's focus point saved in an external file, and recall it at the start of every session. But this is just dreamland material for me right now. Better focus on the other stuffThis would definitely be a good feature, I may be able to add support for it in multicam at some point.
With those two lines I got the AF to jiggle a bit and enter Half press mode. It's not what I really wanted, but at least if I send this afterwards:Again, I don't think the code Caefix posted does anything you want, and again get_focus_ok() normally means the camera found something to focus on in AF mode.
mc:shoot({sd=2000})
The distance is in millimeters, so the above would be a for a subject 2 meters from the cameras.I don't have one of these big multicam rigs, or a workflow for this kind of 360 capture, so it's helpful to have input from people who do.I don't have it... yet, but I'm thinking ahead. Hopefully during this week I'll finally move in and start building it. I can foresee that the biggest problems will be practical/hardware related: power and camera management (reliable supply, turning on/off, issues related to USB connections, etc...), FOV (might need to reposition cameras depending on the scenario, but mostly face scans for now), focus and image quality (top of the list priority).
mc=require('multicam')
repeat
print('1) START&SYNC, 2) FOCUS, 3) FOCUS CHECK, 4) SHOOT (w/params), 5) SHOOT, 6) DOWNLOAD 7) SHUTDOWN REBOOT')
local option = cli.readline('mc>')
if option == '1' then
mc:connect({list='cams.txt'})
mc:start()
mc:cmd('id')
mc:cmdwait('rec')
mc:init_sync()
elseif option == '2' then
mc:cmdwait('call set_aflock(0) sleep(500)') --- This option is temporary, needs refining and/or adding suggested focus distance from file
mc:cmdwait('call press "shoot_half" sleep(200)')
mc:cmdwait('call set_aflock(1) sleep(500)')
elseif option == '3' then
status,r=mc:cmdwait('call return get_focus_ok()') if status then for id,v in ipairs(r) do if v.failed then printf('%d: failed\n',id) else printf('%d %s\n',id,tostring(v.status.status[1])) end end end
elseif option == '4' then ---A prompt here would be ideal, setting exposure for all cams with a given EV value (for simplicity) or specific values?
mc:shoot({tv=exp.shutter_to_tv96(1/50), sv=exp.iso_to_sv96(50),av=exp.f_to_av96(4)})
elseif option == '5' then
mc:shoot() -- Simple, but does it mantain focus distance from option 2?
elseif option == '6' then
mc:cmdwait('play')
mc:download_images({dst='c:/download/TEST01/CAM${id}/_IMG_${shotseq}${ext}',delete=true}) -- A prompt to set different folder name each time would be ideal
elseif option == '7' then
mc:cmdwait('play')
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
elseif option == '8' then
mc:cmdwait('play')
mc:cmd('call sleep(2000) reboot()')
mc:disconnect()
end
until option=='8'
How difficult would be to add a prompt to input certain values/parameters in some of the options? Here's the code i'm using right now (needs refining, but works for now)You can use cli.readline at other points, so you could do something like
local shutter=cli.readline('shutter speed>')
mc:shoot({tv=exp.shutter_to_tv96(tonumber(shutter))})
A couple notes: elseif option == '7' then
mc:cmdwait('play')
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
break
elseif option == '8' then
...
until option=='8'
elseif option == '4' then ---------SHOOT w/FOCUS DIST
local dist=cli.readline('Focus Dist>')
mc:shoot({sd=dist})
elseif option == '6' then ---------DOWNLOAD
local folder=cli.readline('Folder>')
mc:cmdwait('play')
mc:download_images({dst='c:/download/folder/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
elseif option == '4' then ---------SHOOT w/values
local dist=cli.readline('Focus Dist>') fnum=cli.readline('F number>') shutter=cli.readline('Shutter speed>') ISO=cli.readline('ISO>')
mc:shoot({sd=dist, tv=exp.shutter_to_tv96(tonumber(shutter)), sv=exp.iso_to_sv96(ISO),av=exp.f_to_av96(fnum)})
Now, the not so easy one. How should I insert the readline value into the path? This just creates a folder named 'folder? in the download path (i was somehow expecting this to happen :( )No problem, you're learning programming in a roundabout way ;). The stuff in '' or "" in Lua is a string. The value from readline is also a string. In Lua, the concatenate operator .. is used to join strings together, like:Code: [Select]elseif option == '6' then ---------DOWNLOAD
Sorry to ask such basic questions, I'm slowly learning but there's still a lot to improve.
local folder=cli.readline('Folder>')
mc:cmdwait('play')
mc:download_images({dst='c:/download/folder/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
mc:download_images({dst='c:/download/'..folder..'/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
And to complicate things further... This is just optional and probably rarely used option. But if I were to insert multiple values in the shoot function, it should be something like this, right?That approach should be OK. You probably want to use tonumber on the ISO and fnum values as well. I would use oneCode: [Select]elseif option == '4' then ---------SHOOT w/values
There might be some adjustments needed in order to convert the inserted values to a proper format (I still don't understand APEX96 numbers, is there any table or list?). But the structure is somehow OK, right?
local dist=cli.readline('Focus Dist>') fnum=cli.readline('F number>') shutter=cli.readline('Shutter speed>') ISO=cli.readline('ISO>')
mc:shoot({sd=dist, tv=exp.shutter_to_tv96(tonumber(shutter)), sv=exp.iso_to_sv96(ISO),av=exp.f_to_av96(fnum)})
shutter=1/50
ISO=50
fnum=4
dist=nil
Then have a menu item likeelseif option == '9' then
dist=tonumber(cli.readline('Focus Dist>'))
if dist == 0 then
dist = nil
end
fnum=tonumber(cli.readline('F number>'))
shutter=tonumber(cli.readline('Shutter speed>'))
ISO=tonumber(cli.readline('ISO>'))
...
And have your shoot command, just refer to those names like your example.if cli.readline('shoot (y/n)>') == 'y' then
mc:shoot({sd=dist, tv=exp.shutter_to_tv96(tonumber(shutter)), sv=exp.iso_to_sv96(ISO),av=exp.f_to_av96(fnum)})
end
!exp.print_tv_table()
!exp.print_av_table()
!exp.print_sv_table()
The shutter one also gives you decimal values of the normal fractions like 1/50 etc.you're learning programming in a roundabout way ;) .Indeed, and what a ride...! :D
I tried inserting the readline like 'folder', "folder", '..folder..' but to no avail. Will try to copy/paste the error later. It surely is a syntax mistake on my side...Code: [Select]mc:download_images({dst='c:/download/'..folder..'/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
mc:connect({list='cams.txt'})
mc:download_images({dst='c:/download/'..folder..'/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
Camera power is still being handled by hand at the beggining of each session, I can cope with this for now but will be grateful for any tips.The usual solution to this is to mechanically hold the power buttons down or cut them out and hardwire the connections, and then control the power supplies with externally in some way.
mc:cmdwait('post_levent_to_ui"UnpressPowerButton"')
after startup to avoid some parts of the camera firmware getting confused by the power button being held.On the software side, I managed to rebuild the camera list with correct numbering, implemented tonumber in the parameters prompt, and finally got the correct value format for each parameter. So it's all working great. Still haven't managed to get the 'folder' string inserted in the download path, I've tried all the combinations I could think of, but no... no way to get it working. And have left the default values idea for later, to avoid further problems, So if anyone could help me with the 'folder' string, I'll be really grateful :)Can you post the specific error or symptom? It would also be helpful to have the code including where "folder" is set.Code: [Select]mc:download_images({dst='c:/download/'..folder..'/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
elseif option == '6' then ---------DOWNLOAD
local folder=cli.readline('Folder>')
mc:cmdwait('play')
mc:download_images({dst='c:/download/'..folder..'/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
And this is the error from the GUI, I'm back at home and can't test it from CLI since i dont have any cameras here. It acts normally, but there's no files to download and does nothing.> !dofile('MENU4b.lua')
ERROR: call failed:attempt to yield from outside a coroutine
stack traceback:
C:\CHDKPTP\lua\gui.lua:675: in function 'readline'
MENU4b.lua:4: in main chunk
[C]: in function 'dofile'
[string "dofile('MENU4b.lua')"]:1: in main chunk
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:748: in function <C:\CHDKPTP\lua\cli.lua:739>
(...tail calls...)
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:285: in function 'execute'
C:\CHDKPTP\lua\gui.lua:683: in function 'action'
C:\CHDKPTP\lua\gui.lua:642: in function <C:\CHDKPTP\lua\gui.lua:640>
(...tail calls...)
[C]: in function 'MainLoop'
C:\CHDKPTP\lua\gui.lua:758: in function <C:\CHDKPTP\lua\gui.lua:731>
(...tail calls...)
C:\CHDKPTP\lua\main.lua:286: in main chunk
[C]: in function 'require'
[string "require('main')"]:1: in main chunk
If I substitute '..folder..' for 'folder' CLI shuts down. This is the error i get in the GUI.> !dofile('MENU4b.lua')
ERROR: call failed:MENU4b.lua:34: '}' expected near 'folder'
stack traceback:
[string "dofile('MENU4b.lua')"]:1: in main chunk
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:748: in function <C:\CHDKPTP\lua\cli.lua:739>
(...tail calls...)
[C]: in function 'xpcall'
C:\CHDKPTP\lua\cli.lua:285: in function 'execute'
C:\CHDKPTP\lua\gui.lua:683: in function 'action'
C:\CHDKPTP\lua\gui.lua:642: in function <C:\CHDKPTP\lua\gui.lua:640>
(...tail calls...)
[C]: in function 'MainLoop'
C:\CHDKPTP\lua\gui.lua:758: in function <C:\CHDKPTP\lua\gui.lua:731>
(...tail calls...)
C:\CHDKPTP\lua\main.lua:286: in main chunk
[C]: in function 'require'
[string "require('main')"]:1: in main chunk
The gui error is the same one you encountered before, which is a general problem with using readline from the GUI. It's not related to the folder variable or download command. You can start the cli with chdkptp -i whether or not you have cameras. Of course, you won't be able try the actual download.Code: [Select]elseif option == '6' then ---------DOWNLOAD
And this is the error from the GUI, I'm back at home and can't test it from CLI since i dont have any cameras here. It acts normally, but there's no files to download and does nothing.
local folder=cli.readline('Folder>')
mc:cmdwait('play')
mc:download_images({dst='c:/download/'..folder..'/CAM${id}/_IMG_${shotseq}${ext}',delete=true})
The syntax in the first example, with '..folder..' is correct. Without the .. is incorrect, resulting in the second error quoted.Code: [Select]> !dofile('MENU4b.lua')
If I substitute '..folder..' for 'folder' CLI shuts down. This is the error i get in the GUI.
ERROR: call failed:attempt to yield from outside a coroutine
stack traceback:
C:\CHDKPTP\lua\gui.lua:675: in function 'readline'
...
local folder=cli.readline('Folder>')
print('folder is',folder)
To make sure the value was being read like you expected. local mydst='c:/download/'..folder..'/CAM${id}/_IMG_${shotseq}${ext}'
print('dst is',mydst)
And as suggest above, you can use "pretend" to see what the download would do, like mc:download_images({dst=mydst,delete=true,pretend=true})
If you aren't sure of syntax, you can try things in the chdkptp console with the ! command.
Regarding the power button hack, do you think I could glue it down? Thanks again for all your help. :DI haven't done it as a permanent mod. I'd personally go for something less permanent and more adjustable. One approach I recall being suggested is rubber bands holding a washer sized to match the button. A zip tie in a similar setup might work too. Another option is to make some kind of bracket with a set screw.
elseif option == '2' then ---------SET ZOOM
local zoom=cli.readline('Zoom>')
mc:cmdwait('call set_zoom('..zoom..')')
Since I have a few non SX150is cameras (A2600, to A2300) I expected this option to be troublesome given the different range in zoom. But despite the zoom ratios being different, it's working nicely with both types (from 0 to 128 they zoom in and out nicely). And I'm proud I did this one on my own :D ERROR: call failed:I/O error
attempted to close non-present device bus-0:\\.\libusb0-0002-0x04a9-0x3271
I've been reading about this type of error, some suggest it can be due to power failures/instability. Indeed it has happened on one of the A2400 that I've connected to a power source (instead of it's battery) while the other three (on the same source) have remained stable. But next up I've had the same type of error on two A2400s using their own original battery. So I'm quite puzzled, but I'm thinking it might be USB related? Bad cables maybe? (just ordered a couple of new ones)On that matter (I believe it is USB related, correct me if I'm wrong) today i've gotten this error a couple of times during different stages of the process (when syncing, zooming,... it's happened in three different cameras)By itself, that error just tells you that the connection went away. It could be that the camera crashed or hung or other USB errors. Power or grounding issues are certainly a possible cause in a multicam rig, but there are plenty of "normal" bugs that can crash cams too.Code: [Select]ERROR: call failed:I/O error
attempted to close non-present device bus-0:\\.\libusb0-0002-0x04a9-0x3271
The big problem here is that if this error happens, it throws down the whole process and has to be restarted, sometimes even cameras need a fresh start. I suppose this is part of the inner working and there's nothing to do about it? Well, just wanted to check. Thanks again :)If the camera hangs or crashes, it at least needs to be restarted. There is a function mc:check_connections described on https://chdk.setepontos.com/index.php?topic=13212.msg135500#msg135500 which might be helpful.
If you notice cameras are crashed, run mc:check_connections(). You can pass it options for connect, e.g. a camera list like {list='mylist.txt'}
It checks for disconnected cameras in the current selection. If none are found, it returns without making any changes.
Otherwise, it exits the camera side script on the remaining cameras. If mc.cam_powercycle_cmd is defined, it runs it with the IDs of the disconnected cameras and waits 5 seconds. If not, it lists the cameras to be restarted and waits for keyboard input.
After the cameras are restarted, it runs mc:connect with the options passed in, followed by mc:start()
Regarding the actual problem, I'll first go the easy way and swap cables for new ones.
Power or grounding issues are certainly a possible cause in a multicam rig, but there are plenty of "normal" bugs that can crash cams too.I quickly scanned all your previous posts (https://chdk.setepontos.com/index.php?action=profile;area=showposts;u=26658) as I recall various conversations going back 5+ years.
Regarding the actual problem, I'll first go the easy way and swap cables for new ones. If problem persists will try to catch the romlog in case it helps. I don't yet see how mc:check_connections is supposed to work, since my menu system just shuts down when the error happens. I suppose I'd need to implement it on a separate file and run it once the error happens, it should powercycle/restart the crashed cameras, wait 5 secs, and bring the whole system back up again? Or at least it kills the script on the connected cameras in order to have a fresh start in all of them...?Ah right I didn't think of that. Mumbo jumbo ahead:
elseif option == '5' then
mc:shoot()
elseif option == '6' then
To elseif option == '5' then
cli:print_status(pcall(function()
mc:shoot()
end))
elseif option == '6' then
pcall calls a function in protected mode http://www.lua.org/manual/5.2/manual.html#6.1And one quick thing... Can't seem to find any options for white balance nor in mc:shoot nor in the Scripting Cross reference... Am I blind? Set_wb anywhere?!?!You can't set custom white balance values. You can set white balance mode with something like
mc:cmdwait('call set_prop(props.WB_MODE,1)')
1 above would be daylight. For older cameras like yours, the numbers will probably beLooking at the scheme, can you spot any future problems I might have to consider? Thanks a lot for your time. Will keep testing tomorrow.Comments and questions below - thanks for those diagrams. That's a good start.
I bought new powerful High CRI LED strips to replace these cheap ones. Noise (due to low power) and color reproduction are horrible with these.Have you noticed if your connection issues seem to occur more frequently if the LED strips are on or off?
Power failures/unstable power with the A series cameras. I initially had 4 (the ii ones) of them into a 4.5V 2A power source. Today I split those 4 into 2 groups. Tested two connected to the a 1A source and seem to be working fine.I'd say a nominal 1A power source might be okay for 1 camera, which can briefly pull 1.5 amps during certain operations. I would not recommend two or three hooked up to that same power supply.
Up to now, the most reliable cameras are the SX150is with their chinese couplers and power source, no problems whatsoever.That's one bit of good news then ...
I'm having two 5V 10A power sources with voltage adjustment delivered tomorrow in order to have a sturdier power source with the A2300-A2600s, will have to create better dummies with ground..?Good! See my previous comment. Budget 2 amps per camera (or 5 -6 cameras maximum per power supply).
Regarding USB connections, I've had to swap my laptop for a more powerful desktop, to overcome numerous connection issues.By "more powerful" I assume you mean software power not electrical power?
But next up I've had the same type of error on two A2400s using their own original battery.This is the most worrying part electrically. I've assume the USB shield and/or 0V pin is the common ground for all the camera. If the A2400's on battery power are not behaving then we might have to think about that.
Today I received the power sources I mentioned: 5V 10A 50W, brand new..Can you post a link to the units you purchased?
Seems like that 0.3V excess was too much to withstand.So here's the big question. Are you absolutely certain you got the polarity correct? An extra 0.3V over the nominal battery voltage of 4.3V is quite unlikely to damage anything. Reversing the polarity can be fatal though.
maybe i should plug two of them so the excess voltage is split?It does not work that way.
It does not work that way.Yeah, I see that now... That gives you a clue about my electrician skills.
Noob mistake, will never happen again. Will check polarity 20 times before plugging something, I promise.It's not just a noob mistake. Don't ask how I know.
My cheap voltmeter doesn't indicate which cable is which (and they're interchangeable, really cheap stuff)I have several really cheap voltmeters that I've acquired over the years. Analog moving coil models and fully digtal model. It is possible to check polarity with even the very worst of them.
And if you say there's a new build coming... I'm not expecting you to do it at all, but just wanted to remind you this ;)In the latest multicam version (r900) I added code to set different shooting options per camera. This doesn't do exactly what you described, but it provides building blocks to do it. The way it works is you can specify any of the shooting options like sv, tv, sd per camera, using an option named camopts, which is a table of id = {options} for each camera. SoQuote5- Ideally in the future (completely optional), once the cameras are on their final placement, I think it'd be great to have each camera's focus point saved in an external file, and recall it at the start of every session. But this is just dreamland material for me right now. Better focus on the other stuffThis would definitely be a good feature, I may be able to add support for it in multicam at some point.
mc:shoot{camopts={[1]={sd=100},[2]={sd=1000}}}
would set the focus distance of camera 1 to 100mm and camera to 1000. If there were cameras other than 1 or 2, they would just use autofocus or whatever was previously set. The top level values are merged, so if you usemc:shoot{sd=500,camopts={[1]={sd=100},[2]={sd=1000}}}
Any other cameras would use 500. You can also specify different values for different cameras, likemc:shoot{sd=500,svm=768,camopts={[1]={sd=100,tv=96},[2]={sd=1000,av=512}}}
so the default focus distance would be 500, all cameras would use svm 768, and cameras 1 and 2 would have shutter and aperture set, respectively.my_focus_table={
[1]={sd=100},
[2]={sd=500},
...
[20]={sd=123},
}
(... means you fill in the rest of the values)mc:shoot{tv=123,camopts=my_focus_table}
If you wanted to just change settings for one camera, you could use my_focus_table[3]={sd=456}
If you want to save it to a file, you could use fsutil.writefile_e(util.serialize(my_focus_table,{compact_arrays=false}),'my_focus_table.txt')
and to load itmy_focus_table=util.unserialize(fsutil.readfile_e('my_focus_table.txt'))
The format is simple, so you could edit the .txt file in a text editor to adjust the distances if you wanted.my_focus_table={}
mc:cmwait('preshoot')
local status,result=mc:cmdwait("call return get_focus()")
for id, res in pairs(result) do
my_focus_table[id]={sd=res.status.status[1]}
end
That's perfect!!!Code: [Select]my_focus_table={}
mc:cmwait('preshoot')
local status,result=mc:cmdwait("call return get_focus()")
for id, res in pairs(result) do
my_focus_table[id]={sd=res.status.status[1]}
end
Here goes a pic of the voltmeter, I have polarity sorted out now.Nice - the labels on your meter probes are a good idea.
But take a look at the meter, cables are interchangeable, and I still can't find any clear indication of + or - to be sure I had them the right way.The earth symbol and the letters COM (for common) attached to the lower terminal should have been a clue as well.
BTW, while checking the dummies I've come to the conclusion I need a different method to make them. .... Do you have any other ideas?how about this link : 3D Printed Camera Battery Emulator (https://hackaday.com/2015/01/21/3d-printed-camera-battery-emulator/) ??
how about this link : 3D Printed Camera Battery Emulator (https://hackaday.com/2015/01/21/3d-printed-camera-battery-emulator/) ??Funny, I found that 3d model some time ago. Having it 3D printed is even more expensive than a 3rd brand working battery! :lol
But fitting a third (ground) cable in between those two will probably short circuit the whole thing.I must have missed something here. Why are you trying to fit a third wire in there? Are you going to try camera triggering via the battery third terminal method?
All of my life, red has been positive and black has been negative when doing DC electronics projects. It's kind of an unofficial international standard.Well, take a look at the wiring at original mercedes charger. I hope that's just an exception... :D
Regardless of the wire colours that thing uses, having them swap like that when passing through a connector is just frightening. Especially when you see the damage that a incorrectly connected automotive batttery can do.All of my life, red has been positive and black has been negative when doing DC electronics projects. It's kind of an unofficial international standard.Well, take a look at the wiring at original mercedes charger. I hope that's just an exception... :D
Hey waterwingz, not sure if you read #65. But you left me in doubt, not sure if I should proceed with the new grounded cabling/dummies... Actually, the center pin on the batteries says T, for temperature? Maybe it's not ground? Is it pointless to use it?? :blink:Yes, the 3rd battery pin is for the battery thermristor. You should not ground it! (edit: low resistance will make the camera think the battery is on fire ;))
Ok, I won't be touching that then! I wonder what waterwingz meant with "problems with grounding" on #41, and on the last bit of #45...Grounding problems can occur with multi-camera rigs primarily because of all the different AC to DC power supplies being used for the USB hubs and "battery eliminators"
interconnecting the 0V wires coming from each dummy battery power packAll the power strips are grounded to building ground. The power supplies for dummies are grounded individually too. The SX150 battery adapters do not seem to have any grounding (will check tomorrow, I'm out of the studio now) Should I interconnect the ground between them? Never thought that would be safe... But again I have no f*** clue of what I'm talking about. Thanks so much for your patience :)
All the power strips are grounded to building ground.That's good (and almost certainly required by your local electrical code).
The power supplies for dummies are grounded individually too.I assume you mean on the AC side? See my previous comment if so.
The SX150 battery adapters do not seem to have any grounding (will check tomorrow, I'm out of the studio now)AC side again? This is not uncommon and allowed by electrical code if the internal design meets a "double insulated" standard.
Should I interconnect the ground between them?Don't touch anything on the main/AC/high voltage side. Please.
Generally, how to optimize a smooth start of the rig? :-*While I'm not sure that's completely necessary, there is certainly nothing wrong with doing it that way.
I would power up each 'tripod' one by one with some secs delay to avoid heavy power peeks. Then boot computer...
Will check it out tomorrow, but here's a drawing to check if I understood correctly. (Note: red cables are untouched)Good - you've got the concept now. I expanded it a bit for you - note that AC mains wires are a different color too. Safety first!
Today I received the power sources I mentioned: 5V 10A 50W, brand new.. I connected the mains cabling and measured with the voltmeter. At first it was giving around 5.3V so I turned it down to the minimum, and it was around 4.6V. I checked the cameras and at the bottom it says 4.3V so thought the cameras could well withstand a little bit more tension and proceeded to plug one of themIncidentally, there is an old trick you could use here to lower the voltage output a little bit more. Install a 5A silicon diode in series with the +5V output of each of these power supplies. Or a seperate 2A diode to each camera. At the current level you will be using it shoild give you a constant 0.5 to 0.6V voltage drop - enough to get to the specified operating voltage of the camera.
Something like this... Or a 2A on each of the cameras, instead.That's correct. Note that diodes are polarity sensitive - although nothing breaks if you put them in backwards here - it just won't work. For most diodes, there is a band printed around one end of the diode that shows the end to connect to the cameras.
In any case, I may temporarily leave this out. There's 0,5V excess, as long as the power source can keep up with it, the cameras should be fine right?It will probably work fine - there is usually a "safety margin" built into most electronic designs.
See what you can find from your electronics supplier and post a part number for me to check?I will, I recently found a great electronics store nearby. I'm pretty sure I'll be visiting them frequently from now on.
those little cameras were not designed to run continuously - most people turn them on, take a couple of photos, and turn them off.I'm aware of this, always been careful not to have them on for too long. Once the rig is 100% up and running I'll implement the necessary precautions to have it working safely for longer periods. For now, there's a lot of testing to be done, I'll be careful. :)
I'll be uploading the content I've created to thingiverse so people can make use of it.Please post a link here when you get it done? I'll add it the wiki too when you do.
Hi guys, I just caught one of the cameras throwing the following error. It somehow manages to bring the whole system down... Seems like there's something wrong with multicam, this one doesn't understand the iD command??The "failed status from unknown cmd..." message means that some other command received a status message generated by the id command. This could happen if you used mc:cmd('id') rather than mc:cmdwait('id')
mc=require('multicam')
mc:cmdwait('post_levent_to_ui"UnpressPowerButton"')
repeat
print('1) START 2) ZOOM 3) SHOOT w/FOCUS 4) SHOOT (w/params) 5) AUTO 6) DOWNLOAD 7) SHUTDOWN 8) REBOOT')
local option = cli.readline('mc>')
if option == '1' then --------START&SYNC
mc:connect()
mc:start()
mc:cmd('id')
mc:cmdwait('rec')
mc:init_sync()
elseif option == '2' then ---------SET ZOOM
local zoom=cli.readline('Zoom>')
mc:cmdwait('call set_zoom('..zoom..')')
elseif option == '3' then ---------SHOOT w/focus
local dist=cli.readline('Focus Dist>')
mc:shoot({sd=dist})
elseif option == '4' then ---------SHOOT w/values
--- local dist=cli.readline('Focus Dist>')
local fnum=cli.readline('F number>')
local shutter=cli.readline('Shutter speed>')
local ISO=cli.readline('ISO>')
mc:cmdwait('call set_prop(props.WB_MODE,1)')
mc:cmdwait('preshoot')
mc:cmdwait('call click"left" sleep(100) release"shoot_half"')
mc:shoot({tv=exp.shutter_to_tv96(tonumber(shutter)), svm=exp.iso_to_sv96(tonumber(ISO)),av=exp.f_to_av96(tonumber(fnum))})
elseif option == '5' then ---------SHOOT
mc:cmdwait('call set_prop(props.WB_MODE,1)')
mc:cmdwait('preshoot')
mc:cmdwait('call click"left" sleep(100) release"shoot_half"')
mc:shoot()
elseif option == '6' then ---------DOWNLOAD
local folder=cli.readline('Folder>')
mc:cmdwait('play')
--- mc:download_images({dst='c:/download/'..folder..'/CAM${id}/CAM${id}_${shotseq}${ext}',delete=true,verbose=true})
mc:download_images({dst='c:/download/'..folder..'/CAM${id}_${shotseq}${ext}',delete=true,verbose=true})
elseif option == '7' then ---------SHUTDOWN
mc:cmdwait('play')
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
break
elseif option == '8' then ---------REBOOT
mc:cmdwait('play')
mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
mc:cmd('call sleep(2000) reboot()')
mc:disconnect()
break
end
until option=='8'
But every time I try to download files, there's one camera which shuts down/fails, i get the attached message (capture4.jpg) and after a few seconds the command window shuts down. I sometimes get an error poiting to the offending camera (capture1.jpg).The chdkptp error really doesn't tell you anything. It just means USB communication failed. The most common case is probably the camera crashing, but problems in the USB system are also possible, especially in a multicam rig.
I've disabled mc:connect({list='cams.txt'}) because i'm constanly unplugging cameras from the array trying to find which one is crashing/failing. And using that line caused errors if one or more listed cameras were not connected.I believe there will just be a warning, and the missing camera won't be added to the list. If this isn't correct, what kind of error do you see?
Additionally, is there a way to have init_sync produce less verbose? It creates hundreds of lines, too many to scroll up and pinpoint which camera might be the offending one...There isn't currently a way to disable those messages, but if a errors happen in download, I'm not sure why you are trying to spot the problem camera in init_sync.
{
["FF81F24C80E64C60B180914B936E8335"]={
["id"]=12
},
["836BB0F4C82942328CE460978F650B7A"]={
["id"]=22
},
["59F76D99E74D4E56A432C01AA1F25F70"]={
["id"]=08
},
["8D6851BE4706416B83CB24D5C51E008C"]={
["id"]=04 },
["CFFBD611EBFA4B3AB7E7E96DDAACD3D7"]={
["id"]=05
},
["535772AB22C94DC390105204ABE1CEB5"]={
["id"]=16 },
["7C5E599D846B453B9C3D2DC6FE50CA60"]={
["id"]=07
},
["510EC32D808848FDAFB75076CD3321A7"]={
["id"]=17
},
["4A7D94B66EA6466E8457913F3278263C"]={
["id"]=1
8 },
["5F000B5E65AA4054AA7379D9D15AEE9F"]={
["id"]=02 },
["CF100970CC43440C8B7A72FBBC70FE72"]={
["id"]=06
},
["913E2905D0C345908575A42E463FF077"]={
["id"]=15
},
["70C41C4110834DEAA1A54BCFE0F6BE70"]={
["id"]=13 },
["AA0D228C8F5D418B967549835F00EAB5"]={
["id"]=24
},
["B4E1ACD96C454ECB84AC0685EF70D81A"]={
["id"]=01 },
["9D224B712F7D4F12B42EAEFA9FBE8388"]={
["id"]=21
},
["5B844D15130B42328BD2DF240F41561A"]={
["id"]=20 },
["3B8F8341FB524051BC1666ABBA19B580"]={
["id"]=14
},
["2C5B486D306C4596B4BAF7D7B6BD35B9"]={
["id"]=03
},
["A0B8A1BD345B455A95B9C1F8AABCEFED"]={
["id"]=10
},
["C483BAA2681E47A78D5A0B5FFFE5A8B2"]={
["id"]=11 }
}
After lots of testing, the crashing camera was identified. I produced a romlog (see attached) and it says Harware Defect so I'll probably have to discard it.Hardware defect doesn't always mean there's a hardware failure. Sometimes CHDK problems make the camera think there's been a hardware error.
It's odd because out from the rig, individually it seems to work fine. I wonder what the romlog says... (maybe power related?)The romlog doesn't obviously tell, but if it only happens in the rig, power problems do seem like a reasonable guess. Or perhaps something about how it's mechanically mounted.
EDIT: About the error with mc:connect({list='cams.txt'}) I've attached a screengrab just before it closes. If I use mc:connect() , everything works fine. Can´t attach "cams.txt", here's the content:It looks like there might be a syntax error in your list, unless it was a mistake pasting in the forum:
["4A7D94B66EA6466E8457913F3278263C"]={
["id"]=1
8 },
If that's supposed to be 18, it shouldn't have a newline.What model and firmware version is the failing camera?Its an IXUS 145 firmware version 100c. I've been testing further and it's a power problem, it all works perfectly until I try to download the images and the cameras go into PLAY mode, lens retracts and that's when I get the error. I've tested it with it's own battery and works fine. So it has to be power related.
elseif option == '2' then ---------SET ZOOM
local zoom=cli.readline('Zoom>')
mc:cmdwait('call set_zoom('..zoom..')')
3) I've finally implemented mc:check_connections in the menu as option "0". Is this the correct way to go? I've attached the error message I got after checking connections. It's been a last minute quick test and I didn't look if they reconnected.mc=require('multicam')
mc:cmdwait('post_levent_to_ui"UnpressPowerButton"')
mc:connect({list='cams.txt'})
mc:start()
mc:cmdwait('id')
repeat
print('0)CHECK 1)SYNC 2)ZOOM 3)SHOOT AF 4)MANUAL 5)AUTO')
print('6)DOWNLOAD 7)SHUTDOWN 8)REBOOT')
local option = cli.readline('mc>')
if option == '0' then --------CHECK
mc:check_connections(cam_powercycle_cmd)
mc:connect({list='cams.txt'})
mc:start()
mc:cmdwait('id')
elseif option == '1' then --------START&SYNC
mc:cmdwait('rec')
mc:init_sync()
4) Would something like this work if I needed to send manual commands to the cameras inside the? Or I should be looking for an exit/break to go back to the command line and then relaunch the script? I'm out of my water with this... :( elseif option == '9' then ---------COMMAND
local command=cli.readline('>>>')
mc:cmdwait('call ('..command..')')
Hi again, testing goes on. I replaced a couple of faulting cameras. I have a couple of questions...I don't think so. You may find USBView helpful https://docs.microsoft.com/en-us/windows-hardware/drivers/debugger/usbview
1) Not directly CHDK related, but is there some way to rename USB hubs in Device Manager so they don't show up the same "Generic USB Hub" name? It'd be handy to rename them with different labels in case one of the cameras goes rogue and shows "USB device not recognized", it would be handy for debugging.
2) I've replaced the faulty IXUS 160 and 145 with A2400s, and suddenly when using option 2 for zooming (see #88 for full code) everything fails... It used to work perfectly yesterday, before I replaced those. Nothing in the code has changed. And now I get "failed timeout" errors in 15 cameras that used to work perfectly before. Any ideas about what might be happening?Not idea. Timeout without any other errors would normally suggest a software problem. USB connection problems, cameras completely freezing etc should generally cause a connection related error.
3) I've finally implemented mc:check_connections in the menu as option "0". Is this the correct way to go? I've attached the error message I got after checking connections. It's been a last minute quick test and I didn't look if they reconnected.The cam_powercycle_cmd is incorrect. mc:check_connections should be passed options you want to use for mc:connect, probably {list='cams.txt'}
mc.cam_powercycle_cmd = "/path/to/some_command"
The command would need to be custom code that accepts a camera ID number and controls the hardware.4) Would something like this work if I needed to send manual commands to the cameras inside the? Or I should be looking for an exit/break to go back to the command line and then relaunch the script? I'm out of my water with this... :(That seems like it should work. Like always, mc:cmdwait will send the code to all selected cameras, so if you want to do different things on some cameras you'd have to use mc:sel first. If you want to execute local code, like you normally do with !, you'd need a different approach. You could either quit your script, or use something like your example above but instead of mc:cmdwait useCode: [Select]elseif option == '9' then ---------COMMAND
local command=cli.readline('>>>')
mc:cmdwait('call ('..command..')')
cli:print_status(cli:execute('exec '..command))
That should be '..command)) or '..command..')) ??Code: [Select]cli:print_status(cli:execute('exec '..command))
So to clarify the workflow, once some cameras fail (after zooming for example) I'd need to mc:sel({1,3,5}) those problem cameras (1,3,5) and then mc:cmdwait('play') and mc:cmd('call sleep(2000) reboot()') (assuming they're still connected and have not crashed), and once they reboot (it'd be nice to have a beep to know they're back up) I send mc:check_connections. Or I got everything wrong? I could try to do all this from the 9 option I showed before...?In the vast majority of cases, I'd expect you need to physically restart the cameras if it's failed in check_connections(). If you can execute a script to reboot, you probably don't need to reboot.
I'm not sure I got the grasp of how check_connections works. If I should reboot cameras manually (meaning physically turning them on and off by hand), I'm afraid that´ll be impossible, because the way the rig is built. I can only turn on/off the whole group of cameras at once.
Regarding that, I made some 3D printed clamps for various cameras models to have the ON button continually pressed. If waterwingz is interested (didn't get any feedback from the battery dummy 3d prints :( ) I could upload them to thingieverse too. Check the attached image.If it's not much trouble, I don't see any reason not to post it. I expect others could find it useful in the future.
EDIT:The former. ".." concatenates a string. cli:execute expects a string like you'd type in the normal chdkptp command prompt. You want to joint "exec " with whatever you typed. So you could type mc:cmdwait('whatever') and getThat should be '..command)) or '..command..')) ??Code: [Select]cli:print_status(cli:execute('exec '..command))
exec mc:cmdwait('whatever')
(exec is the same as !)
elseif option == '4' then ---------SHOOT w/values
local dist=cli.readline('Focus Dist>')
local fnum=cli.readline('F number>')
local shutter=cli.readline('Shutter speed>')
local ISO=cli.readline('ISO>')
mc:cmdwait('call set_prop(props.WB_MODE,1)')
mc:cmdwait('preshoot')
mc:cmdwait('call click"left" sleep(100) release"shoot_half"')
mc:shoot({tv=exp.shutter_to_tv96(tonumber(shutter)), svm=exp.iso_to_sv96(tonumber(ISO)),av=exp.f_to_av96(tonumber(fnum)),sd=dist,nd=2})
I'm attaching a screenshot of the folder. It's camera 12, and it's not just -2 darker, it's much noisier too. Maybe it's (another) faulty camera? :(
I expect some discrepancies between different camera models, but there's one that is responding way off from the rest, it's an A3400. While the exposure on the rest is quite similar, this one is way darker. And even if the EXIF data says it's shot at f4 1/15 and ISO 100, given the amount of noise, I suspect it's shot at much higher ISO.From the specs, it seems like A3400 and A2400 should should be very similar. The zoom, aperture and ISO ranges are the same. In fact, it looks like the only difference is touch screen https://www.dpreview.com/products/compare/side-by-side?products=canon_a2400is&products=canon_a3400is&sortDir=ascending
Seems like it's not responding to the code... Is there any other way to set the parameters and see if it responds better?Overrides pretty much use the same underlying mechanism. However, testing that camera alone with normal chdkptp commands might help understand what's happening.
2) Have a final prompt to confirm after reading the values, likeCode: [Select]if cli.readline('shoot (y/n)>') == 'y' then
mc:shoot({sd=dist, tv=exp.shutter_to_tv96(tonumber(shutter)), sv=exp.iso_to_sv96(ISO),av=exp.f_to_av96(fnum)})
end
Warmer one was shot on friday, with manual input of exposure values (using the menu, values I dont remember). These pics were not shot on the rig, so they don't have the best lighting conditions, it was intentional. Other two were shot today with values inserted (exact figures I inserted are 4 for aperture, 0.05 for shutter, 100 for ISO) and then in Auto. Both Auto pics are correct, but the others...?? Am I doing something wrong in the menu? Am I using the right format for values?? I'm puzzled. Check the code a couple of posts before.I don't think you are doing something wrong, I'd guess it's either a problem with this specific camera, or a bug in the CHDK (or maybe a bug in multicam).
mc:shoot()
mc:shoot({nd=1})
mc:shoot({nd=2})
Main interest is a3400, but including one a2500 to compare would be worthwhile.And finally, this was mentioned before in post #28 (sorry I'm going back to the basics). How should I insert this prompt option into the Shoot menu? I see and "end" there, not sure how to deal with it...I'm not sure I understand, the "end" goes with the preceding "if", so you should be able to just put the whole if / end block in your code where the shoot command was.2) Have a final prompt to confirm after reading the values, likeCode: [Select]if cli.readline('shoot (y/n)>') == 'y' then
mc:shoot({sd=dist, tv=exp.shutter_to_tv96(tonumber(shutter)), sv=exp.iso_to_sv96(ISO),av=exp.f_to_av96(fnum)})
end
Hi Reyalp, I updated the album with the ND pictures. I'm not sure how the command works regarding the ND, but in the A3400 I see no change, and surprisingly, there's a variance in the A2500... Well, take a look. ThxThanks, I think that confirms that your A3400 has a mechanical problem: The ND filter is stuck in the "in" position. The best bet is probably to replace it, but you since you mentioned you had another 3400 that died, you could try to swap some components, or you could add special code to always offset exposure for this camera by the ND value, or try percussive maintenance (https://en.wiktionary.org/wiki/percussive_maintenance).
https://photos.app.goo.gl/GDJ8YisJvqE1KTQp9
Percussive maintenance seems like the way to go. I recovered an SX150 that showed "Lens Error" that way yesterday. I might not be good with electronics, but I'm damn fine slamming cameras :DOne thing you can check is if the camera makes any sound when it tries to put in the ND filter.
mc:cmdwait('preshoot')
mc:cmdwait('call set_nd_filter(1)')
mc:cmdwait('call set_nd_filter(2)')
If you hear some clicking, then you at least know the actuator can be commanded. If it makes no sound, an electrical problem might be more likely, although it might just be really well stuck. !mc:cmdwait('call for i=1,10 do set_nd_filter(1) sleep(100) set_nd_filter(2) end')
Again, this should be done in half press.I was puzzled with the results since I expected the A2500 to compensate for the ND filter, but yeah.. What you said makes more sense.Yep, as a general rule, the Canon autoexposure does not know about CHDK overrides.
Quick question: Don't worry about the code for now, it's just an ou of the box idea. Would it be possible to shoot a quick burst of 3 or 4 images (I know how to do this), and save them as JPGs, but keep the DNG only for the last one? JPG to allow for a quicker burst/write rate and after the last one there'd be time for the DNG to write. This would be an "emergency" shot, that would allow me to combine multiple JPGs to reduce noise with median filter (just a crazy idea, but is it doable?) I would still need to check if the burst rate across different cameras would be quick enough (only the first shot would need to be synced). Thx :)It should be possible, but would need code changes in mc:shoot or the camera side code if you don't want to do the DNG as a separate shot.
Regarding the 3 JPG+1DNG thing.. I've tested the burst speed in the A2500 and it averages at 1fps, which is not ideal, but who knows it might do the trick? I've tested the technique with a stationary object (a mannequin) and the noise reduction is quite good (combining 3 shots). Anyway, it's just a crazy idea. I have a million more things to deal with a the moment :)You won't get much better than 1 fps on cheap Canon P&S, but as you say, if your subject is still enough, the noise reduction is good.
If you wanted to start from the cameras current focus distance from auto focus, you could use something likeAnd then,Code: [Select]my_focus_table={}
mc:cmwait('preshoot')
local status,result=mc:cmdwait("call return get_focus()")
for id, res in pairs(result) do
my_focus_table[id]={sd=res.status.status[1]}
end
fsutil.writefile_e(util.serialize(my_focus_table,{compact_arrays=false}),'my_focus_table.txt')
To create a file with the focus distances where the current AF is? Correct?my_focus_table={
[1]={sd=2100,tv96=0.06,svm=100,av=4,nd=2},
[2]={sd=1980,tv96=0.04,svm=100,av=4,nd=2},
...
A few more things...{
[1]={
sd=666
},
[2]={
sd=479
},
[3]={
sd=-1
},
[4]={
sd=731
},
[5]={
sd=505
},
[6]={
sd=1536
},
[7]={
sd=1558
},
[8]={
sd=1244
},
[9]={
sd=1635
},
[11]={
sd=482
},
[13]={
sd=-1
},
[14]={
sd=526
},
[15]={
sd=798
},
[16]={
sd=-1
},
[17]={
sd=2576
},
[18]={
sd=1153
},
[19]={
sd=581
},
[20]={
sd=2201
},
[21]={
sd=842
},
[22]={
sd=559
},
[23]={
sd=-1
},
[24]={
sd=479
},
[25]={
sd=-1
}
}
Number 3, is a G10, I can see it nailed the focus and can see every detail, but it says (-1) which I guess means it didn't lock focus. How much should I trust these numbers? Are they in different scales/proportions? They differ from around 500 to 2500 and all cameras are placed around 200cm from the subject with the central focus point aimed at it.
Number 3, is a G10, I can see it nailed the focus and can see every detail, but it says (-1) which I guess means it didn't lock focus. How much should I trust these numbers? Are they in different scales/proportions? They differ from around 500 to 2500 and all cameras are placed around 200cm from the subject with the central focus point aimed at it.-1 means "infinity". Aside from that, the values are always in mm, so your cameras are nominally focusing between 0.5 and 2.5 meters, or infinity. These values are not particularly precise. At wide angle, the depth of field is large, and it's normal for "infinity" to start fairly close.
FWIW, you should only need to set the values that are different from what is set in the command. Setting them all like you have here is fine too.Code: [Select]my_focus_table={
[1]={sd=2100,tv96=0.06,svm=100,av=4,nd=2},
[2]={sd=1980,tv96=0.04,svm=100,av=4,nd=2},
...
- Reboot option makes one of the cameras lens crackle and then crashes while retracting the lens (just one of the A2500, the rest are fine) whereas if I Shutdown, it works fine. Odd...I'd suggest switching to playback and letting the lens retract (or using an eventproc to retract it https://chdk.setepontos.com/index.php?topic=6857.msg73227#msg73227) before using reboot.
- Zooming is still very unstable. Most cameras do zoom in/out nicely, but there's four cameras (in the same power source) that always crash. Interestingly, I get a timeout error on about fifteen of them, but excepting these four i can reconnect to the rest. Looks like the error in those four has a cascade effect in the rest?? I'll try to see what happens if a couple of them are battery poweredThis seems very likely to be a power issue.
- I suppose that check_connections and the current workflow doesn't allow for any remote reboot command, right? It's quite incovenient to reboot them manually, given the fact that I installed clamps in the on/off buttons so they power up automatically. (I should install individual switches on all the power lines?) :(As I said before, if the camera is crashed, then there is not going to be any software way to reboot it. To have software controls, you would need to implement the hardware and software to actually control the power supplies (using GPIO and relays for example)
- Oddly enough, the one single IXUS 165 I (still) have... Always crashes starting the download stage if there's been a shoot before. If I just connect and download, everything works fine.A romlog and the specific code or sequence of actions involved might be helpful. Also, do you mean ixus 160? There isn't (AFAIK) an ixus165 (https://global.canon/en/c-museum/product/dcc832.html) port.
- A minor thing. Looks like the G10s have a different zooming ratio than the SX150 and A2xxx. If I enter 40 as zoom value, they go way beyond what the others do. Would it be possible to add zoom values to the camopts table? Just a quick idea...The zoom value is in "steps" so it will vary a lot between cameras. It would make sense to allow in camopts, I'll look into adding that. An option to set zoom by 35mm equivalent focal length would also be a good idea.
- And finally, while doing the 3D reconstruction JPGs (oddly enough) are giving me better results than DNGs. I didn't expect this, unfortunately the colour balance (even if set to WB_MODE,1) is all over the place. Any ideas on how to get a consistent white balance across the JPGs in the whole rig? I've tried correcting it in Photoshop and Lightroom, but it's very cumbersome and inconsistent :(This doesn't surprise me, Canon jpeg processing is very good, and you usually have to work to get better results from raw.
I'd suggest switching to playback and letting the lens retract (or using an eventproc to retract it https://chdk.setepontos.com/index.php?topic=6857.msg73227#msg73227 (https://chdk.setepontos.com/index.php?topic=6857.msg73227#msg73227)) before using reboot.The reboot and shutdown options are basically the same, cameras go into play mode and then the reboot/shutdown command is sent. I'm puzzled because shutdown works perfectly 100% of the times, but reboot doesn't. I doubt it's power related, since shutdown is OK and this camera is in a safe power source (not the one in conflict with the zoom option). Here's the code.... In any case it's a minor thing, I only mentioned because I find it odd.
However, the fact that only one of the a2500 is affected suggests there's a hardware or power supply factor involved too. You could try getting a romlog from that camera.
elseif option == '7' then ---------SHUTDOWN
mc:cmdwait('play')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
break
elseif option == '8' then ---------REBOOT
mc:cmdwait('play')
mc:cmd('call sleep(2000) reboot()')
mc:disconnect()
break
end
This seems very likely to be a power issue.I couldn't test it yesterday, I will today... That group of cameras (in the same power source) is my main headache, I will test with batteries and split into two power sources if needed. If nothing works, I'll have to install mini switches for each camera and make use of check_connections (which BTW is such a great addition, congrats!)
A romlog and the specific code or sequence of actions involved might be helpful. Also, do you mean ixus 160? There isn't (AFAIK) an ixus165 port.Yeah IXUS 160, sorry. The code is basically the same as in #88, the sequence is just Init&Sync, Shoot a couple of pics and then Download... Crashes. If I reboot the whole system and Init&sync and go directly to download, it works fine...
The zoom value is in "steps" so it will vary a lot between cameras. It would make sense to allow in camopts, I'll look into adding that. An option to set zoom by 35mm equivalent focal length would also be a good idea.That would be awesome! The camopts table is something else I'll be testing today. AV values will be eliminated and I'll compensate exposure with shutter speed. Just wanted to check if the format is the right one. I'll build the whole table like that, so changes in the future are easier to insert instead of setting individual exceptions (makes more sense in MY head)
This doesn't surprise me, Canon jpeg processing is very good, and you usually have to work to get better results from raw.Canon processing is a bit too harsh with noise reduction and sharpening, but does a great job with distortion correction (which I think is what benefits the 3D reconstruction) That's the reason I was hoping for an in-camera solution. The shooting conditions are always going to be the same, so I'll need to test the best values for each camera (but I believe that's external and not possible to implement in camopts, right?) Edit:I was referring to White Balance here
If shots are taken in similar lighting with the same WB setting, you could potentially come up with processing profiles you can re-use between sessions. Raw Therapee lets you do command line processing with saved profiles (https://rawpedia.rawtherapee.com/Command-Line_Options (https://rawpedia.rawtherapee.com/Command-Line_Options)), I expect similar things are possible with other programs.
Aside from color balance, you may also need to correct lens distortion in CHDK raw. This could vary a lot between camera models.
!mc:shoot({zoom=10,sd=2000,zoomwait=200,camopts={{zoom=50},{zoom=100}}})
This sets the default zoom position to 10, subject distance to 2 meters, wait to 200ms. Camera 1 has zoom set to 50, camera 2 is set to 100.The reboot and shutdown options are basically the same, cameras go into play mode and then the reboot/shutdown command is sent. I'm puzzled because shutdown works perfectly 100% of the times, but reboot doesn't.They do different things in CHDK code. A "soft" shutdown in CHDK should take care of retracting the lens just like if you had pressed the power button. A reboot is much less clean.
I doubt it's power related, since shutdown is OK and this camera is in a safe power source (not the one in conflict with the zoom option).If you have many cameras of the same model (and firmware, since only 100A exists for A2500), and only one is affected, it suggests a hardware difference somewhere. Whether it's in the camera itself or external hardware is hard to guess.
AV values will be eliminated and I'll compensate exposure with shutter speed.Note G10 and SX150 do have adjustable apertures, so you may need to control those.
Canon processing is a bit too harsh with noise reduction and sharpening, but does a great job with distortion correction (which I think is what benefits the 3D reconstruction)FWIW, you can control the sharpening of Canon jpeg a bit using the "my colors" custom setting, which can be controlled using propcases from script.
That's the reason I was hoping for an in-camera solution. The shooting conditions are always going to be the same, so I'll need to test the best values for each camera (but I believe that's external and not possible to implement in camopts, right?) Edit:I was referring to White Balance hereI think I didn't read your previous post carefully enough, I thought your WB problem was in raw processing. For jpeg, you can only set WB mode from script, and in modes other than custom, the cameras will still adjust the WB for each shot. To use custom WB, you'd need to set it individually on each camera.
mc:connect
if connect=true then set_led 9 1
But you know my syntax is not enough to get it working :( Also, some more stuff... A few cameras are permanently throwing errors when zooming. Got a romlog and they all share the same error: ASSERT!! FocusLensController Is this too bad?What is the specific sequence of events that's triggering the error? Are you using the new zoom option on mc:shoot, or setting zoom as a standalone call to set_zoom()?
!mc:cmdwait('call bi=get_buildinfo() return bi.build_number,bi.build_revision')
The assert by itself may be be one we've seen before related to focus. I also attached a romlog for an A2400 which afterwards seems to be working fine, says Hardware Defect, but don't know related to what.romlog is recorded when there is a problem, and stays there until the next one is recorded. So, if it's working fine, don't worry about it. The romlog is from a lens error, which could happen if the lens was jammed.
But you know my syntax is not enough to get it working :(The syntax to turn an LED on and off from multicam would be like
!mc:cmdwait('call set_led(1,1)')
!mc:cmdwait('call set_led(1,0)')
The first number specifies the LED, and the second specifies on or off. However, which number corresponds to which physical LED varies by camera model. For cameras with only 2 LEDs, usually 0 will be the power / status LED and 1 will be the AF. For others, you need to test.Additionally, my two cents regarding mc:connect({list='cams.txt'}) It's great in order to have a tidy list of cameras. But in the process, since I'm quite often adding/changing/having problems with some of the cameras, newly added cameras are ignored at connect. I think it would be ideal if it would (as and option maybe?) connect to all available cameras, and id known ones according to the table, and new ones randomly... Does this makes sense?Being able to add cameras while keeping the IDs of known ones does make sense.
EDIT: Something odd is going on with focusing distances. Setting it to 2000, brings it way beyond where it should be. Way past 4 meters, subject is at 2 meters and out of focus. For more precision I gave it a try with cameras zoomed in (shorter DOF) Values do not correspond with real life measurements. I'm puzzled. Here's a gallery with my beautiful test subject and attached is myfocustable.txt too.I'm not sure what to make of this. As I said before, the number aren't super accurate, but I'd expect them to be a bit closer than your description suggests.
The syntax to turn an LED on and off from multicam would be likeI wanted to make it conditional,depending if they connected fine or not (is this a silly option?), thus the if connect=true then !mc:cmdwait('call set_led(1,1)') I think I can manage that by myself, will try later.Code: [Select]!mc:cmdwait('call set_led(1,1)')
!mc:cmdwait('call set_led(1,0)')
Being able to add cameras while keeping the IDs of known ones does make sense.That would be sweet
I'm not sure what to make of this. As I said before, the number aren't super accurate, but I'd expect them to be a bit closer than your description suggests.The gallery pics are the result of preshoot and writefocustable commands. They are in good focus, distances are shown in the table. What I wanted to show, is the disparity between numbers, given the known distance of the subject (about 2 meters to all of the cameras). There's cameras focused at 90cms and others at 3,5m... Focus override does work, I did tests and figures around 1000 and 1200 worked best generally, but some cameras were out of focus. To me it seems like setting a numeric distance to all of them is unreliable in order to get the best focus. I guess different models interpret these distances differently? I think I'm getting better focus with a simple preshoot and not setting it manually...
One thing to check is whether focus override is actually working. For example, if you take a series of shots with sd=10, sd=100, sd=1000, sd=10000
You can do this without involving myfocustable.txt
I'm not sure what the images in your gallery are supposed to show. I didn't look closely at all of them, but the ones I did don't seem to be terribly out of focus.
What is the specific sequence of events that's triggering the error? Are you using the new zoom option on mc:shoot, or setting zoom as a standalone call to set_zoom()?I'll check the version later, but it should be quite recent. The sequence is the one stated in #88. Connect, start, ID, init_sync and then call set_zoom (with the value stated in cli.readline). No camopts table yet, nor mc:shoot zoom... I did it the old fashioned way. Maybe they enter preshoot after init_sync and that causes problems? Regarding the romlog and the A2500s. It happens to 3 of them. Right now I'm not sure if I have more (there's a mix of 2400, 2500 and 2600) will check later, but it could be a model specific problem. In any case, is the assert too bad? are those cameras recoverable?
Are all of the cameras that are affected A2500? If so, are *all* of your A2500 affected, or just some?
What version of CHDK are you using?
The assert by itself may be be one we've seen before related to focus.
I wanted to make it conditional,depending if they connected fine or not (is this a silly option?), thus the if connect=true then !mc:cmdwait('call set_led(1,1)') I think I can manage that by myself, will try later.Maybe I'm missing something, but the command will never reach cameras that aren't connected.
The gallery pics are the result of preshoot and writefocustable commands. They are in good focus, distances are shown in the table. What I wanted to show, is the disparity between numbers, given the known distance of the subject (about 2 meters to all of the cameras). There's cameras focused at 90cms and others at 3,5m... Focus override does work, I did tests and figures around 1000 and 1200 worked best generally, but some cameras were out of focus. To me it seems like setting a numeric distance to all of them is unreliable in order to get the best focus. I guess different models interpret these distances differently?As I said, the values aren't very exact. I'm slightly surprised they're as far off as you've reported, but from your description it sounds like that's the explanation.
I think I'm getting better focus with a simple preshoot and not setting it manually...If you're worried about autofocus being reliable, you could start with the camera autofocus value, like your myfocustable.txt. That would let you keep the same distance for shots in the same session, and you could adjust manually in the file if some were off. You would probably want to start from autofocus again any time the zoom level changed.
EDIT: It's version 1.4.1 5414. Correction it's two A2500 and one A2600, all have the same Romlog showing the assert mentioned before. And they keep crashing when zooming. The bunch of A2400 and A2300 (and the rest of the cameras) are working fine.I'd suggest trying the 1.5 branch (so called "unstable"), as we fixed some issues related to zoom which cause a crash like this. Probably best to test on one camera before updating the whole rig.
Maybe I'm missing something, but the command will never reach cameras that aren't connected.See? I'm SO clever sometimes... ???
As I said, the values aren't very exact. I'm slightly surprised they're as far off as you've reported, but from your description it sounds like that's the explanation.Yeah, no doubt about it. I will basically have two zoom settings, and the general idea (once everything is working) is to create two presets, one for full body scans and one for face scans. Every detail will be set accordingly in two different tables... Someday...
If you're worried about autofocus being reliable, you could start with the camera autofocus value, like your myfocustable.txt. That would let you keep the same distance for shots in the same session, and you could adjust manually in the file if some were off. You would probably want to start from autofocus again any time the zoom level changed.
I'd suggest trying the 1.5 branch (so called "unstable"), as we fixed some issues related to zoom which cause a crash like this. Probably best to test on one camera before updating the whole rig.I will first update the faulty cameras and see how they respond. Eventually I will update all, but for the moment... will these work together with the older versions? As a side note, today I managed to detect a USB problem that was giving me headaches for the last couple of days. Hooray for me, it's been sorted. And most importantly, the LED on thing is VERY handy! :D
Since the SD cards are already prepared, you can just download the zip from the autobuild http://mighty-hoernsche.de/trunk/ (http://mighty-hoernsche.de/trunk/) and upload the files with chdkptp. See https://chdk.setepontos.com/index.php?topic=11667.msg124777#msg124777 (https://chdk.setepontos.com/index.php?topic=11667.msg124777#msg124777) for an example of how to upload from multicam. Note since your rig has several different cameras, you need to be careful to only upload to cameras with the same model and canon firmware.
I will first update the faulty cameras and see how they respond. Eventually I will update all, but for the moment... will these work together with the older versions?Generally, having a mix 1.4 and 1.5 shouldn't be a problem. However, 1.5 also fixes some issues with USB stability where some cameras models would fail on transfers of certain sizes, so going to all 1.5 is probably a good idea.
Edit: Quick and silly thing (i haven't really tested without it) but in CHDK/DATA folder I usually have multicam.0 and multicam.cfg, that are never present originally in the builds. These NEED to be there, right?I'm not sure what these are, chdkptp multicam shouldn't(edit) care about them. Files like that would be created if you ran a script called multicam through the CHDK menu.
Hi guys! After a few months on standby I'm retaking the project. I'd like to know if there's been any major updates to chdk and multicam since... March? (wow, it's been a long time!) I hope you're all doing great, thanks!Not in multicam. The one feature I added was the ability to set the camera clocks (also requires updated CHDK)
(last thing i did was update CHDK to 1.5 on most cameras)
Being able to add cameras while keeping the IDs of known ones does make sense.This little feature would make my life way easier, now that I'll be adding a few more cameras to the rig. :) After so long on standby, it feels like I'm starting from scratch again, but it'll only take me a couple of days to be up and running. I'll keep posting new discoveries and issues (hope not too many of the latter). Thx.
This little feature would make my life way easier, now that I'll be adding a few more cameras to the rig. :) After so long on standby, it feels like I'm starting from scratch again, but it'll only take me a couple of days to be up and running. I'll keep posting new discoveries and issues (hope not too many of the latter). Thx.In the current code, you can use
mc:connect{list='mylist.txt'}
mc:connect{add=true}
If that doesn't fit what you are trying to do, describe how you'd like it to work.mc=require('multicam')
mc:cmdwait('post_levent_to_ui"UnpressPowerButton"')
mc:connect({list='cams.txt'})
mc:start()
mc:cmdwait('id')
repeat
print('0)CHECK 1)SYNC 2)ZOOM 3)SHOOT AF 4)MANUAL 5)SHOOT GOOD')
print('6)DOWNLOAD 7)SHUTDOWN 8)REBOOT 9)COMMAND')
local option = cli.readline('mc>')
if option == '0' then --------CHECK
mc:check_connections()
mc:connect({list='cams.txt'})
mc:connect{add=true}
mc:cmdwait('call set_led(1,1)')
mc:start()
mc:cmdwait('id')
mc:cmdwait('rec')
elseif option == '1' then --------START&SYNC
---mc:connect({list='cams.txt'})
---mc:cmdwait('call set_led(1,1)')
---mc:start()
---mc:cmdwait('id')
---mc:cmdwait('rec')
mc:init_sync()
elseif option == '2' then ---------SET ZOOM
local zoom=cli.readline('Zoom>')
mc:cmdwait('call set_zoom('..zoom..')')
elseif option == '3' then ---------SHOOT AF
local fnum=cli.readline('F number>')
local shutter=cli.readline('Shutter speed>')
local ISO=cli.readline('ISO>')
mc:cmdwait('call set_prop(props.WB_MODE,1)')
mc:cmdwait('preshoot')
mc:cmdwait('call click"left" sleep(100) release"shoot_half"')
---mc:shoot({tv=exp.shutter_to_tv96(tonumber(shutter)), svm=exp.iso_to_sv96(tonumber(ISO)),av=exp.f_to_av96(tonumber(fnum)),nd=2})
if cli.readline('shoot (y/n)>') == 'y' then
mc:shoot({sd=dist, tv=exp.shutter_to_tv96(tonumber(shutter)), sv=exp.iso_to_sv96(ISO),av=exp.f_to_av96(fnum),nd=2})
end
elseif option == '4' then ---------SHOOT MANUAL
local dist=cli.readline('Focus Dist>')
local fnum=cli.readline('F number>')
local shutter=cli.readline('Shutter speed>')
local ISO=cli.readline('ISO>')
mc:cmdwait('call set_prop(props.WB_MODE,1)')
mc:cmdwait('preshoot')
mc:cmdwait('call click"left" sleep(100) release"shoot_half"')
mc:shoot({tv=exp.shutter_to_tv96(tonumber(shutter)), svm=exp.iso_to_sv96(tonumber(ISO)),av=exp.f_to_av96(tonumber(fnum)),sd=dist,nd=2})
elseif option == '5' then ---------SHOOT OPTIM
mc:cmdwait('call set_prop(props.WB_MODE,1)')
mc:cmdwait('preshoot')
mc:cmdwait('call click"left" sleep(100) release"shoot_half"')
mc:shoot({tv=exp.shutter_to_tv96(tonumber(0.05)), svm=exp.iso_to_sv96(tonumber(100)),av=exp.f_to_av96(tonumber(4)),nd=2})
elseif option == '6' then ---------DOWNLOAD
local folder=cli.readline('Folder>')
mc:cmdwait('play')
--- mc:download_images({dst='c:/download/'..folder..'/CAM${id}/CAM${id}_${shotseq}${ext}',delete=true,verbose=true})
mc:download_images({dst='c:/download/${ldate,%d%m%y} '..folder..'/${shotseq}_CAM${id}${ext}',delete=true,verbose=true})
elseif option == '7' then ---------SHUTDOWN
mc:cmdwait('play')
---mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
mc:cmd('call sleep(2000) shut_down()')
mc:disconnect()
break
elseif option == '8' then ---------REBOOT
mc:cmdwait('play')
---mc:cmdwait('call local fh=io.open(get_image_dir().."/IMG_1000.JPG","wb") fh:close()')
mc:cmd('call sleep(2000) reboot()')
mc:disconnect()
break
elseif option == '9' then ---------COMMAND
local command=cli.readline('>>>')
cli:print_status(cli:execute('exec '..command))
break
end
until option=='9'
I can get back to the old version which worked, but maybe I'm missing something out. I'm attaching part of the error messages.From the error message, it looks like the version of multicam.lua you are using is different from the chdkptp version. The reference to drive_mode_info was added in r944. The chdkptp binary release including this change is r964, available from https://app.assembla.com/spaces/chdkptp/documents
Thanks so much Reyalp. Yeah, in fact that was the problem, i just updated it. After such a long time without working in the project, is there anything else i should be updating? I see CHDK 1.6 available for most of the cameras (some benefited much from the experimental features)There's not a whole lot of difference between 1.5 and 1.6 for most cameras at this point. The only major feature added is support for floating point math in Lua scripts https://chdk.setepontos.com/index.php?topic=14305.msg145763#msg145763, which probably doesn't matter for you. Bug fixes should mostly be backported to 1.5.
elseif option == '6' then ---------DOWNLOAD
local folder=cli.readline('Folder>')
mc:cmdwait('play')
--- mc:download_images({dst='c:/download/'..folder..'/CAM${id}/CAM${id}_${shotseq}${ext}',delete=true,verbose=true}) mc:download_images({dst='c:/download/${ldate,%d%m%y} '..folder..'/CAM${id}_${shotseq}${ext}',delete=true,verbose=true})
luar function c(k,x) for x=1,x or 1 do click(k or "set") sleep(500) end end c("menu") c("down",4) c() c("up") c() c("right") c() sleep(40000)
:o DON´T INVOKE THIS SPELL IF YOU DON´T WANT NO IMAGE! :oYou could DELETE! :-X with a modification of c("down",>4<) in an adaption of ...This really has nothing to do with ikercito's question. They already have a way to delete files, the problem is integrating with multicam in a way that gracefully handles failures. Please, take the time to understand the context before posting a suggestion. Otherwise, people can spend a lot of time trying to understand your answer, only to find out that it doesn't help them at all.Code: [Select]luar function c(k,x) for x=1,x or 1 do click(k or "set") sleep(500) end end c("menu") c("down",4) c() c("up") c() c("right") c() sleep(40000)
:o DON´T INVOKE THIS SPELL IF YOU DON´T WANT NO IMAGE! :o
https://chdk.setepontos.com/index.php?topic=14302.msg147262#msg147262
files=mc:download_images({...})
mc:delete_files_list(files,{verbose=true})
The advantage of this is if download_images fails, you re-run the delete command.files=mc:imglist({... options ...})
mc:delete_files_list(files,{verbose=true})
mc:imglist takes the same options as download, except obviously the ones that deal with file destination and deleting.My main concern (since I already have a "working" download sequence in the code) would be adding an easy option to erase everything, clear the queue, start fresh, specially when doing test shots. Should I use mc:delete_files_list to point towards DCIM and erase the pics? How?Yes, if you just want to delete all the files, get the list with mc:imglist and delete with mc:delete_files_list. Minimal version
mc:delete_files_list(mc:imglist())
elseif option == '8' then ---------DELETE
mc:cmdwait('play')
if cli.readline('DELETE (y/n)>') == 'y' then
files=mc:imglist({...})
mc:delete_files_list(files,{verbose=true})
end
And here comes two more questions. Would it be possible to generate a cumulative local log file with the output of mc:start (or mc:check_connections?) with the camera model, libusb port, serial, etc... (basically the verbose that mc:start produces). It would be handy to keep track of cameras and debug in some situations. And also, cameras are all set to shoot jpg and dng, but I see that I'm not using DNGs lately and they weight quite a bit, making the downloads quite long. Is there any option to change this from multicam? Maybe make it conditional and only produce DNGs on certain occasions? Or maybe just ignore them in download and delete them afterwards as a possible solution??It's the only Canon G9 i have, it works perfectly on every other stage, ...;) ... I expect the FAQs "Which firmware?" && "What happens with ... "
exec require'camtests'.runbatch{bench=true,shoot=true,filexfer=true,xfersizebugs=true}
And here comes two more questions. Would it be possible to generate a cumulative local log file with the output of mc:start (or mc:check_connections?) with the camera model, libusb port, serial, etc... (basically the verbose that mc:start produces). It would be handy to keep track of cameras and debug in some situations.The output comes from from the printf and warnf lines lines in mc:connect, which write to stdout and stderr respectively by default (set in util.lua). If you want those lines to log a file, *in addition* to printing to stdout or stderr, you could override those functions like
function util.printf(format,...)
if multicam_log then
util.fprintf(multicam_log,format,...)
end
util.fprintf(util.stdout,format,...)
end
function util.warnf(format,...)
if multicam_log then
util.fprintf(multicam_log,"WARNING: "..format,...)
end
util.fprintf(util.stderr,"WARNING: "..format,...)
end
-- in chdkptp, these functions are sometimes accessed through util and sometimes
-- through the global, override both
printf = util.printf
warnf = util.warnf
Then you can add functions to start and stop logging:-- open the log
function start_log()
multicam_log = io.open('multicam.log','a') -- 'a' is a append, use 'w' to overwrite
end
-- close the log and unset log handle
function stop_log()
multicam_log:close()
multicam_log = nil
end
Note the above is all untested, typos and other errors are possible.And also, cameras are all set to shoot jpg and dng, but I see that I'm not using DNGs lately and they weight quite a bit, making the downloads quite long. Is there any option to change this from multicam? Maybe make it conditional and only produce DNGs on certain occasions?Sure, you can change the CHDK raw enable setting using the camera side lua function set_raw. To turn raw off, you'd just use
mc:cmdwait('call set_raw(false)')
Use true to turn it back on.Or maybe just ignore them in download and delete them afterwards as a possible solution??mc:imglist supports a bunch of filtering options, generally equivalent to what is described in the help for the imls command. The options are mostly documented in rlibs.lua, above ff_findfiles and ff_imglist. To match only jpeg files, you could use fmatch='%.JPG$'. To match only DNG, '%.DNG$'
And one final thing, there is one particular camera that always crashes the download. It's the only Canon G9 i have, it works perfectly on every other stage, but despite updating CHDK, changing USB ports and cables (power is the only thing i didn't touch, but it has its own third party adapter and not one of my DIYs), it keeps crashing no matter what I do (read_data failed 0x2ff Error: call failed:I/O error). Any idea to try and save it?Can you get a romlog? https://chdk.fandom.com/wiki/Debugging#Camera_crash_logs_.28romlog.29
Now that I'm trying the camera to have a crash and produce a romlog.... Murphy's law, it's not crashing. ... :)The Romlog of the last (multicam-setup) crash is to save ... :-[
Yeah, but for some reason it was empty, or i couldn't save it on time. That particular camera is on a difficult position to reach, is it possible to produce the romlog from CLI?Probably You need to upload a build with Lua Native Calls enabled first.
Yeah, but for some reason it was empty, or i couldn't save it on time. That particular camera is on a difficult position to reach, is it possible to produce the romlog from CLI?As caefix says, you need native functions calls enabled to get it via the CLI. This can be done by setting in the CHDK (have to physically access the camera, but only once), setting it in the CFG (perhaps by uploading one from a camera that's easier to reach) or uploading a build that has native calls hard coded on.
!require'extras/devutil'.init_cli()
dromlog
Where/in which file can I find the setting to allow Native Calls? I'm gonna have to upload it from some other camera (must be same model?),You should be able to set it on another camera, and then copy CHDK/CCHDK4.CFG from the camera where you set the setting to the G9, and then immediately restart the G9 without touching any CHDK settings. It does not need to be the same model. (Some model specific settings are reset when you load a CFG on a different model, but not native calls)
cause the G9, aside from being impossible to reach, has a faulty screen (which may be the culprit??) and can't activate the setting in the menus.FWIW, you should be able to use chdkptp live view to see the menus even if the physical display is broken. You'd still need to access the physical buttons to navigate the CHDK menu though, so the CFG route is probably easier.
Camera is quite possibly gonna go to waste, but I'd like to give it a last chance and check the romlogAn otherwise functional camera with a broken screen is still useful for development, so if you're planning to throw someone here would probably take it.
Also: For some time I couldn't get STICK to work with new builds and installed them manually. Now I'm seeing some 1.5.1 versions error out when downloading, I could only get to download 1.6 unstable for A2300 - 100e and SX150 100aDo you mean errors downloading from http://mighty-hoernsche.de/ or through stick?
That camera has been functioning perfectly since the first day I started all this, first one I bought! I hope it can go back to the rig.I missed that. Can you give any detail of what of what you were doing when the camera crashed? Also, if possible, what CHDK version was running at the time?
Regarding the downloads, I don't know maybe it was me, but there were a couple of builds that errored out on mighty-hoernsche. I suppose Stick has been deprecated? It was very handy :(You could compare the dates of DISKBOOT.BIN & /../MODULES/.. 8)
if so then where() end
I'll check, but most probably the date is not set correctly (in any of the cameras, since they're most of the time without power). Just wondering... Is there an option to feed the date and time of PC to all the cameras at every startup?Yes,
mc:setclock()
This requires at least CHDK 1.5.1 and chdkptp r941, and should be run after init_sync()I remember we skipped this at the beginning of this thread, for simplicity. I believe it had version 1.4.1 with the first crashes, and I updated to 1.6 to see if it helped. Im on my way to the studio now, but I think camera refused to connect or sync, I don't remember it getting it to the shooting stage.Can you describe what happens when it errors? Does the camera immediately shut down? What is the error on the chdkptp side?
Edit: Confirmed SX150 errors at mc:connect
Ok, just checking dates, i thought I got the correct romlog but seems to be old. Will provide new one.The way the romlog works is when the camera crashes, the firmware saves the crash information to a specific block in the camera onboard flash memory (the "ROM" where the firmware is stored) and then when you get the romlog, that block is read out to a file on the SD card. Both the CHDK romlog menu and the chdkptp dromlog command delete any existing romlog file form SD beforehand, so the only way you should be able to get an old one is if that's what actually stored in flash.
BUT... Most of the times there's some camera that refuses to connect (ptp_opensession error, or failed i/o error...), so I'm beginning to think that it's all related to the USB network being somehow saturated (I have only 32 cameras, is this possible??)The number of cameras should be ok, but the chance of running into electrical issue or flaky hubs goes up.
EDIT: Also, I tried setclock command and gave errors on a few cameras (outdated CHDK surely), can anyone remind me how to update CHDK remotely? My mind is blocked right now :-[You just need to unzip the CHDK zip somewhere, and then use
mup c:/path/to/zip/files A/
That's for a single camera using the regular cli. You can do multiple cameras using multicam like the example on https://chdk.setepontos.com/index.php?topic=11667.msg124777#msg124777 but you need to be sure only cameras of a single model and firmware version are connected.mdl DISKBOOT.BIN PS.FI2 c:/path/to/save/on/pc
to backup your CHDK install.