From 0d8798606654e3f5bde5581c51206731241b4829 Mon Sep 17 00:00:00 2001 From: "Mihail Semenyako (mike.dld)" Date: Sun, 30 Mar 2008 22:31:00 +0000 Subject: [PATCH] libimg: image flipping and rotating (look into .test/test002 for example use) libini: small fix in ini.get_int git-svn-id: svn://kolibrios.org@783 a494cfbc-eb01-0410-851d-a64ba20cac60 --- .../libraries/libs-dev/.test/002/test002.asm | 88 ++++- .../develop/libraries/libs-dev/.test/dll.inc | 5 +- .../libraries/libs-dev/libimg/gif/gif.asm | 2 +- .../libraries/libs-dev/libimg/libimg.asm | 301 ++++++++++++++++-- .../libraries/libs-dev/libimg/libimg.inc | 6 + .../libraries/libs-dev/libini/libini.asm | 2 +- 6 files changed, 364 insertions(+), 40 deletions(-) diff --git a/programs/develop/libraries/libs-dev/.test/002/test002.asm b/programs/develop/libraries/libs-dev/.test/002/test002.asm index f4c2bf0332..85dbf07b57 100644 --- a/programs/develop/libraries/libs-dev/.test/002/test002.asm +++ b/programs/develop/libraries/libs-dev/.test/002/test002.asm @@ -14,6 +14,7 @@ include '../../../../../macros.inc' include '../dll.inc' include '../../libio/libio.inc' +include '../../libimg/libimg.inc' ;----------------------------------------------------------------------------- @@ -49,6 +50,7 @@ START: invoke img.decode, [img_data], [img_data_len] or eax, eax jz exit + mov [image], eax invoke img.to_rgb, eax or eax, eax jz exit @@ -75,16 +77,62 @@ still: button: mcall 17 - cmp ah, 1 + shr eax, 8 + + ; flip horizontally + cmp eax, 'flh' + jne @f + + invoke img.flip, [image], FLIP_HORIZONTAL + jmp redraw_image + + ; flip vertically + @@: cmp eax, 'flv' + jne @f + + invoke img.flip, [image], FLIP_VERTICAL + jmp redraw_image + + ; flip both horizontally and vertically + @@: cmp eax, 'flb' + jne @f + + invoke img.flip, [image], FLIP_BOTH + jmp redraw_image + + ; rotate left + @@: cmp eax, 'rtl' + jne @f + + invoke img.rotate, [image], ROTATE_90_CCW + jmp redraw_image + + ; rotate right + @@: cmp eax, 'rtr' + jne @f + + invoke img.rotate, [image], ROTATE_90_CW + jmp redraw_image + + @@: cmp eax, 1 jne still exit: mcall -1 + redraw_image: + stdcall mem.Free, [rgb_img] + invoke img.to_rgb, [image] + or eax, eax + jz exit + mov [rgb_img], eax + jmp red + draw_window: invoke gfx.open, TRUE mov [ctx], eax +@^ mov edi, [rgb_img] mov ebx, 200 * 65536 mov bx, [edi + 0] @@ -93,13 +141,27 @@ draw_window: mov cx, [edi + 4] add cx, 5 + 21 mcall 0, , , 0x33FF0000, , s_header +^@ + mcall 0, <100, 640>, <100, 480>, 0x33FFFFFF, , s_header + + invoke gfx.pen.color, [ctx], 0x007F7F7F + invoke gfx.line, [ctx], 0, 30, 630, 30 + + mcall 8, <5 + 25 * 0, 20>, <5, 20>, 'flh', 0x007F7F7F + mcall 8, <5 + 25 * 1, 20>, <5, 20>, 'flv', 0x007F7F7F + mcall 8, <5 + 25 * 2, 20>, <5, 20>, 'flb', 0x007F7F7F + + invoke gfx.line, [ctx], 5 + 25 * 3, 0, 5 + 25 * 3, 30 + + mcall 8, <10 + 25 * 3, 20>, <5, 20>, 'rtl', 0x007F7F7F + mcall 8, <10 + 25 * 4, 20>, <5, 20>, 'rtr', 0x007F7F7F mov ebx, [rgb_img] mov ecx, [ebx + 0] shl ecx, 16 mov cx, [ebx + 4] add ebx, 4 * 2 - mcall 7, , , <0, 0> + mcall 7, , , <5, 35> invoke gfx.close, [ctx] ret @@ -168,19 +230,26 @@ library \ libimg , 'libimg.obj' import libio , \ + libio.init , 'lib_init' , \ file.size , 'file.size' , \ file.open , 'file.open' , \ file.read , 'file.read' , \ file.close , 'file.close' -import libgfx , \ - gfx.open , 'gfx.open' , \ - gfx.close , 'gfx.close' +import libgfx , \ + libgfx.init , 'lib_init' , \ + gfx.open , 'gfx.open' , \ + gfx.close , 'gfx.close' , \ + gfx.pen.color , 'gfx.pen.color' , \ + gfx.line , 'gfx.line' -import libimg , \ - img.is_img , 'img.is_img' , \ - img.to_rgb , 'img.to_rgb' , \ - img.decode , 'img.decode' +import libimg , \ + libimg.init , 'lib_init' , \ + img.is_img , 'img.is_img' , \ + img.to_rgb , 'img.to_rgb' , \ + img.decode , 'img.decode' , \ + img.flip , 'img.flip' , \ + img.rotate , 'img.rotate' ;----------------------------------------------------------------------------- @@ -190,6 +259,7 @@ img_data dd ? img_data_len dd ? fh dd ? rgb_img dd ? +image dd ? ctx dd ? diff --git a/programs/develop/libraries/libs-dev/.test/dll.inc b/programs/develop/libraries/libs-dev/.test/dll.inc index dbd5ff366c..e1cb98d178 100644 --- a/programs/develop/libraries/libs-dev/.test/dll.inc +++ b/programs/develop/libraries/libs-dev/.test/dll.inc @@ -58,7 +58,10 @@ endp proc dll.GetProcAddress, exp:dword,sz_name:dword mov edx,[exp] - .next: test edx,edx + xor eax,eax + .next: or edx,edx + jz .end + cmp dword[edx],0 jz .end stdcall strcmp,[edx],[sz_name] test eax,eax diff --git a/programs/develop/libraries/libs-dev/libimg/gif/gif.asm b/programs/develop/libraries/libs-dev/libimg/gif/gif.asm index 7e6661da73..41c231b987 100644 --- a/programs/develop/libraries/libs-dev/libimg/gif/gif.asm +++ b/programs/develop/libraries/libs-dev/libimg/gif/gif.asm @@ -145,7 +145,7 @@ endl jne .error movzx eax, [ebx + gif.ImageDescriptor.Width] movzx ecx, [ebx + gif.ImageDescriptor.Height] - stdcall img._resize_data, [img], eax, ecx + stdcall img._.resize_data, [img], eax, ecx or eax, eax jz .error diff --git a/programs/develop/libraries/libs-dev/libimg/libimg.asm b/programs/develop/libraries/libs-dev/libimg/libimg.asm index 9cef637227..324dc1e3fb 100644 --- a/programs/develop/libraries/libs-dev/libimg/libimg.asm +++ b/programs/develop/libraries/libs-dev/libimg/libimg.asm @@ -235,7 +235,7 @@ proc img.create _width, _height ;/////////////////////////////////////////////// push eax - stdcall img._resize_data, eax, [_width], [_height] + stdcall img._.resize_data, eax, [_width], [_height] or eax, eax jz .error.2 @@ -267,34 +267,47 @@ proc img.destroy _img ;///////////////////////////////////////////////////////// endp ;;================================================================================================;; -proc img._resize_data _img, _width, _height ;/////////////////////////////////////////////////////;; +proc img.count _img ;/////////////////////////////////////////////////////////////////////////////;; ;;------------------------------------------------------------------------------------------------;; -;? --- TBD --- ;; +;? Get number of images in the list (e.g. in animated GIF file) ;; ;;------------------------------------------------------------------------------------------------;; -;> --- TBD --- ;; +;> _img = pointer to image ;; ;;------------------------------------------------------------------------------------------------;; -;< --- TBD --- ;; +;< eax = -1 (fail) / >0 (ok) ;; ;;================================================================================================;; - push ebx - mov ebx, [_img] - mov eax, [_height] - imul eax, [_width] - shl eax, 2 - invoke mem.realloc, [ebx + Image.Data], eax + push ecx edx + mov edx, [_img] + stdcall img._.validate, edx or eax, eax - jz .error + jnz .error - mov [ebx + Image.Data], eax - push [_width] - pop [ebx + Image.Width] - push [_height] - pop [ebx + Image.Height] + @@: mov eax, [edx + Image.Previous] + or eax, eax + jz @f + mov edx, eax + jmp @b + + @@: xor ecx, ecx + @@: inc ecx + mov eax, [edx + Image.Next] + or eax, eax + jz .exit + mov edx, eax + jmp @b + + .exit: + mov eax, ecx + pop edx ecx + ret .error: - pop ebx + or eax, -1 + pop edx ecx ret endp +;;//// image processing //////////////////////////////////////////////////////////////////////////;; + ;;================================================================================================;; proc img.lock_bits _img, _start_line, _end_line ;/////////////////////////////////////////////////;; ;;------------------------------------------------------------------------------------------------;; @@ -321,16 +334,15 @@ proc img.unlock_bits _img, _lock ;////////////////////////////////////////////// ret endp -;;//// image processing //////////////////////////////////////////////////////////////////////////;; - ;;================================================================================================;; proc img.flip _img, _flip_kind ;//////////////////////////////////////////////////////////////////;; ;;------------------------------------------------------------------------------------------------;; -;? --- TBD --- ;; +;? Flip image ;; ;;------------------------------------------------------------------------------------------------;; -;> --- TBD --- ;; +;> _img = pointer to image ;; +;> _flip_kind = one of FLIP_* constants ;; ;;------------------------------------------------------------------------------------------------;; -;< eax = false / true ;; +;< eax = false / true ;; ;;================================================================================================;; locals scanline_len dd ? @@ -347,6 +359,8 @@ endl shl eax, 2 mov [scanline_len], eax + push esi + test [_flip_kind], FLIP_VERTICAL jz .dont_flip_vert @@ -360,27 +374,51 @@ endl push ecx mov ecx, [scanline_len] + shr ecx, 2 @@: lodsd xchg eax, [edi] mov [esi - 4], eax add edi, 4 - add ecx, -4 + dec ecx jnz @b + pop ecx mov eax, [scanline_len] shl eax, 1 sub edi, eax - - pop ecx dec ecx jnz .next_line_vert .dont_flip_vert: + pop esi + test [_flip_kind], FLIP_HORIZONTAL jz .exit - ;TODO: horz flip code + mov ecx, [esi + Image.Height] + mov esi, [esi + Image.Data] + lea edi, [esi - 4] + add edi, [scanline_len] + + .next_line_horz: + push ecx esi edi + + mov ecx, [scanline_len] + shr ecx, 3 + @@: mov eax, [esi] + xchg eax, [edi] + mov [esi], eax + add esi, 4 + add edi, -4 + dec ecx + jnz @b + + pop edi esi ecx + add esi, [scanline_len] + add edi, [scanline_len] + dec ecx + jnz .next_line_horz .exit: xor eax, eax @@ -394,6 +432,181 @@ endl ret endp +;;================================================================================================;; +proc img.rotate _img, _rotate_kind ;//////////////////////////////////////////////////////////////;; +;;------------------------------------------------------------------------------------------------;; +;? Rotate image ;; +;;------------------------------------------------------------------------------------------------;; +;> _img = pointer to image ;; +;> _rotate_kind = one of ROTATE_* constants ;; +;;------------------------------------------------------------------------------------------------;; +;< eax = false / true ;; +;;================================================================================================;; +locals + scanline_len_old dd ? + scanline_len_new dd ? + scanline_pixels_new dd ? + line_buffer dd ? + pixels_ptr dd ? +endl + + mov [line_buffer], 0 + + push ebx esi edi + stdcall img._.validate, [_img] + or eax, eax + jnz .error + + cmp [_rotate_kind], ROTATE_90_CCW + je .rotate_ccw_low + cmp [_rotate_kind], ROTATE_90_CW + je .rotate_cw_low + cmp [_rotate_kind], ROTATE_180 + je .flip + jmp .exit + + .rotate_ccw_low: + mov ebx, [_img] + mov eax, [ebx + Image.Height] + mov [scanline_pixels_new], eax + shl eax, 2 + mov [scanline_len_new], eax + + invoke mem.alloc, eax + or eax, eax + jz .error + mov [line_buffer], eax + + mov ecx, [ebx + Image.Width] + lea eax, [ecx * 4] + mov [scanline_len_old], eax + + mov eax, [scanline_len_new] + imul eax, ecx + add eax, [ebx + Image.Data] + mov [pixels_ptr], eax + + .next_column_ccw_low: + dec ecx + jz .exchange_dims + push ecx + + mov edx, [scanline_len_old] + add [scanline_len_old], -4 + + mov ecx, [scanline_pixels_new] + mov esi, [ebx + Image.Data] + mov edi, [line_buffer] + @@: mov eax, [esi] + stosd + add esi, edx + dec ecx + jnz @b + + mov eax, [scanline_pixels_new] + mov edi, [ebx + Image.Data] + lea esi, [edi + 4] + mov edx, [scanline_len_old] + shr edx, 2 + @@: mov ecx, edx + rep movsd + add esi, 4 + dec eax + jnz @b + + mov eax, [scanline_len_new] + sub [pixels_ptr], eax + mov ecx, [scanline_pixels_new] + mov esi, [line_buffer] + mov edi, [pixels_ptr] + rep movsd + + pop ecx + jmp .next_column_ccw_low + + .rotate_cw_low: + mov ebx, [_img] + mov eax, [ebx + Image.Height] + mov [scanline_pixels_new], eax + shl eax, 2 + mov [scanline_len_new], eax + + invoke mem.alloc, eax + or eax, eax + jz .error + mov [line_buffer], eax + + mov ecx, [ebx + Image.Width] + lea eax, [ecx * 4] + mov [scanline_len_old], eax + + mov eax, [scanline_len_new] + imul eax, ecx + add eax, [ebx + Image.Data] + mov [pixels_ptr], eax + + .next_column_cw_low: + dec ecx + js .exchange_dims + push ecx + + mov edx, [scanline_len_old] + add [scanline_len_old], -4 + + mov ecx, [scanline_pixels_new] + mov esi, [pixels_ptr] + add esi, -4 + mov edi, [line_buffer] + @@: mov eax, [esi] + stosd + sub esi, edx + dec ecx + jnz @b + + mov eax, [scanline_pixels_new] + dec eax + mov edi, [ebx + Image.Data] + add edi, [scanline_len_old] + lea esi, [edi + 4] + mov edx, [scanline_len_old] + shr edx, 2 + @@: mov ecx, edx + rep movsd + add esi, 4 + dec eax + jnz @b + + mov eax, [scanline_len_new] + sub [pixels_ptr], eax + mov ecx, [scanline_pixels_new] + mov esi, [line_buffer] + mov edi, [pixels_ptr] + rep movsd + + pop ecx + jmp .next_column_cw_low + + .flip: + jmp .exit + + .exchange_dims: + push [ebx + Image.Width] [ebx + Image.Height] + pop [ebx + Image.Width] [ebx + Image.Height] + + .exit: + invoke mem.free, [line_buffer] + xor eax, eax + inc eax + pop edi esi ebx + ret + + .error: + invoke mem.free, [line_buffer] + xor eax, eax + pop edi esi ebx + ret +endp + ;;================================================================================================;; ;;////////////////////////////////////////////////////////////////////////////////////////////////;; @@ -452,6 +665,35 @@ proc img._.delete _img ;//////////////////////////////////////////////////////// ret endp +;;================================================================================================;; +proc img._.resize_data _img, _width, _height ;////////////////////////////////////////////////////;; +;;------------------------------------------------------------------------------------------------;; +;? --- TBD --- ;; +;;------------------------------------------------------------------------------------------------;; +;> --- TBD --- ;; +;;------------------------------------------------------------------------------------------------;; +;< --- TBD --- ;; +;;================================================================================================;; + push ebx + mov ebx, [_img] + mov eax, [_height] + imul eax, [_width] + shl eax, 2 + invoke mem.realloc, [ebx + Image.Data], eax + or eax, eax + jz .error + + mov [ebx + Image.Data], eax + push [_width] + pop [ebx + Image.Width] + push [_height] + pop [ebx + Image.Height] + + .error: + pop ebx + ret +endp + ;;================================================================================================;; ;;////////////////////////////////////////////////////////////////////////////////////////////////;; @@ -497,5 +739,8 @@ export \ img.encode , 'img.encode' , \ img.create , 'img.create' , \ img.destroy , 'img.destroy' , \ + img.count , 'img.count' , \ img.lock_bits , 'img.lock_bits' , \ - img.unlock_bits , 'img.unlock_bits' + img.unlock_bits , 'img.unlock_bits' , \ + img.flip , 'img.flip' , \ + img.rotate , 'img.rotate' diff --git a/programs/develop/libraries/libs-dev/libimg/libimg.inc b/programs/develop/libraries/libs-dev/libimg/libimg.inc index 1222fe8354..aac8ab138b 100644 --- a/programs/develop/libraries/libs-dev/libimg/libimg.inc +++ b/programs/develop/libraries/libs-dev/libimg/libimg.inc @@ -37,3 +37,9 @@ ends FLIP_VERTICAL = 0x01 FLIP_HORIZONTAL = 0x02 FLIP_BOTH = FLIP_VERTICAL or FLIP_HORIZONTAL + +ROTATE_90_CW = 0x01 +ROTATE_180 = 0x02 +ROTATE_270_CW = 0x03 +ROTATE_90_CCW = ROTATE_270_CW +ROTATE_270_CCW = ROTATE_90_CW diff --git a/programs/develop/libraries/libs-dev/libini/libini.asm b/programs/develop/libraries/libs-dev/libini/libini.asm index c3d1ab9c3e..01fc91e4f6 100644 --- a/programs/develop/libraries/libs-dev/libini/libini.asm +++ b/programs/develop/libraries/libs-dev/libini/libini.asm @@ -1020,7 +1020,7 @@ endl or eax, eax jnz .exit_error - stdcall ini._.skip_nonblanks, [f] + stdcall ini._.skip_nonblanks, [f_addr] xor eax, eax xor ebx, ebx xor edx, edx