summaryrefslogtreecommitdiff
path: root/apps/plugins/lua/include_lua/image.lua
diff options
context:
space:
mode:
Diffstat (limited to 'apps/plugins/lua/include_lua/image.lua')
-rw-r--r--apps/plugins/lua/include_lua/image.lua184
1 files changed, 0 insertions, 184 deletions
diff --git a/apps/plugins/lua/include_lua/image.lua b/apps/plugins/lua/include_lua/image.lua
index 2b2a1ce19f..5fd452ea78 100644
--- a/apps/plugins/lua/include_lua/image.lua
+++ b/apps/plugins/lua/include_lua/image.lua
@@ -23,7 +23,6 @@
23 23
24--[[ Exposed Functions 24--[[ Exposed Functions
25 25
26 _img.save
27 _img.search 26 _img.search
28 _img.rotate 27 _img.rotate
29 _img.resize 28 _img.resize
@@ -156,189 +155,6 @@ local _img = {} do
156 return r_img 155 return r_img
157 end 156 end
158 157
159 -- saves img to file: name
160 _img.save = function(img, name)
161 -- bmp saving derived from rockbox - screendump.c
162 -- bitdepth is limited by the device
163 -- eg. device displays greyscale, rgb images are saved greyscale
164 local file
165 local bbuffer = {} -- concat buffer for s_bytes
166 local fbuffer = {} -- concat buffer for file writes, reused
167
168 local function s_bytesLE(bits, value)
169 -- bits must be multiples of 8 (sizeof byte)
170 local byte
171 local nbytes = bit.rshift(bits, 3)
172 for b = 1, nbytes do
173 if value > 0 then
174 byte = value % 256
175 value = (value - byte) / 256
176 else
177 byte = 0
178 end
179 bbuffer[b] = string.char(byte)
180 end
181 return table.concat(bbuffer, _NIL, 1, nbytes)
182 end
183
184 local function s_bytesBE(bits, value)
185 -- bits must be multiples of 8 (sizeof byte)
186 local byte
187 local nbytes = bit.rshift(bits, 3)
188 for b = nbytes, 1, -1 do
189 if value > 0 then
190 byte = value % 256
191 value = (value - byte) / 256
192 else
193 byte = 0
194 end
195 bbuffer[b] = string.char(byte)
196 end
197 return table.concat(bbuffer, _NIL, 1, nbytes)
198 end
199
200 local cmp = {["r"] = function(c) return bit.band(bit.rshift(c, 16), 0xFF) end,
201 ["g"] = function(c) return bit.band(bit.rshift(c, 08), 0xFF) end,
202 ["b"] = function(c) return bit.band(c, 0xFF) end}
203
204 local function bmp_color(color)
205 return s_bytesLE(8, cmp.b(color))..
206 s_bytesLE(8, cmp.g(color))..
207 s_bytesLE(8, cmp.r(color))..
208 s_bytesLE(8, 0) .. ""
209 end -- c_cmp(color, c.r))
210
211 local function bmp_color_mix(c1, c2, num, den)
212 -- mixes c1 and c2 as ratio of numerator / denominator
213 -- used 2x each save results
214 local bc1, gc1, rc1 = cmp.b(c1), cmp.g(c1), cmp.r(c1)
215
216 return s_bytesLE(8, cmp.b(c2) - bc1 * num / den + bc1)..
217 s_bytesLE(8, cmp.g(c2) - gc1 * num / den + gc1)..
218 s_bytesLE(8, cmp.r(c2) - rc1 * num / den + rc1)..
219 s_bytesLE(8, 0) .. ""
220 end
221
222 local w, h = img:width(), img:height()
223 local depth = tonumber(img:__tostring(6)) -- RLI_INFO_DEPTH = 0x6
224 local format = tonumber(img:__tostring(7)) -- RLI_INFO_FORMAT = 0x7
225
226 local bpp, bypl -- bits per pixel, bytes per line
227 -- bypl, pad rows to a multiple of 4 bytes
228 if depth <= 4 then
229 bpp = 8 -- 256 color image
230 bypl = (w + 3)
231 elseif depth <= 16 then
232 bpp = 16
233 bypl = (w * 2 + 3)
234 elseif depth <= 24 then
235 bpp = 24
236 bypl = (w * 3 + 3)
237 else
238 bpp = 32
239 bypl = (w * 4 + 3)
240 end
241
242 local linebytes = bit.band(bypl, bit.bnot(3))
243
244 local bytesperpixel = bit.rshift(bpp, 3)
245 local headersz = 54
246 local imgszpad = h * linebytes
247
248 local compression, n_colors = 0, 0
249 local h_ppm, v_ppm = 0x00000EC4, 0x00000EC4 --Pixels Per Meter ~ 96 dpi
250
251 if depth == 16 then
252 compression = 3 -- BITFIELDS
253 n_colors = 3
254 elseif depth <= 8 then
255 n_colors = bit.lshift(1, depth)
256 end
257
258 headersz = headersz + (4 * n_colors)
259
260 file = io.open('/' .. name, "w+") -- overwrite, rb ignores the 'b' flag
261
262 if not file then
263 rb.splash(rb.HZ, "Error opening /" .. name)
264 return
265 end
266 -- create a bitmap header 'rope' with image details -- concatenated at end
267 local bmpheader = fbuffer
268
269 bmpheader[01] = "BM"
270 bmpheader[02] = s_bytesLE(32, headersz + imgszpad)
271 bmpheader[03] = "\0\0\0\0" -- WORD reserved 1 & 2
272 bmpheader[04] = s_bytesLE(32, headersz) -- BITMAPCOREHEADER size
273 bmpheader[05] = s_bytesLE(32, 40) -- BITMAPINFOHEADER size
274
275 bmpheader[06] = s_bytesLE(32, w)
276 bmpheader[07] = s_bytesLE(32, h)
277 bmpheader[08] = "\1\0" -- WORD color planes ALWAYS 1
278 bmpheader[09] = s_bytesLE(16, bpp) -- bits/pixel
279 bmpheader[10] = s_bytesLE(32, compression)
280 bmpheader[11] = s_bytesLE(32, imgszpad)
281 bmpheader[12] = s_bytesLE(32, h_ppm) -- biXPelsPerMeter
282 bmpheader[13] = s_bytesLE(32, v_ppm) -- biYPelsPerMeter
283 bmpheader[14] = s_bytesLE(32, n_colors)
284 bmpheader[15] = s_bytesLE(32, n_colors)
285
286 -- Color Table (#n_colors entries)
287 if depth == 1 then -- assuming positive display
288 bmpheader[#bmpheader + 1] = bmp_color(0xFFFFFF)
289 bmpheader[#bmpheader + 1] = bmp_color(0x0)
290 elseif depth == 2 then
291 bmpheader[#bmpheader + 1] = bmp_color(0xFFFFFF)
292 bmpheader[#bmpheader + 1] = bmp_color_mix(0xFFFFFF, 0, 1, 3)
293 bmpheader[#bmpheader + 1] = bmp_color_mix(0xFFFFFF, 0, 2, 3)
294 bmpheader[#bmpheader + 1] = bmp_color(0x0)
295 elseif depth == 16 then
296 if format == 555 then
297 -- red bitfield mask
298 bmpheader[#bmpheader + 1] = s_bytesLE(32, 0x00007C00)
299 -- green bitfield mask
300 bmpheader[#bmpheader + 1] = s_bytesLE(32, 0x000003E0)
301 -- blue bitfield mask
302 bmpheader[#bmpheader + 1] = s_bytesLE(32, 0x0000001F)
303 else --565
304 -- red bitfield mask
305 bmpheader[#bmpheader + 1] = s_bytesLE(32, 0x0000F800)
306 -- green bitfield mask
307 bmpheader[#bmpheader + 1] = s_bytesLE(32, 0x000007E0)
308 -- blue bitfield mask
309 bmpheader[#bmpheader + 1] = s_bytesLE(32, 0x0000001F)
310 end
311 end
312
313 file:write(table.concat(fbuffer))-- write the header to the file now
314 for i=1, #fbuffer do fbuffer[i] = _NIL end -- reuse table
315
316 local imgdata = fbuffer
317 -- pad rows to a multiple of 4 bytes
318 local bytesleft = linebytes - (bytesperpixel * w)
319 local t_data = {}
320 local fs_bytes_E = s_bytesLE -- default save in Little Endian
321
322 if format == 3553 then -- RGB565SWAPPED
323 fs_bytes_E = s_bytesBE -- Saves in Big Endian
324 end
325
326 -- Bitmap lines start at bottom unless biHeight is negative
327 for point in _points(img, 1, h, w + bytesleft, 1) do
328 imgdata[#imgdata + 1] = fs_bytes_E(bpp, point or 0)
329
330 if #fbuffer >= 31 then -- buffered write, increase # for performance
331 file:write(table.concat(fbuffer))
332 for i=1, #fbuffer do fbuffer[i] = _NIL end -- reuse table
333 end
334
335 end
336 file:write(table.concat(fbuffer)) --write leftovers to file
337 fbuffer = _NIL
338
339 file:close()
340 end -- save(img, name)
341
342 --searches an image for target color 158 --searches an image for target color
343 _img.search = function(img, x1, y1, x2, y2, targetclr, variation, stepx, stepy) 159 _img.search = function(img, x1, y1, x2, y2, targetclr, variation, stepx, stepy)
344 160