Skip to content

Commit 6d8da4f

Browse files
committed
Fix error when calling requestJpegThumbnail()
In LrC 14 (WIN) requestJpegThumbnail() fails on every first call for an image.
1 parent 92c769f commit 6d8da4f

File tree

1 file changed

+47
-29
lines changed

1 file changed

+47
-29
lines changed

focuspoints.lrdevplugin/MogrifyUtils.lua

+47-29
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ local mogrifyPath
3131

3232
--[[
3333
-- Call mogrify with 'params'
34-
-- Raises a LrError in case of an execution error
34+
-- Raises a LrError in case of an execution error
3535
--]]
3636
local function mogrifyExecute(params, script)
3737
if mogrifyPath == nil then
@@ -44,15 +44,15 @@ local function mogrifyExecute(params, script)
4444
local cmdline = '\"' .. mogrifyPath .. '\" '
4545
if script then
4646
scriptName = createMagickScript(params)
47-
cmdline = cmdline .. '-script ' .. '\"' .. scriptName .. '\"'
47+
cmdline = cmdline .. '-script ' .. '\"' .. scriptName .. '\"'
4848
else
4949
cmdline = cmdline .. 'mogrify ' .. params
5050
end
51-
logDebug('mogrifyExecute', cmdline )
51+
logDebug('mogrifyExecute', cmdline )
5252
local stat = LrTasks.execute( '\"' .. cmdline .. '\"' )
5353
if stat ~= 0 then
54-
logError('mogrifyDraw', 'Error calling: ' .. cmdline )
55-
LrErrors.throwUserError("Error calling 'mogirfy.exe' Please check plugin configuration")
54+
logError('mogrifyDraw', 'Error calling: ' .. cmdline )
55+
LrErrors.throwUserError("Error calling 'mogrify.exe' Please check plugin configuration")
5656
end
5757
if script then
5858
local prefs = LrPrefs.prefsForPlugin( nil )
@@ -61,39 +61,57 @@ local function mogrifyExecute(params, script)
6161
LrFileUtils.delete(scriptName)
6262
end
6363
end
64-
65-
end
6664

65+
end
6766

6867

6968
--[[
7069
-- Export the catalog photo to disk
7170
-- photo: Lr catalog photo
7271
-- xSize: width in pixel of the create temporary photo
7372
-- ySize: height in pixel of the create temporary photo
74-
--
73+
--
7574
-- requestJpegThumbnail treats the size as minimum value, thus the image on the disk maybe larger
75+
--
76+
-- Note: in LrC 14 (at least on WIN) this function fails on the first call for an image.
77+
-- Analysis and proposal for a fix by John R. Ellis (LR SDK luminary on Adobe forums):
78+
--
79+
-- requestJpegThumbnail() appears to call the callback synchronously if the requested thumbnail
80+
-- is in an internal cache. Otherwise, it returns immediately and calls the callback asynchronously
81+
-- after the thumbnail is generated and loaded into the cache, which could take anywhere from
82+
-- 0.01 seconds to a couple seconds if the photo has to be re-rendered.
83+
-- In order to make sure the thumbnail has been written to file before proceeding with the next
84+
-- steps, exportToDisk() should busy wait until the callback is invoked.
85+
-- photo:getRawMetadata() has to be executed outside the callback, because this method "yields"
86+
-- which is not allowed in a no-yielding context (asynchronous call of callback)
7687
--]]
7788
local function exportToDisk(photo, xSize, ySize)
89+
local done = false
90+
local orgPath = photo:getRawMetadata("path")
7891
local thumb = photo:requestJpegThumbnail(xSize, ySize, function(data, errorMsg)
7992
if data == nil then
8093
logError('exportToDisk', 'No thumbnail data')
8194
LrErrors.throwUserError("Export to disk failed. No thumbnail data received.")
8295
else
83-
local orgPath = photo:getRawMetadata("path")
8496
local leafName = LrPathUtils.leafName( orgPath )
8597
local leafWOExt = LrPathUtils.removeExtension( leafName )
8698
local tempPath = LrPathUtils.getStandardFilePath( "temp" )
8799
fileName = LrPathUtils.child( tempPath, leafWOExt .. "-fpoints.jpg" )
88-
logDebug('exportToDisk', "filename = " .. fileName )
100+
logDebug('exportToDisk', "filename = " .. fileName )
89101

90102
local localFile = io.open(fileName, "w+b")
91103
localFile:write(data)
92104
localFile:close()
93105
end
106+
done = true
94107
end)
108+
if not done then
109+
-- busy wait for (asynchronous) callback to complete
110+
while not done do LrTasks.sleep (0.1) end
111+
end
95112
end
96113

