@a1ex
If I want to trigger advanced bracketing in a script, I need to simulate a shutter press. The question is, what is the best way.
Do I need to do a full sequence, ie press(half), press(full), press(unpressfull), press(unpresshalf)?
Or some other sequence.
How do I pause the script to wait for advanced bracketing to finish, eg before I refocus etc.
Hope you can educate me.
Cheers
Garry
Theory:
camera.shoot()
camera.wait()
Practice: to be tested...
@a1ex
I tried that earlier but it didn't seem to go well.
I've now decided on a compromise. Script will only be allowed to run in M or Av mode.
The user can elect to rune the script with the normal focus stacking and assuming three Canon-set brackets at each focus stop.
Thus I have:
if stop_count == 3 then -- assume 3 brackets requested
local count = dryos.shooting_card.file_number
key.press(KEY.HALFSHUTTER)
key.press(KEY.FULLSHUTTER)
repeat sleep(0.1) until dryos.shooting_card.file_number - count == stop_count
key.press(KEY.UNPRESS_FULLSHUTTER)
key.press(KEY.UNPRESS_HALFSHUTTER)
else
camera.shoot()
end
If the user doesn't have the brackets set on the Canon side, the worst that can happen is you will get three exposures the same.
I've just tested the shoot/wait sequence on 5D2 and it worked...
BTW, your full-shutter press sequence is reinventing camera.burst(3), and has an edge case when image number wraps around at 9999.
@a1ex
QuoteI've just tested the shoot/wait sequence on 5D2 and it worked...
I just tried it on a 5D3 and it didn't ::)
I'm in M mode and have a two brackets set via Canon.
I'm using this:
function my_shoot()
camera.shoot()
camera.wait()
end
All I get is a single image.
Quote from: garry23 on April 19, 2019, 10:28:40 AM
If I want to trigger advanced bracketing in a script [...]
Quote from: garry23 on April 19, 2019, 03:31:37 PM
I'm in M mode and have a two brackets set via Canon.
These are not the same.
The shoot/wait sequence will cover the first case; that's what I've tested.
The burst() function should work with the second case, but I didn't test it.
@a1ex
:-[
But it still doesn'y work on my (sic) 5D3. That is M mode, ML bracketing on, Canon off and this code:
--[[
Script to capture 'perfect' focus brackets from the current focus position to a defocus (CoC) blur defined infinity.
Needs to run in LV and M Mode.
If the current position is greater than the ML hyperfocal/3, then three brackets will be taken at H/3, H and 3*H, giving a depth of focus of H/4 to infinity, using the ML CoC. Thus, if using the script, you don't need to worry
about focusing too much, as you will get three focus brackets to look at in post.
Reduce the ML CoC to achieve greater bracket to bracket focus overlap, ie focus insurance, but, sensibly, don't go below, say, 15/Crop.
Reducing the ML CoC below the 'normally recognised' CoC, eg 30/Crop , will result in more brackets, but higher focus quality through the scene.
The closer you are to the macro end, the more brackets will be taken, obviously.
Note an estimate (sic) of the number of brackets is shown in the top ML bar (RHS). B=0 means can't run script. B=n means estimate of number of brackets that will be taken. B=666 means too
much diffraction, so back off the aperture.
Script assumes you will not change lens without switching the camera off ;-)
The algorithm used is OK for non-macro use, ie landscape focus bracketing; and works best with WA lenses. So be warned and shoot wide!
The script allows the user to select a trigger key (that is hijacked if the script can run). Change this as required.
Two (different exposure) bookend images are taken at the beginning and end of bracketing, to help differentiate the bracket set in post.
The script is placed the ML Focus menu.
Finally, the script has one menu item, so it can be switched on and off, eg if you wish to access the trigger key in its normal mode.
Release 0.57
April 2019
Garry George
--]]
require("config")
direction = 1
trigger_key = KEY.RATE -- works for me on a 5D3 :-)
get_brackets = false
good_2_go = false
switched_off = false
bookends = true
options = {"ON+Bookends","ON","ONx2+Book","ONx3+Book","OFF"}
calibrated = false
function property.AF_MODE:handler(value)
if not lens.af then good_2_go = false else good_2_go = true end
end
function test_OK()
if lens.name == "" then return false end
if not lens.af then return false end
return true
end
function my_shoot()
camera.shoot()
camera.wait()
end
function calibrate()
local normal = false
local current_x = lens.focus_distance
lens.focus(1,2,true) -- test lens chirality
sleep(0.5)
if lens.focus_distance > current_x then normal = true end
lens.focus(-1,2,true)
if not normal then direction = -direction end
end
function bookend()
if camera.mode == MODE.M then
local s = camera.shutter.apex
camera.shutter.apex = 9
camera.shoot()
camera.shutter.apex = s
else
local t = camera.kelvin
camera.kelvin = 0
camera.shoot()
camera.kelvin = t
end
end
function set_focus(x)
repeat sleep(0.1) until lv.running
local current_x = lens.focus_distance
if x == current_x then return x end
local lens_ok = true
if x > current_x then
while lens.focus_distance < x and lens_ok do lens_ok = lens.focus(direction,2,true) end
while lens.focus_distance > x and lens_ok do lens_ok = lens.focus(-direction,1,true) end
else
while lens.focus_distance > x and lens_ok do lens_ok = lens.focus(-direction,2,true) end
while lens.focus_distance < x and lens_ok do lens_ok = lens.focus(direction,1,true) end
end
return lens.focus_distance -- final focus distance, ie may not be extactly x ;-)
end
function look_4_bracketing(pressed)
if switched_off then
get_brackets = false
return true
end
if pressed == trigger_key then
if not good_2_go then
get_brackets = false
return true -- as can't use script
else
get_brackets = true
return false -- steal trigger key
end
else
return true
end
end
function capture_brackets()
if switched_off or not lv.running then
get_brackets = false
good_2_go = false
return true
end
if not (camera.mode == MODE.M) then
get_brackets = false
good_2_go = false
return true
end
if not calibrated and lv.running then
calibrate()
calibrated = true
end
if not test_OK() then
good_2_go = false
return true
else
good_2_go = true
end
if not get_brackets or not good_2_go then return true end
get_brackets = false
if bookends then bookend() end
local x = lens.focus_distance
local start_x = x
while x < lens.hyperfocal/3 do
x = set_focus(x)
my_shoot()
x = (x*(lens.hyperfocal - 2*lens.focal_length))/(lens.hyperfocal - 2*x) -- estimate of next bracket position
end
set_focus(lens.hyperfocal/3)
my_shoot()
set_focus(lens.hyperfocal)
my_shoot()
set_focus(3*lens.hyperfocal)
my_shoot()
if bookends then bookend() end
set_focus(start_x)
return true
end
get_brackets_menu = menu.new
{
parent = "Focus",
name = "Get Focus Brackets",
help = "Press your trigger key to start",
help2 = "Switch Bookends on/off here",
depends_on = DEPENDS_ON.LIVEVIEW,
choices = options,
update = function(this,delta)
if this.value == "ON+Bookends" then
switched_off = false
bookends = true
elseif this.value == "ON" then
switched_off = false
bookends = false
elseif this.value == "ONx2+Book" then
switched_off = false
bookends = true
elseif this.value == "ONx3+Book" then
switched_off = false
bookends = true
elseif this.value == "OFF" then
switched_off = true
bookends = false
end
end
}
lv.info
{
name = "GFB",
value = "",
priority = 100,
update = function(this)
this.value = ""
if not switched_off then
local num = 0
if lens.hyperfocal < 65000 then
num = 1 + math.ceil((1 + lens.hyperfocal/lens.focus_distance)/2)
else
num = 666
end
if num < 3 then num = 3 end
if not good_2_go then num = 0 end
this.value = "#B="..num
end
end
}
event.keypress = look_4_bracketing
event.shoot_task = capture_brackets
config.create_from_menu(get_brackets_menu) -- keep a track of the script's menu state at camera close
I get a single image out of the my_shoot function.
Further testing.
What seems to be happening is camera.wait() doesn't wait.
Thus the script moves on to the next op, ie refocus and take another bracket set, which once again fails.
What does appear to work is the last bookend image, which takes the required bookend and another image (I had two brackets set in ML).
It's giving me a headache :-( :-)
Got it - the issue appears because ML bracketing happens in shoot_task. That means, as long as your shoot_task hook is running, ML cannot trigger its advanced bracketing sequence.
I've tested with a "simple" script (without custom menu); that one runs in a new task.
@a1ex
Great: I was beginning to think you would never talk to me again, as I was stupid ;)
Simple question: is there a fix I can do, or will I need to wait for a Lua Fix uplift?
As usual, thanks for your support and guidance.
Cheers
Garry
Well, is there any reason to run this script as a "complex" one, with custom menu?
I mean, you could use a "simple" script, for example:
-- Bracketing test
menu.close()
sleep(2)
camera.shoot()
camera.wait()
display.notify_box("Finished.")
User would trigger the bracketing sequence from the "Run script" menu - no need to assign a shortcut key for it. The scripting backend will create a DryOS task for this script, with no extra effort on your part.
You would still have to define the options for bookends, but... is this something you would change often?
Yes, this suggestion is because of the multitasking limitations of our Lua integration with DryOS (read: it's a hack). It's not trivial to fix this, I've asked for help (https://www.magiclantern.fm/forum/index.php?topic=14828.msg179227#msg179227) a very long time ago, but...
So, your best bet is to keep things simple (within a single task).
@a1ex
Thanks for the sound advice: I'll try going simple ;)
...@a1ex
Damn! I was really happy with the simple version of my script: but when testing to the extreme I get the attached error.
It seems to only happen if the Advanced Bracketing goes to Bulb mode.
BTW here is the latest draft of the script:
--[[
Get Brackets
This is a Lua 'simple script' to capture 'perfect' focus brackets from the current focus position to a defocus blur defined infinity, related to the ML CoC.
There is no menu and no feedback.
Needs to run in LV, AF mode and M Mode.
If the current position is greater than the ML hyperfocal/3, then three brackets will be taken at H/3, H and 3*H, giving a depth of focus of H/4 to infinity, using the ML CoC.
Thus, if using the script, you don't need to worry about focusing too much, as you will get three focus brackets to look at in post.
Set the ML CoC to achieve the required bracket to bracket defocus blur overlap, ie focus insurance, but, sensibly, don't go below, say, 15/Crop.
Reducing the ML CoC below the 'normally recognised' CoC, eg 30/Crop , will result in more brackets, but higher focus quality through the scene.
The script will pause to ask if you are content with the number of focus brackets (note exposure brackets are on top of this number).
The closer you are to the macro end, the more brackets will be taken, obviously.
The set the exposure brackets simply turn on ML's Advanced Bracketing.
The algorithm used is OK for non-macro use, ie landscape focus bracketing; and works best with WA lenses. So be warned and shoot wide!
Two (different exposure) bookend images are taken, one at the beginning and one at end of bracketing, to help differentiate the bracket set in post.
The script is run from the ML Scripts menu.
***WARNING*** Some lenses may not work with this script: sorry.
Please let me know if you have any issues or feedback.
Release 0.7
April 2019
Garry George
photography.grayheron.net
--]]
direction = 1
bookends = true
good_2_go = true
function my_shoot()
camera.shoot()
camera.wait()
end
function my_display(text,time,x_pos,y_pos)
text = string.rep("\n",y_pos)..string.rep(" ",x_pos)..text
display.notify_box(text,time*1000)
end
function calibrate()
repeat sleep(0.1) until lv.running
local normal = false
local current_x = lens.focus_distance
lens.focus(1,2,true) -- test lens chirality
sleep(0.5)
if lens.focus_distance > current_x then normal = true end
lens.focus(-1,2,true)
if not normal then direction = -direction end
end
function bookend()
local test = menu.get("Shoot","Advanced Bracket",0)
if test == 1 then menu.set("Shoot","Advanced Bracket",0) end
local t = camera.shutter.apex
camera.shutter.apex = 10
my_shoot()
camera.shutter.apex = t
if test == 1 then menu.set("Shoot","Advanced Bracket",1) end
end
function set_focus(x)
repeat sleep(0.1) until lv.running
sleep(1)
local current_x = lens.focus_distance
if x == current_x then return x end
local lens_ok = true
if x > current_x then
while lens.focus_distance < x and lens_ok do lens_ok = lens.focus(direction,2,true) end
while lens.focus_distance > x and lens_ok do lens_ok = lens.focus(-direction,1,true) end
else
while lens.focus_distance > x and lens_ok do lens_ok = lens.focus(-direction,2,true) end
while lens.focus_distance < x and lens_ok do lens_ok = lens.focus(direction,1,true) end
end
current_x = lens.focus_distance
return lens.focus_distance -- final focus distance, ie may not be extactly x ;-)
end
function capture_brackets()
if menu.get("Get Brackets","Autorun",0) == 1 then
menu.set("Get Brackets","Autorun",0)
return
end
menu.close()
if not lv.running then lv.start() end
repeat sleep(0.1) until lv.running
if not (camera.mode == MODE.M) then my_display("Must be in M Mode",2,0,5) return end
if lens.name == "" then my_display("Lens no good",2,0,5) return end
if not lens.af then
my_display("Switch AF on",2,0,5)
repeat sleep(1) until lens.af
end
local num = 1 + math.ceil((1 + lens.hyperfocal/lens.focus_distance)/2)
if num < 3 then num = 3 end
my_display(tostring(num).." brackets: Press half shutter if OK?",5,0,5)
if key.wait() ~= KEY.HALFSHUTTER then return end
calibrate()
if bookends then bookend() end
local x = lens.focus_distance
local start_x = x
while x < lens.hyperfocal/3 do
x = set_focus(x)
my_shoot()
x = (x*(lens.hyperfocal - 2*lens.focal_length))/(lens.hyperfocal - 2*x) -- estimate of next bracket position
end
set_focus(lens.hyperfocal/3)
my_shoot()
set_focus(lens.hyperfocal)
my_shoot()
set_focus(3*lens.hyperfocal)
my_shoot()
if bookends then bookend() end
set_focus(start_x)
end
capture_brackets()
(https://i.ibb.co/SXj65Km/image1.jpg) (https://ibb.co/SXj65Km)
***UPDATE***
More testing and confirmed error only occurs if Advanced Bracketing uses BULB mode :'(
Understood, will prepare a fix.
@a1ex
Many thanks, I won't publish the script until I confirm all is ok.
Cheers
Garry
...BTW
As long as I manage Advanced Bracketing settings, I can use the script OK.
For example I just took the test image below with my Sigma 12-24 at 12mm, f/5.6, a base exposure of 0.5s, and with a ZN strategy in Advanced Bracketing, ie +4Ev from an ML ETTR shutter.
I moved focus to focus min and ran the script, which said I would take four images, ie from min focus (some 200mm) out to 3*hyperfocal.
Plus, the script works well beside my DoF Bar. Fun to watch the DoF Bar change in front of you ;)
(https://i.ibb.co/bPTjKfh/Test-image-5-D3.jpg) (https://ibb.co/bPTjKfh)