Skip to main content
Participating Frequently
March 6, 2025
Question

Binding to collection of GUI elements (Lightroom)

  • March 6, 2025
  • 1 reply
  • 141 views

I'm writing a plugin for Lightromm and I'm displaying list of selectable items with checkboxes. List is created basing on http data.

 

Now - question is how to bind to those checkboxes automatically?

 

I came up with such solution:

 

 

-- function called on storing property - currently unused:
local function saveSelection( propertyTable, key, val )

end

-- data
local collection = {}     -- data model
local selections          -- bindings

-- function which automatically binds to collection:
local function initSelectionBinding( context )
   selections = LrBinding.makePropertyTable(context)
   for idx, val in pairs(collection) do
      local propidx = tostring(idx)
      selections:addObserver( propidx, saveSelection )    -- not used
      selections["< contents >"][propidx] = false         -- hack to init checkboxes
   end
end

 

 

and GUI:

 

local rowView = {}

for idx, val in pairs(collection) do
   table.insert (rowView, 
      f:group_box {
         width = 450,
         f:row { 
            f:checkbox { value = LrView.bind{ bind_to_object = selections, key = tostring(idx) }, },
            f:static_text { title = val["state"], },
	 },
end

f:scrolled_view {
   width = 950,
   height = 500,
   f:column (rowView),
},

 

 

now, the trick is that binding is done by asigning key names as numbers converted to string.

 

And the same indexes must be used for data model and gui elements.

To make it easier I assigned a metatable to data model:

CollectionIndexes = function (tbl, tag)
    local i = tonumber(tag)
    if i then
        return tbl[i]
    end
    return nil
end

setmetatable(Collection, { __index = CollectionIndexes })

 

There is also second trick - how to access key, which is basically prop.1, prop.2, etc?
I came up with this hack to access property table elements - by looking at ["< contents >"] table:

 

selections["< contents >"][propidx] = false

 

 

Can it be done in nicer way?

1 reply

johnrellis
Legend
March 9, 2025

[This post contains formatting and embedded images that don't appear in email. View the post in your Web browser.]

 

"Can it be done in nicer way?"

 

That general method is the only way. But you can make it a lot more concise:

local prop = LrBinding.makePropertyTable (context)

for i, val in pairs (collection) do 
   prop ["box" .. i] = false
   table.insert (rowView, f:group_box {width = 450, 
      f:row {
         f:checkbox {value = LrView.bind {"box" .. i}},
         f:static_text {title = val.state}}})
   end 

f:scrolled_view {bind_to_object = prop, 
   width = 950, height = 500, f:column (rowView)}

 

Later code can refer to the checkbox values using prop ["box" .. i].

zuber1979Author
Participating Frequently
March 9, 2025

Thanks, that's what I wanted to know 🙂