114+
97115
--[[
98116
-- Resize the disk image to the given ize
99117
-- xSize: width in pixel
@@ -118,26 +136,26 @@ local function mapIconToStrokewidthAndColor(name)
118136
end
119137

120138
--[[
121-
-- Build the mogirfy draw parameters base on the focuspointsTable
139+
-- Build the mogrify draw parameters base on the focuspointsTable
122140
--]]
123141
local function buildDrawParams(focuspointsTable)
124-
local para = nil
125-
local sw = nil
126-
local color = nil
127-
142+
local para
143+
local sw
144+
local color
145+
128146
local params = '-fill none '
129147
for i, fpPoint in ipairs(focuspointsTable) do
130148
if fpPoint.template.center ~= nil then
131-
local x = math.floor(tonumber(fpPoint.points.center.x))
149+
local x = math.floor(tonumber(fpPoint.points.center.x))
132150
local y = math.floor(tonumber(fpPoint.points.center.y))
133151
para = '-stroke red -fill red -draw \"circle ' ..x .. ',' .. y .. ' ' .. x+3 .. ',' .. y .. '\" -fill none '
134-
logDebug('buildCmdLine', '[' .. i .. '] ' .. para )
152+
logDebug('buildCmdLine', '[' .. i .. '] ' .. para )
135153
params = params .. para
136154
end
137155
if fpPoint.template.corner ~= nil then
138156
sw, color = mapIconToStrokewidthAndColor(fpPoint.template.corner.fileTemplate)
139157
para = '-strokewidth ' .. sw .. ' -stroke ' .. color .. ' '
140-
local tlx = math.floor(tonumber(fpPoint.points.tl.x))
158+
local tlx = math.floor(tonumber(fpPoint.points.tl.x))
141159
local tly = math.floor(tonumber(fpPoint.points.tl.y))
142160
local brx = math.floor(tonumber(fpPoint.points.br.x))
143161
local bry = math.floor(tonumber(fpPoint.points.br.y))
@@ -146,48 +164,48 @@ local function buildDrawParams(focuspointsTable)
146164
local x = tlx
147165
tlx = brx
148166
brx = x
149-
end
150-
if fpPoint.rotation == 0 or fpPoint.rotation == 360 then
167+
end
168+
if fpPoint.rotation == 0 or fpPoint.rotation == 360 then
151169
para = para .. '-draw \"roundRectangle ' .. tlx .. ',' .. tly .. ' ' .. brx .. ',' .. bry .. ' 1,1\" '
152170
else
153171
local trx = math.floor(tonumber(fpPoint.points.tr.x))
154172
local try = math.floor(tonumber(fpPoint.points.tr.y))
155173
local blx = math.floor(tonumber(fpPoint.points.bl.x))
156174
local bly = math.floor(tonumber(fpPoint.points.bl.y))
157-
para = para .. '-draw \"polyline ' .. trx .. ',' .. try .. ' ' .. tlx .. ',' .. tly .. ' '
175+
para = para .. '-draw \"polyline ' .. trx .. ',' .. try .. ' ' .. tlx .. ',' .. tly .. ' '
158176
.. blx .. ',' .. bly .. ' ' .. brx .. ',' .. bry .. ' ' .. trx .. ',' .. try .. '\" '
159177
end
160-
logDebug('buildCmdLine', '[' .. i .. '] ' .. para .. ' ' .. fpPoint.template.corner.fileTemplate)
178+
logDebug('buildCmdLine', '[' .. i .. '] ' .. para .. ' ' .. fpPoint.template.corner.fileTemplate)
161179
params = params .. para
162180
end
163181
end
164182
return params
165183
end
166184

167185
--[[
168-
-- Create a temprory disk impage for the given Lightroom catalog photo.
186+
-- Create a temprory disk impage for the given Lightroom catalog photo.
169187
-- photo: Lr catalog photo
170188
-- xSize: width in pixel of the create temporary photo
171189
-- ySize: height in pixel of the create temporary photo
172190
--]]
173191
function MogrifyUtils.createDiskImage(photo, xSize, ySize)
174-
logInfo('MogrifyUtils.createDiskImage', photo:getFormattedMetadata( 'fileName' ) .. ' ' .. xSize .. ' ' .. ySize )
192+
logInfo('MogrifyUtils.createDiskImage', photo:getFormattedMetadata( 'fileName' ) .. ' ' .. xSize .. ' ' .. ySize )
175193
exportToDisk(photo, xSize, ySize)
176194
mogrifyResize(xSize, ySize)
177195
return fileName
178196
end
179197

180198

181-
--[[
199+
--[[
182200
-- Draw the focus poins bases on focuspointsTable (see 'DefaultPointRenderer.prepareRendering' for adescription of the table)
183201
--]]
184202
function MogrifyUtils.drawFocusPoints(focuspointsTable)
185-
local params = buildDrawParams(focuspointsTable)
203+
local params = buildDrawParams(focuspointsTable)
186204
mogrifyExecute(params, true)
187205
end
188206

189207

190-
--[[
208+
--[[
191209
-- Creates a temporay script file for Magick. Returns the name of the temp file
192210
--]]
193211
function createMagickScript(params)
@@ -201,8 +219,8 @@ function createMagickScript(params)
201219
end
202220

203221

204-
--[[
205-
-- Deletes the temporary file (created by 'MogrifyUtils.exportToDisk')
222+
--[[
223+
-- Deletes the temporary file (created by 'MogrifyUtils.exportToDisk')
206224
-- Raises a LrError in case that the deletion fails
207225
--]]
208226
function MogrifyUtils.cleanup()

0 commit comments

Comments
 (0)