Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-cw
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-cw
Commits
288b8ee1
Commit
288b8ee1
authored
Oct 08, 2002
by
Michael Günnewig
Committed by
Alexandre Julliard
Oct 08, 2002
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Implemented the MS RLE video codec.
parent
d25e0399
Hide whitespace changes
Inline
Side-by-side
Showing
14 changed files
with
2070 additions
and
13 deletions
+2070
-13
configure
configure
+2
-2
configure.ac
configure.ac
+1
-1
Makefile.in
dlls/Makefile.in
+7
-7
msrle32.c
dlls/msrle32/msrle32.c
+0
-1
msrle32.spec
dlls/msrle32/msrle32.spec
+0
-1
.cvsignore
dlls/msvideo/msrle32/.cvsignore
+1
-0
Makefile.in
dlls/msvideo/msrle32/Makefile.in
+4
-1
msrle32.c
dlls/msvideo/msrle32/msrle32.c
+1877
-0
msrle32.spec
dlls/msvideo/msrle32/msrle32.spec
+3
-0
msrle_De.rc
dlls/msvideo/msrle32/msrle_De.rc
+28
-0
msrle_En.rc
dlls/msvideo/msrle32/msrle_En.rc
+28
-0
msrle_Fr.rc
dlls/msvideo/msrle32/msrle_Fr.rc
+28
-0
msrle_private.h
dlls/msvideo/msrle32/msrle_private.h
+56
-0
rsrc.rc
dlls/msvideo/msrle32/rsrc.rc
+35
-0
No files found.
configure
View file @
288b8ee1
...
...
@@ -14207,7 +14207,7 @@ MAKE_TEST_RULES=dlls/Maketest.rules
MAKE_PROG_RULES
=
programs/Makeprog.rules
ac_config_files
=
"
$ac_config_files
Make.rules dlls/Makedll.rules dlls/Maketest.rules programs/Makeprog.rules Makefile dlls/Makefile dlls/advapi32/Makefile dlls/advapi32/tests/Makefile dlls/avicap32/Makefile dlls/avifil32/Makefile dlls/comcat/Makefile dlls/comctl32/Makefile dlls/commdlg/Makefile dlls/crtdll/Makefile dlls/crypt32/Makefile dlls/d3d8/Makefile dlls/dciman32/Makefile dlls/ddraw/Makefile dlls/devenum/Makefile dlls/dinput/Makefile dlls/dinput8/Makefile dlls/dplay/Makefile dlls/dplayx/Makefile dlls/dsound/Makefile dlls/gdi/Makefile dlls/gdi/tests/Makefile dlls/glu32/Makefile dlls/icmp/Makefile dlls/imagehlp/Makefile dlls/imm32/Makefile dlls/kernel/Makefile dlls/kernel/tests/Makefile dlls/lzexpand/Makefile dlls/mapi32/Makefile dlls/mpr/Makefile dlls/msacm/Makefile dlls/msacm/imaadp32/Makefile dlls/msacm/msadp32/Makefile dlls/msacm/msg711/Makefile dlls/msacm/winemp3/Makefile dlls/msdmo/Makefile dlls/msimg32/Makefile dlls/msisys/Makefile dlls/msnet32/Makefile dlls/ms
rle32/Makefile dlls/msvcrt/Makefile dlls/msvcrt20/Makefile dlls/msvideo
/Makefile dlls/netapi32/Makefile dlls/netapi32/tests/Makefile dlls/ntdll/Makefile dlls/ntdll/tests/Makefile dlls/odbc32/Makefile dlls/ole32/Makefile dlls/oleaut32/Makefile dlls/oleaut32/tests/Makefile dlls/olecli/Makefile dlls/oledlg/Makefile dlls/olepro32/Makefile dlls/olesvr/Makefile dlls/opengl32/Makefile dlls/psapi/Makefile dlls/qcap/Makefile dlls/quartz/Makefile dlls/rasapi32/Makefile dlls/richedit/Makefile dlls/rpcrt4/Makefile dlls/rpcrt4/tests/Makefile dlls/serialui/Makefile dlls/setupapi/Makefile dlls/shdocvw/Makefile dlls/shell32/Makefile dlls/shell32/tests/Makefile dlls/shfolder/Makefile dlls/shlwapi/Makefile dlls/shlwapi/tests/Makefile dlls/snmpapi/Makefile dlls/sti/Makefile dlls/tapi32/Makefile dlls/ttydrv/Makefile dlls/twain/Makefile dlls/url/Makefile dlls/urlmon/Makefile dlls/user/Makefile dlls/user/tests/Makefile dlls/version/Makefile dlls/win32s/Makefile dlls/winaspi/Makefile dlls/winedos/Makefile dlls/wineps/Makefile dlls/wininet/Makefile dlls/wininet/tests/Makefile dlls/winmm/Makefile dlls/winmm/joystick/Makefile dlls/winmm/mcianim/Makefile dlls/winmm/mciavi/Makefile dlls/winmm/mcicda/Makefile dlls/winmm/mciseq/Makefile dlls/winmm/mciwave/Makefile dlls/winmm/midimap/Makefile dlls/winmm/wavemap/Makefile dlls/winmm/winealsa/Makefile dlls/winmm/winearts/Makefile dlls/winmm/wineaudioio/Makefile dlls/winmm/winenas/Makefile dlls/winmm/wineoss/Makefile dlls/winnls/Makefile dlls/winsock/Makefile dlls/winsock/tests/Makefile dlls/winspool/Makefile dlls/wintrust/Makefile dlls/wow32/Makefile dlls/wsock32/Makefile dlls/x11drv/Makefile documentation/Makefile include/Makefile library/Makefile miscemu/Makefile ole/Makefile programs/Makefile programs/avitools/Makefile programs/clock/Makefile programs/cmdlgtst/Makefile programs/control/Makefile programs/expand/Makefile programs/notepad/Makefile programs/osversioncheck/Makefile programs/progman/Makefile programs/regapi/Makefile programs/regedit/Makefile programs/regsvr32/Makefile programs/regtest/Makefile programs/uninstaller/Makefile programs/view/Makefile programs/wcmd/Makefile programs/wineconsole/Makefile programs/winedbg/Makefile programs/winefile/Makefile programs/winemine/Makefile programs/winepath/Makefile programs/winetest/Makefile programs/winhelp/Makefile programs/winver/Makefile server/Makefile tools/Makefile tools/widl/Makefile tools/winapi/Makefile tools/winebuild/Makefile tools/winedump/Makefile tools/wmc/Makefile tools/wpp/Makefile tools/wrc/Makefile unicode/Makefile"
ac_config_files
=
"
$ac_config_files
Make.rules dlls/Makedll.rules dlls/Maketest.rules programs/Makeprog.rules Makefile dlls/Makefile dlls/advapi32/Makefile dlls/advapi32/tests/Makefile dlls/avicap32/Makefile dlls/avifil32/Makefile dlls/comcat/Makefile dlls/comctl32/Makefile dlls/commdlg/Makefile dlls/crtdll/Makefile dlls/crypt32/Makefile dlls/d3d8/Makefile dlls/dciman32/Makefile dlls/ddraw/Makefile dlls/devenum/Makefile dlls/dinput/Makefile dlls/dinput8/Makefile dlls/dplay/Makefile dlls/dplayx/Makefile dlls/dsound/Makefile dlls/gdi/Makefile dlls/gdi/tests/Makefile dlls/glu32/Makefile dlls/icmp/Makefile dlls/imagehlp/Makefile dlls/imm32/Makefile dlls/kernel/Makefile dlls/kernel/tests/Makefile dlls/lzexpand/Makefile dlls/mapi32/Makefile dlls/mpr/Makefile dlls/msacm/Makefile dlls/msacm/imaadp32/Makefile dlls/msacm/msadp32/Makefile dlls/msacm/msg711/Makefile dlls/msacm/winemp3/Makefile dlls/msdmo/Makefile dlls/msimg32/Makefile dlls/msisys/Makefile dlls/msnet32/Makefile dlls/ms
vcrt/Makefile dlls/msvcrt20/Makefile dlls/msvideo/Makefile dlls/msvideo/msrle32
/Makefile dlls/netapi32/Makefile dlls/netapi32/tests/Makefile dlls/ntdll/Makefile dlls/ntdll/tests/Makefile dlls/odbc32/Makefile dlls/ole32/Makefile dlls/oleaut32/Makefile dlls/oleaut32/tests/Makefile dlls/olecli/Makefile dlls/oledlg/Makefile dlls/olepro32/Makefile dlls/olesvr/Makefile dlls/opengl32/Makefile dlls/psapi/Makefile dlls/qcap/Makefile dlls/quartz/Makefile dlls/rasapi32/Makefile dlls/richedit/Makefile dlls/rpcrt4/Makefile dlls/rpcrt4/tests/Makefile dlls/serialui/Makefile dlls/setupapi/Makefile dlls/shdocvw/Makefile dlls/shell32/Makefile dlls/shell32/tests/Makefile dlls/shfolder/Makefile dlls/shlwapi/Makefile dlls/shlwapi/tests/Makefile dlls/snmpapi/Makefile dlls/sti/Makefile dlls/tapi32/Makefile dlls/ttydrv/Makefile dlls/twain/Makefile dlls/url/Makefile dlls/urlmon/Makefile dlls/user/Makefile dlls/user/tests/Makefile dlls/version/Makefile dlls/win32s/Makefile dlls/winaspi/Makefile dlls/winedos/Makefile dlls/wineps/Makefile dlls/wininet/Makefile dlls/wininet/tests/Makefile dlls/winmm/Makefile dlls/winmm/joystick/Makefile dlls/winmm/mcianim/Makefile dlls/winmm/mciavi/Makefile dlls/winmm/mcicda/Makefile dlls/winmm/mciseq/Makefile dlls/winmm/mciwave/Makefile dlls/winmm/midimap/Makefile dlls/winmm/wavemap/Makefile dlls/winmm/winealsa/Makefile dlls/winmm/winearts/Makefile dlls/winmm/wineaudioio/Makefile dlls/winmm/winenas/Makefile dlls/winmm/wineoss/Makefile dlls/winnls/Makefile dlls/winsock/Makefile dlls/winsock/tests/Makefile dlls/winspool/Makefile dlls/wintrust/Makefile dlls/wow32/Makefile dlls/wsock32/Makefile dlls/x11drv/Makefile documentation/Makefile include/Makefile library/Makefile miscemu/Makefile ole/Makefile programs/Makefile programs/avitools/Makefile programs/clock/Makefile programs/cmdlgtst/Makefile programs/control/Makefile programs/expand/Makefile programs/notepad/Makefile programs/osversioncheck/Makefile programs/progman/Makefile programs/regapi/Makefile programs/regedit/Makefile programs/regsvr32/Makefile programs/regtest/Makefile programs/uninstaller/Makefile programs/view/Makefile programs/wcmd/Makefile programs/wineconsole/Makefile programs/winedbg/Makefile programs/winefile/Makefile programs/winemine/Makefile programs/winepath/Makefile programs/winetest/Makefile programs/winhelp/Makefile programs/winver/Makefile server/Makefile tools/Makefile tools/widl/Makefile tools/winapi/Makefile tools/winebuild/Makefile tools/winedump/Makefile tools/wmc/Makefile tools/wpp/Makefile tools/wrc/Makefile unicode/Makefile"
cat
>
confcache
<<
\
_ACEOF
...
...
@@ -14728,10 +14728,10 @@ do
"dlls/msimg32/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msimg32/Makefile" ;;
"dlls/msisys/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msisys/Makefile" ;;
"dlls/msnet32/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msnet32/Makefile" ;;
"dlls/msrle32/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msrle32/Makefile" ;;
"dlls/msvcrt/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msvcrt/Makefile" ;;
"dlls/msvcrt20/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msvcrt20/Makefile" ;;
"dlls/msvideo/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msvideo/Makefile" ;;
"dlls/msvideo/msrle32/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/msvideo/msrle32/Makefile" ;;
"dlls/netapi32/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/netapi32/Makefile" ;;
"dlls/netapi32/tests/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/netapi32/tests/Makefile" ;;
"dlls/ntdll/Makefile" ) CONFIG_FILES="
$CONFIG_FILES
dlls/ntdll/Makefile" ;;
...
...
configure.ac
View file @
288b8ee1
...
...
@@ -1412,10 +1412,10 @@ dlls/msdmo/Makefile
dlls/msimg32/Makefile
dlls/msisys/Makefile
dlls/msnet32/Makefile
dlls/msrle32/Makefile
dlls/msvcrt/Makefile
dlls/msvcrt20/Makefile
dlls/msvideo/Makefile
dlls/msvideo/msrle32/Makefile
dlls/netapi32/Makefile
dlls/netapi32/tests/Makefile
dlls/ntdll/Makefile
...
...
dlls/Makefile.in
View file @
288b8ee1
...
...
@@ -47,10 +47,10 @@ BASEDIRS = \
msimg32
\
msisys
\
msnet32
\
msrle32
\
msvcrt
\
msvcrt20
\
msvideo
\
msvideo/msrle32
\
netapi32
\
ntdll
\
odbc32
\
...
...
@@ -396,8 +396,8 @@ msisys.ocx$(DLLEXT): msisys/msisys.ocx$(DLLEXT)
msnet32.dll$(DLLEXT)
:
msnet32/msnet32.dll$(DLLEXT)
$(RM)
$@
&&
$(LN_S)
msnet32/msnet32.dll
$(DLLEXT)
$@
msrle32.dll$(DLLEXT)
:
msrle32/msrle32.dll$(DLLEXT)
$(RM)
$@
&&
$(LN_S)
msrle32/msrle32.dll
$(DLLEXT)
$@
msrle32.dll$(DLLEXT)
:
ms
video/ms
rle32/msrle32.dll$(DLLEXT)
$(RM)
$@
&&
$(LN_S)
ms
video/ms
rle32/msrle32.dll
$(DLLEXT)
$@
msvcrt.dll$(DLLEXT)
:
msvcrt/msvcrt.dll$(DLLEXT)
$(RM)
$@
&&
$(LN_S)
msvcrt/msvcrt.dll
$(DLLEXT)
$@
...
...
@@ -605,7 +605,7 @@ msacm/msg711/msg711.acm$(DLLEXT): msacm/msg711
msimg32/msimg32.dll$(DLLEXT)
:
msimg32
msisys/msisys.ocx$(DLLEXT)
:
msisys
msnet32/msnet32.dll$(DLLEXT)
:
msnet32
ms
rle32/msrle32.dll$(DLLEXT)
:
msrle32
ms
video/msrle32/msrle32.dll$(DLLEXT)
:
msvideo/
msrle32
msvcrt/msvcrt.dll$(DLLEXT)
:
msvcrt
msvcrt20/msvcrt20.dll$(DLLEXT)
:
msvcrt20
msvideo/msvfw32.dll$(DLLEXT)
:
msvideo
...
...
@@ -704,7 +704,7 @@ msacm/msg711/__install__: msg711.acm$(DLLEXT)
msimg32/__install__
:
msimg32.dll$(DLLEXT)
msisys/__install__
:
msisys.ocx$(DLLEXT)
msnet32/__install__
:
msnet32.dll$(DLLEXT)
msrle32/__install__
:
msrle32.dll$(DLLEXT)
ms
video/ms
rle32/__install__
:
msrle32.dll$(DLLEXT)
msvcrt/__install__
:
msvcrt.dll$(DLLEXT)
msvcrt20/__install__
:
msvcrt20.dll$(DLLEXT)
msvideo/__install__
:
msvfw32.dll$(DLLEXT)
...
...
@@ -762,7 +762,7 @@ x11drv/__install__: x11drv.dll$(DLLEXT)
# Inter-dll dependencies
advapi32
:
kernel32.dll$(DLLEXT) ntdll.dll$(DLLEXT)
avicap32
:
kernel32
.dll$(DLLEXT)
avicap32
:
ntdll
.dll$(DLLEXT)
avifil32
:
msvfw32.dll$(DLLEXT) kernel32.dll$(DLLEXT)
comcat
:
ole32.dll$(DLLEXT) user32.dll$(DLLEXT) advapi32.dll$(DLLEXT) kernel32.dll$(DLLEXT)
comctl32
:
user32.dll$(DLLEXT) gdi32.dll$(DLLEXT) advapi32.dll$(DLLEXT) kernel32.dll$(DLLEXT)
\
...
...
@@ -799,9 +799,9 @@ msdmo: kernel32.dll$(DLLEXT)
msimg32
:
kernel32.dll$(DLLEXT)
msisys
:
kernel32.dll$(DLLEXT)
msnet32
:
kernel32.dll$(DLLEXT)
msrle32
:
kernel32.dll$(DLLEXT)
msvcrt20
:
msvcrt.dll$(DLLEXT)
msvcrt
:
kernel32.dll$(DLLEXT) ntdll.dll$(DLLEXT)
msvideo/msrle32
:
winmm.dll$(DLLEXT) user32.dll$(DLLEXT) kernel32.dll$(DLLEXT)
msvideo
:
winmm.dll$(DLLEXT) comctl32.dll$(DLLEXT) version.dll$(DLLEXT) user32.dll$(DLLEXT)
\
gdi32.dll$(DLLEXT) kernel32.dll$(DLLEXT)
netapi32
:
advapi32.dll$(DLLEXT) kernel32.dll$(DLLEXT)
...
...
dlls/msrle32/msrle32.c
deleted
100644 → 0
View file @
d25e0399
/* all codes are removed by author */
dlls/msrle32/msrle32.spec
deleted
100644 → 0
View file @
d25e0399
@ stub DriverProc #(long long long long long)
dlls/msrle32/.cvsignore
→
dlls/ms
video/ms
rle32/.cvsignore
View file @
288b8ee1
Makefile
msrle32.dll.dbg.c
msrle32.spec.c
rsrc.res
dlls/msrle32/Makefile.in
→
dlls/ms
video/ms
rle32/Makefile.in
View file @
288b8ee1
TOPSRCDIR
=
@top_srcdir@
TOPOBJDIR
=
../..
TOPOBJDIR
=
../..
/..
SRCDIR
=
@srcdir@
VPATH
=
@srcdir@
MODULE
=
msrle32.dll
IMPORTS
=
winmm user32 kernel32
LDDLLFLAGS
=
@LDDLLFLAGS@
SYMBOLFILE
=
$(MODULE)
.tmp.o
C_SRCS
=
msrle32.c
RC_SRCS
=
rsrc.rc
@MAKE_DLL_RULES@
### Dependencies:
dlls/msvideo/msrle32/msrle32.c
0 → 100644
View file @
288b8ee1
/*
* Copyright 2002 Michael Gnnewig
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
/* TODO:
* - compression of RLE4 is buggy -- see FIXME's
* - many improvements possible
* - implement DecompressSetPalette? -- does we need it for anything?
*/
#include <assert.h>
#include "msrle_private.h"
#include "winnls.h"
#include "winuser.h"
#include "windowsx.h"
#include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL
(
msrle32
);
static
HINSTANCE
MSRLE32_hModule
=
0
;
#define ABS(a) ((a) < 0 ? -(a) : (a))
#define SQR(a) ((a) * (a))
#define QUALITY_to_DIST(q) (ICQUALITY_HIGH - q)
inline
WORD
ColorCmp
(
WORD
clr1
,
WORD
clr2
)
{
register
UINT
a
=
(
clr1
-
clr2
);
return
SQR
(
a
);
}
inline
WORD
Intensity
(
RGBQUAD
clr
)
{
return
(
30
*
clr
.
rgbRed
+
59
*
clr
.
rgbGreen
+
11
*
clr
.
rgbBlue
)
/
4
;
}
#define GetRawPixel(lpbi,lp,x) \
((lpbi)->biBitCount == 1 ? ((lp)[(x)/8] >> (8 - (x)%8)) & 1 : \
((lpbi)->biBitCount == 4 ? ((lp)[(x)/2] >> (4 * (1 - (x)%2))) & 15 : lp[x]))
/*****************************************************************************/
/* utility functions */
static
BOOL
isSupportedDIB
(
LPCBITMAPINFOHEADER
lpbi
);
static
BOOL
isSupportedMRLE
(
LPCBITMAPINFOHEADER
lpbi
);
static
void
LoadWideString
(
UINT
id
,
LPWSTR
str
,
INT
len
);
static
BYTE
MSRLE32_GetNearestPaletteIndex
(
UINT
count
,
const
RGBQUAD
*
clrs
,
RGBQUAD
clr
);
/* compression functions */
static
void
computeInternalFrame
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBYTE
lpIn
);
static
LONG
MSRLE32_GetMaxCompressedSize
(
LPCBITMAPINFOHEADER
lpbi
);
static
LRESULT
MSRLE32_CompressRLE4
(
CodecInfo
*
pi
,
LPBITMAPINFOHEADER
lpbiIn
,
LPBYTE
lpIn
,
LPBITMAPINFOHEADER
lpbiOut
,
LPBYTE
lpOut
,
BOOL
isKey
);
static
LRESULT
MSRLE32_CompressRLE8
(
CodecInfo
*
pi
,
LPBITMAPINFOHEADER
lpbiIn
,
LPBYTE
lpIn
,
LPBITMAPINFOHEADER
lpbiOut
,
LPBYTE
lpOut
,
BOOL
isKey
);
/* decompression functions */
static
LRESULT
MSRLE32_DecompressRLE4
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbi
,
LPBYTE
lpIn
,
LPBYTE
lpOut
);
static
LRESULT
MSRLE32_DecompressRLE8
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbi
,
LPBYTE
lpIn
,
LPBYTE
lpOut
);
/* API functions */
static
LRESULT
CompressGetFormat
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBITMAPINFOHEADER
lpbiOut
);
static
LRESULT
CompressGetSize
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
);
static
LRESULT
CompressQuery
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
);
static
LRESULT
CompressBegin
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
);
static
LRESULT
Compress
(
CodecInfo
*
pi
,
ICCOMPRESS
*
lpic
,
DWORD
dwSize
);
static
LRESULT
CompressEnd
(
CodecInfo
*
pi
);
static
LRESULT
DecompressGetFormat
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBITMAPINFOHEADER
lpbiOut
);
static
LRESULT
DecompressQuery
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
);
static
LRESULT
DecompressBegin
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
);
static
LRESULT
Decompress
(
CodecInfo
*
pi
,
ICDECOMPRESS
*
pic
,
DWORD
dwSize
);
static
LRESULT
DecompressEnd
(
CodecInfo
*
pi
);
static
LRESULT
DecompressGetPalette
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBITMAPINFOHEADER
lpbiOut
);
/*****************************************************************************/
static
void
LoadWideString
(
UINT
id
,
LPWSTR
str
,
INT
len
)
{
char
szTemp
[
80
];
LoadStringA
(
MSRLE32_hModule
,
id
,
szTemp
,
sizeof
(
szTemp
));
MultiByteToWideChar
(
CP_ACP
,
0
,
szTemp
,
-
1
,
str
,
len
);
}
static
BOOL
isSupportedMRLE
(
LPCBITMAPINFOHEADER
lpbi
)
{
/* pre-conditions */
assert
(
lpbi
!=
NULL
);
if
(
lpbi
->
biSize
<
sizeof
(
BITMAPINFOHEADER
)
||
\
lpbi
->
biPlanes
!=
1
)
return
FALSE
;
if
(
lpbi
->
biCompression
==
BI_RLE4
)
{
if
(
lpbi
->
biBitCount
!=
4
||
\
(
lpbi
->
biWidth
%
2
)
!=
0
)
return
FALSE
;
}
else
if
(
lpbi
->
biCompression
==
BI_RLE8
)
{
if
(
lpbi
->
biBitCount
!=
8
)
return
FALSE
;
}
else
return
FALSE
;
return
TRUE
;
}
static
BOOL
isSupportedDIB
(
LPCBITMAPINFOHEADER
lpbi
)
{
/* pre-conditions */
assert
(
lpbi
!=
NULL
);
/* check structure version/planes/compression */
if
(
lpbi
->
biSize
<
sizeof
(
BITMAPINFOHEADER
)
||
lpbi
->
biPlanes
!=
1
)
return
FALSE
;
if
(
lpbi
->
biCompression
!=
BI_RGB
&&
lpbi
->
biCompression
!=
BI_BITFIELDS
)
return
FALSE
;
/* check bit-depth */
if
(
lpbi
->
biBitCount
!=
1
&&
lpbi
->
biBitCount
!=
4
&&
lpbi
->
biBitCount
!=
8
&&
lpbi
->
biBitCount
!=
15
&&
lpbi
->
biBitCount
!=
16
&&
lpbi
->
biBitCount
!=
24
&&
lpbi
->
biBitCount
!=
32
)
return
FALSE
;
/* check for size(s) */
if
(
!
lpbi
->
biWidth
||
!
lpbi
->
biHeight
)
return
FALSE
;
/* image with zero size, makes no sense so error ! */
if
(
DIBWIDTHBYTES
(
*
lpbi
)
*
lpbi
->
biHeight
>=
(
1UL
<<
31
)
-
1
)
return
FALSE
;
/* image too big ! */
/* check for non existing colortable for hi- and true-color DIB's */
if
(
lpbi
->
biBitCount
>=
15
&&
lpbi
->
biClrUsed
>
0
)
return
FALSE
;
return
TRUE
;
}
static
BYTE
MSRLE32_GetNearestPaletteIndex
(
UINT
count
,
const
RGBQUAD
*
clrs
,
RGBQUAD
clr
)
{
INT
diff
=
0x00FFFFFF
;
UINT
i
;
UINT
index
=
0
;
/* pre-conditions */
assert
(
clrs
!=
NULL
);
for
(
i
=
0
;
i
<
count
;
i
++
)
{
int
r
=
((
int
)
clrs
[
i
].
rgbRed
-
(
int
)
clr
.
rgbRed
);
int
g
=
((
int
)
clrs
[
i
].
rgbGreen
-
(
int
)
clr
.
rgbGreen
);
int
b
=
((
int
)
clrs
[
i
].
rgbBlue
-
(
int
)
clr
.
rgbBlue
);
r
=
r
*
r
+
g
*
g
+
b
*
b
;
if
(
r
<
diff
)
{
index
=
i
;
diff
=
r
;
if
(
diff
==
0
)
break
;
}
}
return
index
;
}
/*****************************************************************************/
void
computeInternalFrame
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBYTE
lpIn
)
{
WORD
wIntensityTbl
[
256
];
LONG
lInLine
,
lOutLine
;
LPWORD
lpOut
;
int
i
,
y
;
/* pre-conditions */
assert
(
pi
!=
NULL
&&
lpbiIn
!=
NULL
&&
lpIn
!=
NULL
);
assert
(
pi
->
pCurFrame
!=
NULL
);
lInLine
=
DIBWIDTHBYTES
(
*
lpbiIn
);
lOutLine
=
WIDTHBYTES
(
lpbiIn
->
biWidth
*
8
*
sizeof
(
WORD
))
/
2
;
lpOut
=
pi
->
pCurFrame
;
assert
(
lpbiIn
->
biClrUsed
!=
0
);
{
const
RGBQUAD
*
lp
=
(
LPRGBQUAD
)((
LPBYTE
)
lpbiIn
+
lpbiIn
->
biSize
);
for
(
i
=
0
;
i
<
lpbiIn
->
biClrUsed
;
i
++
)
wIntensityTbl
[
i
]
=
Intensity
(
lp
[
i
]);
}
for
(
y
=
0
;
y
<
lpbiIn
->
biHeight
;
y
++
)
{
int
x
;
switch
(
lpbiIn
->
biBitCount
)
{
case
1
:
for
(
x
=
0
;
x
<
lpbiIn
->
biWidth
;
x
+=
8
)
{
for
(
i
=
0
;
i
<
7
;
i
++
)
lpOut
[
x
+
i
]
=
wIntensityTbl
[(
lpIn
[
x
]
>>
(
7
-
i
))
&
1
];
}
break
;
case
4
:
for
(
x
=
0
;
x
<
lpbiIn
->
biWidth
;
x
+=
2
)
{
lpOut
[
x
+
0
]
=
wIntensityTbl
[(
lpIn
[
x
]
>>
4
)];
lpOut
[
x
+
1
]
=
wIntensityTbl
[(
lpIn
[
x
]
&
0x0F
)];
}
break
;
case
8
:
for
(
x
=
0
;
x
<
lpbiIn
->
biWidth
;
x
++
)
lpOut
[
x
]
=
wIntensityTbl
[
lpIn
[
x
]];
break
;
}
lpIn
+=
lInLine
;
lpOut
+=
lOutLine
;
}
}
static
LONG
MSRLE32_GetMaxCompressedSize
(
LPCBITMAPINFOHEADER
lpbi
)
{
LONG
a
,
b
,
size
;
/* pre-condition */
assert
(
lpbi
!=
NULL
);
a
=
lpbi
->
biWidth
/
255
;
b
=
lpbi
->
biWidth
%
255
;
if
(
lpbi
->
biBitCount
<=
4
)
{
a
/=
2
;
b
/=
2
;
}
size
=
(
2
+
a
*
(
2
+
((
a
+
2
)
&
~
2
))
+
b
*
(
2
+
((
b
+
2
)
&
~
2
)));
return
size
*
lpbi
->
biHeight
;
}
/* lpP => current pos in previous frame
* lpA => previous pos in current frame
* lpB => current pos in current frame
*/
static
INT
countDiffRLE4
(
LPWORD
lpP
,
LPWORD
lpA
,
LPWORD
lpB
,
INT
pos
,
LONG
lDist
,
LONG
width
)
{
INT
count
;
WORD
clr1
,
clr2
;
/* pre-conditions */
assert
(
lpA
&&
lpB
&&
lDist
>=
0
&&
width
>
0
);
if
(
pos
>=
width
)
return
0
;
if
(
pos
+
1
==
width
)
return
1
;
clr1
=
lpB
[
pos
++
];
clr2
=
lpB
[
pos
];
count
=
2
;
while
(
pos
+
1
<
width
)
{
WORD
clr3
,
clr4
;
clr3
=
lpB
[
++
pos
];
if
(
pos
+
1
>=
width
)
return
count
+
1
;
clr4
=
lpB
[
++
pos
];
if
(
ColorCmp
(
clr1
,
clr3
)
<=
lDist
&&
ColorCmp
(
clr2
,
clr4
)
<=
lDist
)
{
/* diff at end? -- look-ahead for atleast ?? more encodable pixel */
/* FIXME */
return
count
;
}
else
if
(
lpP
&&
ColorCmp
(
lpP
[
pos
],
lpB
[
pos
])
<=
lDist
)
{
/* 'compare' with previous frame for end of diff */
INT
count2
=
0
;
/* FIXME */
if
(
count2
>=
4
)
return
count
;
pos
-=
count2
;
}
count
+=
2
;
clr1
=
clr3
;
clr2
=
clr4
;
}
return
count
;
}
/* lpP => current pos in previous frame
* lpA => previous pos in current frame
* lpB => current pos in current frame
*/
static
INT
countDiffRLE8
(
LPWORD
lpP
,
LPWORD
lpA
,
LPWORD
lpB
,
INT
pos
,
LONG
lDist
,
LONG
width
)
{
INT
count
;
for
(
count
=
0
;
pos
<
width
;
pos
++
,
count
++
)
{
if
(
ColorCmp
(
lpA
[
pos
],
lpB
[
pos
])
<=
lDist
)
{
/* diff at end? -- look-ahead for atleast one more encodable pixel */
if
(
pos
+
1
<
width
&&
ColorCmp
(
lpA
[
pos
],
lpB
[
pos
+
1
])
<=
lDist
)
return
count
;
}
else
if
(
lpP
!=
NULL
&&
ColorCmp
(
lpP
[
pos
],
lpB
[
pos
])
<=
lDist
)
{
/* 'compare' with previous frame for end of diff */
INT
count2
=
0
;
for
(
count2
=
0
,
pos
++
;
pos
<
width
&&
count2
<=
5
;
pos
++
,
count2
++
)
{
if
(
ColorCmp
(
lpP
[
pos
],
lpB
[
pos
])
>
lDist
)
break
;
}
if
(
count2
>
4
)
return
count
;
pos
-=
count2
;
}
}
return
count
;
}
static
INT
MSRLE32_CompressRLE4Line
(
CodecInfo
*
pi
,
LPWORD
lpP
,
LPWORD
lpC
,
LPCBITMAPINFOHEADER
lpbi
,
BYTE
*
lpIn
,
LONG
lDist
,
INT
x
,
LPBYTE
*
ppOut
,
DWORD
*
lpSizeImage
)
{
LPBYTE
lpOut
=
*
ppOut
;
INT
count
,
pos
;
WORD
clr1
,
clr2
;
/* try to encode as many pixel as possible */
count
=
1
;
pos
=
x
;
clr1
=
lpC
[
pos
++
];
if
(
pos
<
lpbi
->
biWidth
)
{
clr2
=
lpC
[
pos
];
for
(
++
count
;
pos
+
1
<
lpbi
->
biWidth
;
)
{
++
pos
;
if
(
ColorCmp
(
clr1
,
lpC
[
pos
])
>
lDist
)
break
;
count
++
;
if
(
pos
+
1
>=
lpbi
->
biWidth
)
break
;
++
pos
;
if
(
ColorCmp
(
clr2
,
lpC
[
pos
])
>
lDist
)
break
;
count
++
;
}
}
if
(
count
<
4
)
{
/* add some pixel for absoluting if possible */
count
+=
countDiffRLE4
(
lpP
,
lpC
-
1
,
lpC
,
pos
-
1
,
lDist
,
lpbi
->
biWidth
);
/* check for near end of line */
if
(
x
+
count
>
lpbi
->
biWidth
)
count
=
lpbi
->
biWidth
-
x
;
/* absolute pixel(s) in groups of atleast 3 and maximal 254 pixel */
while
(
count
>
2
)
{
INT
i
;
INT
size
=
min
(
count
,
254
);
BOOL
extra_byte
=
size
%
2
;
*
lpSizeImage
+=
2
+
size
+
extra_byte
;
count
-=
size
;
*
lpOut
++
=
0
;
*
lpOut
++
=
size
;
for
(
i
=
0
;
i
<
size
;
i
+=
2
)
{
clr1
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
x
++
;
if
(
i
+
1
<
size
)
{
clr2
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
x
++
;
}
else
clr2
=
0
;
*
lpOut
++
=
(
clr1
<<
4
)
|
clr2
;
}
if
(
extra_byte
)
*
lpOut
++
=
0
;
}
if
(
count
>
0
)
{
/* too less for absoluting so we must encode them */
assert
(
count
<=
2
);
*
lpSizeImage
+=
2
;
clr1
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
x
++
;
if
(
count
==
2
)
{
clr2
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
x
++
;
}
else
clr2
=
0
;
*
lpOut
++
=
count
;
*
lpOut
++
=
(
clr1
<<
4
)
|
clr2
;
}
}
else
{
/* encode count pixel(s) */
clr1
=
((
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)]
<<
4
)
|
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
+
1
)]);
x
+=
count
;
while
(
count
>
0
)
{
INT
size
=
min
(
count
,
254
);
*
lpSizeImage
+=
2
;
count
-=
size
;
*
lpOut
++
=
size
;
*
lpOut
++
=
clr1
;
}
}
*
ppOut
=
lpOut
;
return
x
;
}
static
INT
MSRLE32_CompressRLE8Line
(
CodecInfo
*
pi
,
LPWORD
lpP
,
LPWORD
lpC
,
LPCBITMAPINFOHEADER
lpbi
,
BYTE
*
lpIn
,
LONG
lDist
,
INT
x
,
LPBYTE
*
ppOut
,
DWORD
*
lpSizeImage
)
{
LPBYTE
lpOut
=
*
ppOut
;
INT
count
,
pos
;
WORD
clr
;
assert
(
lpbi
->
biBitCount
<=
8
);
assert
(
lpbi
->
biCompression
==
BI_RGB
);
/* try to encode as much as possible */
pos
=
x
;
clr
=
lpC
[
pos
++
];
for
(
count
=
1
;
pos
<
lpbi
->
biWidth
;
count
++
)
{
if
(
ColorCmp
(
clr
,
lpC
[
pos
++
])
>
lDist
)
break
;
}
if
(
count
<
2
)
{
/* add some more pixels for absoluting if possible */
count
+=
countDiffRLE8
(
lpP
,
lpC
-
1
,
lpC
,
pos
-
1
,
lDist
,
lpbi
->
biWidth
);
/* check for over end of line */
if
(
x
+
count
>
lpbi
->
biWidth
)
count
=
lpbi
->
biWidth
-
x
;
/* absolute pixel(s) in groups of atleast 3 and maximal 255 pixels */
while
(
count
>
2
)
{
INT
i
;
INT
size
=
min
(
count
,
255
);
BOOL
extra_byte
=
size
%
2
;
*
lpSizeImage
+=
2
+
size
+
extra_byte
;
count
-=
size
;
*
lpOut
++
=
0
;
*
lpOut
++
=
size
;
for
(
i
=
0
;
i
<
size
;
i
++
)
{
*
lpOut
++
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
x
++
;
}
if
(
extra_byte
)
*
lpOut
++
=
0
;
}
if
(
count
>
0
)
{
/* too less for absoluting so we must encode them even if it's expensive! */
assert
(
count
<=
2
);
*
lpSizeImage
+=
2
*
count
;
*
lpOut
++
=
1
;
*
lpOut
++
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
x
++
;
if
(
count
==
2
)
{
*
lpOut
++
=
1
;
*
lpOut
++
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
x
++
;
}
}
}
else
{
/* encode count pixel(s) */
clr
=
pi
->
palette_map
[
GetRawPixel
(
lpbi
,
lpIn
,
x
)];
/* optimize end of line */
if
(
x
+
count
+
1
==
lpbi
->
biWidth
)
count
++
;
x
+=
count
;
while
(
count
>
0
)
{
INT
size
=
min
(
count
,
255
);
*
lpSizeImage
+=
2
;
count
-=
size
;
*
lpOut
++
=
size
;
*
lpOut
++
=
clr
;
}
}
*
ppOut
=
lpOut
;
return
x
;
}
LRESULT
MSRLE32_CompressRLE4
(
CodecInfo
*
pi
,
LPBITMAPINFOHEADER
lpbiIn
,
LPBYTE
lpIn
,
LPBITMAPINFOHEADER
lpbiOut
,
LPBYTE
lpOut
,
BOOL
isKey
)
{
LPWORD
lpC
;
LONG
lLine
,
lInLine
,
lDist
;
/* pre-conditions */
assert
(
pi
!=
NULL
&&
lpbiOut
!=
NULL
);
assert
(
lpIn
!=
NULL
&&
lpOut
!=
NULL
);
assert
(
pi
->
pCurFrame
!=
NULL
);
lpC
=
pi
->
pCurFrame
;
lDist
=
QUALITY_to_DIST
(
pi
->
dwQuality
);
lInLine
=
DIBWIDTHBYTES
(
*
lpbiIn
);
lLine
=
WIDTHBYTES
(
lpbiOut
->
biWidth
*
16
)
/
2
;
lpbiOut
->
biSizeImage
=
0
;
if
(
isKey
)
{
/* keyframe -- convert internal frame to output format */
INT
x
,
y
;
for
(
y
=
0
;
y
<
lpbiOut
->
biHeight
;
y
++
)
{
x
=
0
;
do
{
x
=
MSRLE32_CompressRLE4Line
(
pi
,
NULL
,
lpC
,
lpbiIn
,
lpIn
,
lDist
,
x
,
&
lpOut
,
&
lpbiOut
->
biSizeImage
);
}
while
(
x
<
lpbiOut
->
biWidth
);
lpC
+=
lLine
;
lpIn
+=
lInLine
;
/* add EOL -- end of line */
lpbiOut
->
biSizeImage
+=
2
;
*
((
LPWORD
)
lpOut
)
++
=
0
;
}
}
else
{
/* delta-frame -- compute delta between last and this internal frame */
LPWORD
lpP
;
INT
x
,
y
;
INT
jumpx
,
jumpy
;
assert
(
pi
->
pPrevFrame
!=
NULL
);
lpP
=
pi
->
pPrevFrame
;
jumpy
=
0
;
jumpx
=
-
1
;
for
(
y
=
0
;
y
<
lpbiOut
->
biHeight
;
y
++
)
{
x
=
0
;
do
{
INT
count
,
pos
;
if
(
jumpx
==
-
1
)
jumpx
=
x
;
for
(
count
=
0
,
pos
=
x
;
pos
<
lpbiOut
->
biWidth
;
pos
++
,
count
++
)
{
if
(
ColorCmp
(
lpP
[
pos
],
lpC
[
pos
])
>
lDist
)
break
;
}
if
(
pos
==
lpbiOut
->
biWidth
&&
count
>
8
)
{
/* (count > 8) secures that we will save space */
jumpy
++
;
break
;
}
else
if
(
jumpy
||
jumpx
!=
pos
)
{
/* time to jump */
assert
(
jumpx
!=
-
1
);
if
(
pos
<
jumpx
)
{
/* can only jump in positive direction -- jump until EOL, EOL */
INT
w
=
lpbiOut
->
biWidth
-
jumpx
;
assert
(
jumpy
>
0
);
assert
(
w
>=
4
);
jumpx
=
0
;
jumpy
--
;
/* if (w % 255 == 2) then equal costs
* else if (w % 255 < 4 && we could encode all) then 2 bytes too expensive
* else it will be cheaper
*/
while
(
w
>
0
)
{
lpbiOut
->
biSizeImage
+=
4
;
*
lpOut
++
=
0
;
*
lpOut
++
=
2
;
*
lpOut
=
min
(
w
,
255
);
w
-=
*
lpOut
++
;
*
lpOut
++
=
0
;
}
/* add EOL -- end of line */
lpbiOut
->
biSizeImage
+=
2
;
*
((
LPWORD
)
lpOut
)
++
=
0
;
}
/* FIXME: if (jumpy == 0 && could encode all) then jump too expensive */
/* write out real jump(s) */
while
(
jumpy
||
pos
!=
jumpx
)
{
lpbiOut
->
biSizeImage
+=
4
;
*
lpOut
++
=
0
;
*
lpOut
++
=
2
;
*
lpOut
=
min
(
pos
-
jumpx
,
255
);
x
+=
*
lpOut
;
jumpx
+=
*
lpOut
++
;
*
lpOut
=
min
(
jumpy
,
255
);
jumpy
-=
*
lpOut
++
;
}
jumpy
=
0
;
}
jumpx
=
-
1
;
if
(
x
<
lpbiOut
->
biWidth
)
{
/* skipped the 'same' things corresponding to previous frame */
x
=
MSRLE32_CompressRLE4Line
(
pi
,
lpP
,
lpC
,
lpbiIn
,
lpIn
,
lDist
,
x
,
&
lpOut
,
&
lpbiOut
->
biSizeImage
);
}
}
while
(
x
<
lpbiOut
->
biWidth
);
lpP
+=
lLine
;
lpC
+=
lLine
;
lpIn
+=
lInLine
;
if
(
jumpy
==
0
)
{
assert
(
jumpx
==
-
1
);
/* add EOL -- end of line */
lpbiOut
->
biSizeImage
+=
2
;
*
((
LPWORD
)
lpOut
)
++
=
0
;
}
}
}
/* add EOI -- end of image */
lpbiOut
->
biSizeImage
+=
2
;
*
lpOut
++
=
0
;
*
lpOut
++
=
1
;
return
ICERR_OK
;
}
LRESULT
MSRLE32_CompressRLE8
(
CodecInfo
*
pi
,
LPBITMAPINFOHEADER
lpbiIn
,
LPBYTE
lpIn
,
LPBITMAPINFOHEADER
lpbiOut
,
LPBYTE
lpOut
,
BOOL
isKey
)
{
LPWORD
lpC
;
LONG
lDist
,
lInLine
,
lLine
;
assert
(
pi
!=
NULL
&&
lpbiOut
!=
NULL
);
assert
(
lpIn
!=
NULL
&&
lpOut
!=
NULL
);
assert
(
pi
->
pCurFrame
!=
NULL
);
lpC
=
pi
->
pCurFrame
;
lDist
=
QUALITY_to_DIST
(
pi
->
dwQuality
);
lInLine
=
DIBWIDTHBYTES
(
*
lpbiIn
);
lLine
=
WIDTHBYTES
(
lpbiOut
->
biWidth
*
16
)
/
2
;
lpbiOut
->
biSizeImage
=
0
;
if
(
isKey
)
{
/* keyframe -- convert internal frame to output format */
INT
x
,
y
;
for
(
y
=
0
;
y
<
lpbiOut
->
biHeight
;
y
++
)
{
x
=
0
;
do
{
x
=
MSRLE32_CompressRLE8Line
(
pi
,
NULL
,
lpC
,
lpbiIn
,
lpIn
,
lDist
,
x
,
&
lpOut
,
&
lpbiOut
->
biSizeImage
);
}
while
(
x
<
lpbiOut
->
biWidth
);
lpC
+=
lLine
;
lpIn
+=
lInLine
;
/* add EOL -- end of line */
lpbiOut
->
biSizeImage
+=
2
;
*
((
LPWORD
)
lpOut
)
++
=
0
;
}
}
else
{
/* delta-frame -- compute delta between last and this internal frame */
LPWORD
lpP
;
INT
x
,
y
;
INT
jumpx
,
jumpy
;
assert
(
pi
->
pPrevFrame
!=
NULL
);
lpP
=
pi
->
pPrevFrame
;
jumpx
=
-
1
;
jumpy
=
0
;
for
(
y
=
0
;
y
<
lpbiOut
->
biHeight
;
y
++
)
{
x
=
0
;
do
{
INT
count
,
pos
;
if
(
jumpx
==
-
1
)
jumpx
=
x
;
for
(
count
=
0
,
pos
=
x
;
pos
<
lpbiOut
->
biWidth
;
pos
++
,
count
++
)
{
if
(
ColorCmp
(
lpP
[
pos
],
lpC
[
pos
])
>
lDist
)
break
;
}
if
(
pos
==
lpbiOut
->
biWidth
&&
count
>
4
)
{
/* (count > 4) secures that we will save space */
jumpy
++
;
break
;
}
else
if
(
jumpy
||
jumpx
!=
pos
)
{
/* time to jump */
assert
(
jumpx
!=
-
1
);
if
(
pos
<
jumpx
)
{
/* can only jump in positive direction -- do a EOL then jump */
assert
(
jumpy
>
0
);
jumpx
=
0
;
jumpy
--
;
/* add EOL -- end of line */
lpbiOut
->
biSizeImage
+=
2
;
*
((
LPWORD
)
lpOut
)
++
=
0
;
}
/* FIXME: if (jumpy == 0 && could encode all) then jump too expensive */
/* write out real jump(s) */
while
(
jumpy
||
pos
!=
jumpx
)
{
lpbiOut
->
biSizeImage
+=
4
;
*
lpOut
++
=
0
;
*
lpOut
++
=
2
;
*
lpOut
=
min
(
pos
-
jumpx
,
255
);
jumpx
+=
*
lpOut
++
;
*
lpOut
=
min
(
jumpy
,
255
);
jumpy
-=
*
lpOut
++
;
}
x
=
pos
;
jumpy
=
0
;
}
jumpx
=
-
1
;
if
(
x
<
lpbiOut
->
biWidth
)
{
/* skip the 'same' things corresponding to previous frame */
x
=
MSRLE32_CompressRLE8Line
(
pi
,
lpP
,
lpC
,
lpbiIn
,
lpIn
,
lDist
,
x
,
&
lpOut
,
&
lpbiOut
->
biSizeImage
);
}
}
while
(
x
<
lpbiOut
->
biWidth
);
lpP
+=
lLine
;
lpC
+=
lLine
;
lpIn
+=
lInLine
;
if
(
jumpy
==
0
)
{
/* add EOL -- end of line */
lpbiOut
->
biSizeImage
+=
2
;
*
lpOut
++
=
0
;
*
lpOut
++
=
0
;
}
}
}
/* add EOI -- end of image */
lpbiOut
->
biSizeImage
+=
2
;
*
lpOut
++
=
0
;
*
lpOut
++
=
1
;
return
ICERR_OK
;
}
/*****************************************************************************/
static
LRESULT
MSRLE32_DecompressRLE4
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbi
,
LPBYTE
lpIn
,
LPBYTE
lpOut
)
{
int
bytes_per_pixel
;
int
line_size
;
int
pixel_ptr
=
0
;
int
i
;
BOOL
bEndFlag
=
FALSE
;
assert
(
pi
!=
NULL
);
assert
(
lpbi
!=
NULL
&&
lpbi
->
biCompression
==
BI_RGB
);
assert
(
lpIn
!=
NULL
&&
lpOut
!=
NULL
);
bytes_per_pixel
=
(
lpbi
->
biBitCount
+
1
)
/
8
;
line_size
=
DIBWIDTHBYTES
(
*
lpbi
);
do
{
BYTE
code0
,
code1
;
code0
=
*
lpIn
++
;
code1
=
*
lpIn
++
;
if
(
code0
==
0
)
{
int
extra_byte
;
switch
(
code1
)
{
case
0
:
/* EOL - end of line */
pixel_ptr
=
0
;
lpOut
+=
line_size
;
break
;
case
1
:
/* EOI - end of image */
bEndFlag
=
TRUE
;
break
;
case
2
:
/* skip */
pixel_ptr
+=
*
lpIn
++
*
bytes_per_pixel
;
lpOut
+=
*
lpIn
++
*
line_size
;
if
(
pixel_ptr
>=
lpbi
->
biWidth
*
bytes_per_pixel
)
{
pixel_ptr
=
0
;
lpOut
+=
line_size
;
}
break
;
default:
/* absolute mode */
extra_byte
=
(
code1
/
2
)
&
0x01
;
if
(
pixel_ptr
/
bytes_per_pixel
+
code1
>
lpbi
->
biWidth
)
return
ICERR_ERROR
;
code0
=
code1
;
for
(
i
=
0
;
i
<
code0
/
2
;
i
++
)
{
if
(
bytes_per_pixel
==
1
)
{
code1
=
lpIn
[
i
];
lpOut
[
pixel_ptr
++
]
=
pi
->
palette_map
[(
code1
>>
4
)];
if
(
2
*
i
<=
code0
)
lpOut
[
pixel_ptr
++
]
=
pi
->
palette_map
[(
code1
&
0x0F
)];
}
else
if
(
bytes_per_pixel
==
2
)
{
code1
=
lpIn
[
i
]
>>
4
;
lpOut
[
pixel_ptr
++
]
=
pi
->
palette_map
[
code1
*
2
+
0
];
lpOut
[
pixel_ptr
++
]
=
pi
->
palette_map
[
code1
*
2
+
1
];
if
(
2
*
i
<=
code0
)
{
code1
=
lpIn
[
i
]
&
0x0F
;
lpOut
[
pixel_ptr
++
]
=
pi
->
palette_map
[
code1
*
2
+
0
];
lpOut
[
pixel_ptr
++
]
=
pi
->
palette_map
[
code1
*
2
+
1
];
}
}
else
{
code1
=
lpIn
[
i
]
>>
4
;
lpOut
[
pixel_ptr
+
0
]
=
pi
->
palette_map
[
code1
*
4
+
0
];
lpOut
[
pixel_ptr
+
1
]
=
pi
->
palette_map
[
code1
*
4
+
1
];
lpOut
[
pixel_ptr
+
2
]
=
pi
->
palette_map
[
code1
*
4
+
2
];
pixel_ptr
+=
bytes_per_pixel
;
if
(
2
*
i
<=
code0
)
{
code1
=
lpIn
[
i
]
&
0x0F
;
lpOut
[
pixel_ptr
+
0
]
=
pi
->
palette_map
[
code1
*
4
+
0
];
lpOut
[
pixel_ptr
+
1
]
=
pi
->
palette_map
[
code1
*
4
+
1
];
lpOut
[
pixel_ptr
+
2
]
=
pi
->
palette_map
[
code1
*
4
+
2
];
pixel_ptr
+=
bytes_per_pixel
;
}
}
}
lpIn
+=
code0
/
2
;
/* if the RLE code is odd, skip a byte in the stream */
if
(
extra_byte
)
lpIn
++
;
};
}
else
{
/* coded mode */
if
(
pixel_ptr
/
bytes_per_pixel
+
code0
>
lpbi
->
biWidth
)
return
ICERR_ERROR
;
if
(
bytes_per_pixel
==
1
)
{
BYTE
c1
=
pi
->
palette_map
[(
code1
>>
4
)];
BYTE
c2
=
pi
->
palette_map
[(
code1
&
0x0F
)];
for
(
i
=
0
;
i
<
code0
;
i
++
)
{
if
((
i
&
1
)
==
0
)
lpOut
[
pixel_ptr
++
]
=
c1
;
else
lpOut
[
pixel_ptr
++
]
=
c2
;
}
}
else
if
(
bytes_per_pixel
==
2
)
{
BYTE
hi1
=
pi
->
palette_map
[(
code1
>>
4
)
*
2
+
0
];
BYTE
lo1
=
pi
->
palette_map
[(
code1
>>
4
)
*
2
+
1
];
BYTE
hi2
=
pi
->
palette_map
[(
code1
&
0x0F
)
*
2
+
0
];
BYTE
lo2
=
pi
->
palette_map
[(
code1
&
0x0F
)
*
2
+
1
];
for
(
i
=
0
;
i
<
code0
;
i
++
)
{
if
((
i
&
1
)
==
0
)
{
lpOut
[
pixel_ptr
++
]
=
hi1
;
lpOut
[
pixel_ptr
++
]
=
lo1
;
}
else
{
lpOut
[
pixel_ptr
++
]
=
hi2
;
lpOut
[
pixel_ptr
++
]
=
lo2
;
}
}
}
else
{
BYTE
b1
=
pi
->
palette_map
[(
code1
>>
4
)
*
4
+
0
];
BYTE
g1
=
pi
->
palette_map
[(
code1
>>
4
)
*
4
+
1
];
BYTE
r1
=
pi
->
palette_map
[(
code1
>>
4
)
*
4
+
2
];
BYTE
b2
=
pi
->
palette_map
[(
code1
&
0x0F
)
*
4
+
0
];
BYTE
g2
=
pi
->
palette_map
[(
code1
&
0x0F
)
*
4
+
1
];
BYTE
r2
=
pi
->
palette_map
[(
code1
&
0x0F
)
*
4
+
2
];
for
(
i
=
0
;
i
<
code0
;
i
++
)
{
if
((
i
&
1
)
==
0
)
{
lpOut
[
pixel_ptr
+
0
]
=
b1
;
lpOut
[
pixel_ptr
+
1
]
=
g1
;
lpOut
[
pixel_ptr
+
2
]
=
r1
;
}
else
{
lpOut
[
pixel_ptr
+
0
]
=
b2
;
lpOut
[
pixel_ptr
+
1
]
=
g2
;
lpOut
[
pixel_ptr
+
2
]
=
r2
;
}
pixel_ptr
+=
bytes_per_pixel
;
}
}
}
}
while
(
!
bEndFlag
);
return
ICERR_OK
;
}
static
LRESULT
MSRLE32_DecompressRLE8
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbi
,
LPBYTE
lpIn
,
LPBYTE
lpOut
)
{
int
bytes_per_pixel
;
int
line_size
;
int
pixel_ptr
=
0
;
BOOL
bEndFlag
=
FALSE
;
assert
(
pi
!=
NULL
);
assert
(
lpbi
!=
NULL
&&
lpbi
->
biCompression
==
BI_RGB
);
assert
(
lpIn
!=
NULL
&&
lpOut
!=
NULL
);
bytes_per_pixel
=
(
lpbi
->
biBitCount
+
1
)
/
8
;
line_size
=
DIBWIDTHBYTES
(
*
lpbi
);
do
{
BYTE
code0
,
code1
;
code0
=
*
lpIn
++
;
code1
=
*
lpIn
++
;
if
(
code0
==
0
)
{
int
extra_byte
;
switch
(
code1
)
{
case
0
:
/* EOL - end of line */
pixel_ptr
=
0
;
lpOut
+=
line_size
;
break
;
case
1
:
/* EOI - end of image */
bEndFlag
=
TRUE
;
break
;
case
2
:
/* skip */
pixel_ptr
+=
*
lpIn
++
*
bytes_per_pixel
;
lpOut
+=
*
lpIn
++
*
line_size
;
if
(
pixel_ptr
>=
lpbi
->
biWidth
*
bytes_per_pixel
)
{
pixel_ptr
=
0
;
lpOut
+=
line_size
;
}
break
;
default:
/* absolute mode */
if
(
pixel_ptr
/
bytes_per_pixel
+
code1
>
lpbi
->
biWidth
)
{
WARN
(
"aborted absolute: (%d=%d/%d+%d) > %ld
\n
"
,
pixel_ptr
/
bytes_per_pixel
+
code1
,
pixel_ptr
,
bytes_per_pixel
,
code1
,
lpbi
->
biWidth
);
return
ICERR_ERROR
;
}
extra_byte
=
code1
&
0x01
;
code0
=
code1
;
while
(
code0
--
)
{
code1
=
*
lpIn
++
;
if
(
bytes_per_pixel
==
1
)
{
lpOut
[
pixel_ptr
]
=
pi
->
palette_map
[
code1
];
}
else
if
(
bytes_per_pixel
==
2
)
{
lpOut
[
pixel_ptr
+
0
]
=
pi
->
palette_map
[
code1
*
2
+
0
];
lpOut
[
pixel_ptr
+
1
]
=
pi
->
palette_map
[
code1
*
2
+
1
];
}
else
{
lpOut
[
pixel_ptr
+
0
]
=
pi
->
palette_map
[
code1
*
4
+
0
];
lpOut
[
pixel_ptr
+
1
]
=
pi
->
palette_map
[
code1
*
4
+
1
];
lpOut
[
pixel_ptr
+
2
]
=
pi
->
palette_map
[
code1
*
4
+
2
];
}
pixel_ptr
+=
bytes_per_pixel
;
}
/* if the RLE code is odd, skip a byte in the stream */
if
(
extra_byte
)
lpIn
++
;
};
}
else
{
/* coded mode */
if
(
pixel_ptr
/
bytes_per_pixel
+
code0
>
lpbi
->
biWidth
)
{
WARN
(
"aborted coded: (%d=%d/%d+%d) > %ld
\n
"
,
pixel_ptr
/
bytes_per_pixel
+
code1
,
pixel_ptr
,
bytes_per_pixel
,
code1
,
lpbi
->
biWidth
);
return
ICERR_ERROR
;
}
if
(
bytes_per_pixel
==
1
)
{
code1
=
pi
->
palette_map
[
code1
];
while
(
code0
--
)
lpOut
[
pixel_ptr
++
]
=
code1
;
}
else
if
(
bytes_per_pixel
==
2
)
{
BYTE
hi
=
pi
->
palette_map
[
code1
*
2
+
0
];
BYTE
lo
=
pi
->
palette_map
[
code1
*
2
+
1
];
while
(
code0
--
)
{
lpOut
[
pixel_ptr
+
0
]
=
hi
;
lpOut
[
pixel_ptr
+
1
]
=
lo
;
pixel_ptr
+=
bytes_per_pixel
;
}
}
else
{
BYTE
r
=
pi
->
palette_map
[
code1
*
4
+
2
];
BYTE
g
=
pi
->
palette_map
[
code1
*
4
+
1
];
BYTE
b
=
pi
->
palette_map
[
code1
*
4
+
0
];
while
(
code0
--
)
{
lpOut
[
pixel_ptr
+
0
]
=
b
;
lpOut
[
pixel_ptr
+
1
]
=
g
;
lpOut
[
pixel_ptr
+
2
]
=
r
;
pixel_ptr
+=
bytes_per_pixel
;
}
}
}
}
while
(
!
bEndFlag
);
return
ICERR_OK
;
}
/*****************************************************************************/
static
CodecInfo
*
Open
(
LPICOPEN
icinfo
)
{
CodecInfo
*
pi
=
NULL
;
if
(
icinfo
==
NULL
)
{
TRACE
(
"(NULL)
\n
"
);
return
(
LPVOID
)
0xFFFF0000
;
}
TRACE
(
"(%p = {%lu,0x%08lX(%4.4s),0x%08lX(%4.4s),0x%lX,0x%lX,...})
\n
"
,
icinfo
,
icinfo
->
dwSize
,
icinfo
->
fccType
,
(
char
*
)
&
icinfo
->
fccType
,
icinfo
->
fccHandler
,
(
char
*
)
&
icinfo
->
fccHandler
,
icinfo
->
dwVersion
,
icinfo
->
dwFlags
);
if
(
icinfo
->
fccType
!=
ICTYPE_VIDEO
)
return
NULL
;
switch
(
icinfo
->
fccHandler
)
{
case
FOURCC_RLE
:
case
FOURCC_RLE4
:
case
FOURCC_RLE8
:
case
FOURCC_MRLE
:
break
;
case
mmioFOURCC
(
'm'
,
'r'
,
'l'
,
'e'
):
icinfo
->
fccHandler
=
FOURCC_MRLE
;
break
;
default:
WARN
(
"unknown FOURCC = 0x%08lX(%4.4s) !
\n
"
,
icinfo
->
fccHandler
,(
char
*
)
&
icinfo
->
fccHandler
);
return
NULL
;
}
pi
=
(
CodecInfo
*
)
LocalAlloc
(
LPTR
,
sizeof
(
CodecInfo
));
if
(
pi
!=
NULL
)
{
pi
->
fccHandler
=
icinfo
->
fccHandler
;
pi
->
bCompress
=
FALSE
;
pi
->
dwQuality
=
MSRLE32_DEFAULTQUALITY
;
pi
->
nPrevFrame
=
-
1
;
pi
->
pPrevFrame
=
pi
->
pCurFrame
=
NULL
;
pi
->
bDecompress
=
FALSE
;
pi
->
palette_map
=
NULL
;
}
icinfo
->
dwError
=
(
pi
!=
NULL
?
ICERR_OK
:
ICERR_MEMORY
);
return
pi
;
}
static
LRESULT
Close
(
CodecInfo
*
pi
)
{
TRACE
(
"(%p)
\n
"
,
pi
);
/* pre-condition */
assert
(
pi
!=
NULL
);
if
(
pi
->
pPrevFrame
!=
NULL
||
pi
->
pCurFrame
!=
NULL
)
CompressEnd
(
pi
);
LocalFree
((
HLOCAL
)
pi
);
return
1
;
}
static
LRESULT
GetInfo
(
CodecInfo
*
pi
,
ICINFO
*
icinfo
,
DWORD
dwSize
)
{
/* pre-condition */
assert
(
pi
!=
NULL
);
/* check parameters */
if
(
icinfo
==
NULL
)
return
sizeof
(
ICINFO
);
if
(
dwSize
<
sizeof
(
ICINFO
))
return
0
;
icinfo
->
dwSize
=
sizeof
(
ICINFO
);
icinfo
->
fccType
=
streamtypeVIDEO
;
icinfo
->
fccHandler
=
(
pi
!=
NULL
?
pi
->
fccHandler
:
FOURCC_MRLE
);
icinfo
->
dwFlags
=
VIDCF_QUALITY
|
VIDCF_TEMPORAL
|
VIDCF_CRUNCH
|
VIDCF_FASTTEMPORALC
;
icinfo
->
dwVersion
=
MSRLE32_VERSION
;
icinfo
->
dwVersionICM
=
0x01040000
;
/* Version 1.4 build 0 */
LoadWideString
(
IDS_NAME
,
icinfo
->
szName
,
sizeof
(
icinfo
->
szName
));
LoadWideString
(
IDS_DESCRIPTION
,
icinfo
->
szDescription
,
sizeof
(
icinfo
->
szDescription
));
return
sizeof
(
ICINFO
);
}
static
LRESULT
SetQuality
(
CodecInfo
*
pi
,
LONG
lQuality
)
{
/* pre-condition */
assert
(
pi
!=
NULL
);
if
(
lQuality
==
-
1
)
lQuality
=
MSRLE32_DEFAULTQUALITY
;
else
if
(
ICQUALITY_LOW
>
lQuality
||
lQuality
>
ICQUALITY_HIGH
)
return
ICERR_BADPARAM
;
pi
->
dwQuality
=
(
DWORD
)
lQuality
;
return
ICERR_OK
;
}
static
LRESULT
Configure
(
CodecInfo
*
pi
,
HWND
hWnd
)
{
/* pre-condition */
assert
(
pi
!=
NULL
);
/* FIXME */
return
ICERR_OK
;
}
static
LRESULT
About
(
CodecInfo
*
pi
,
HWND
hWnd
)
{
CHAR
szTitle
[
20
];
CHAR
szAbout
[
128
];
/* pre-condition */
assert
(
MSRLE32_hModule
!=
0
);
LoadStringA
(
MSRLE32_hModule
,
IDS_NAME
,
szTitle
,
sizeof
(
szTitle
));
LoadStringA
(
MSRLE32_hModule
,
IDS_ABOUT
,
szAbout
,
sizeof
(
szAbout
));
MessageBoxA
(
hWnd
,
szAbout
,
szTitle
,
MB_OK
|
MB_ICONINFORMATION
);
return
ICERR_OK
;
}
static
LRESULT
CompressGetFormat
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBITMAPINFOHEADER
lpbiOut
)
{
LRESULT
size
;
TRACE
(
"(%p,%p,%p)
\n
"
,
pi
,
lpbiIn
,
lpbiOut
);
/* pre-condition */
assert
(
pi
!=
NULL
);
/* check parameters -- need atleast input format */
if
(
lpbiIn
==
NULL
)
{
if
(
lpbiOut
!=
NULL
)
return
ICERR_BADPARAM
;
return
0
;
}
/* handle unsupported input format */
if
(
CompressQuery
(
pi
,
lpbiIn
,
NULL
)
!=
ICERR_OK
)
return
(
lpbiOut
==
NULL
?
ICERR_BADFORMAT
:
0
);
assert
(
0
<
lpbiIn
->
biBitCount
&&
lpbiIn
->
biBitCount
<=
8
);
switch
(
pi
->
fccHandler
)
{
case
FOURCC_RLE4
:
size
=
1
<<
4
;
break
;
case
FOURCC_RLE8
:
size
=
1
<<
8
;
break
;
case
FOURCC_RLE
:
case
FOURCC_MRLE
:
size
=
(
lpbiIn
->
biBitCount
<=
4
?
1
<<
4
:
1
<<
8
);
break
;
default:
return
ICERR_ERROR
;
}
if
(
lpbiIn
->
biClrUsed
!=
0
)
size
=
lpbiIn
->
biClrUsed
;
size
=
sizeof
(
BITMAPINFOHEADER
)
+
size
*
sizeof
(
RGBQUAD
);
if
(
lpbiOut
!=
NULL
)
{
lpbiOut
->
biSize
=
sizeof
(
BITMAPINFOHEADER
);
lpbiOut
->
biWidth
=
lpbiIn
->
biWidth
;
lpbiOut
->
biHeight
=
lpbiIn
->
biHeight
;
lpbiOut
->
biPlanes
=
1
;
if
(
pi
->
fccHandler
==
FOURCC_RLE4
||
lpbiIn
->
biBitCount
<=
4
)
{
lpbiOut
->
biCompression
=
BI_RLE4
;
lpbiOut
->
biBitCount
=
4
;
}
else
{
lpbiOut
->
biCompression
=
BI_RLE8
;
lpbiOut
->
biBitCount
=
8
;
}
lpbiOut
->
biSizeImage
=
MSRLE32_GetMaxCompressedSize
(
lpbiOut
);
lpbiOut
->
biXPelsPerMeter
=
lpbiIn
->
biXPelsPerMeter
;
lpbiOut
->
biYPelsPerMeter
=
lpbiIn
->
biYPelsPerMeter
;
if
(
lpbiIn
->
biClrUsed
==
0
)
size
=
1
<<
lpbiIn
->
biBitCount
;
else
size
=
lpbiIn
->
biClrUsed
;
lpbiOut
->
biClrUsed
=
min
(
size
,
1u
<<
lpbiOut
->
biBitCount
);
lpbiOut
->
biClrImportant
=
0
;
memcpy
((
LPBYTE
)
lpbiOut
+
lpbiOut
->
biSize
,
(
LPBYTE
)
lpbiIn
+
lpbiIn
->
biSize
,
lpbiOut
->
biClrUsed
*
sizeof
(
RGBQUAD
));
return
ICERR_OK
;
}
else
return
size
;
}
static
LRESULT
CompressGetSize
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
)
{
/* pre-condition */
assert
(
pi
!=
NULL
);
TRACE
(
"(%p,%p,%p)
\n
"
,
pi
,
lpbiIn
,
lpbiOut
);
/* check parameter -- need atleast one format */
if
(
lpbiIn
==
NULL
&&
lpbiOut
==
NULL
)
return
0
;
/* check if the given format is supported */
if
(
CompressQuery
(
pi
,
lpbiIn
,
lpbiOut
)
!=
ICERR_OK
)
return
0
;
/* the worst case is coding the complete image in absolute mode. */
if
(
lpbiIn
)
return
MSRLE32_GetMaxCompressedSize
(
lpbiIn
);
else
return
MSRLE32_GetMaxCompressedSize
(
lpbiOut
);
}
static
LRESULT
CompressQuery
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
)
{
/* pre-condition */
assert
(
pi
!=
NULL
);
/* need atleast one format */
if
(
lpbiIn
==
NULL
&&
lpbiOut
==
NULL
)
return
ICERR_BADPARAM
;
/* check input format if given */
if
(
lpbiIn
!=
NULL
)
{
if
(
!
isSupportedDIB
(
lpbiIn
))
return
ICERR_BADFORMAT
;
/* for 4-bit need an even width */
if
(
lpbiIn
->
biBitCount
<=
4
&&
(
lpbiIn
->
biWidth
%
2
))
return
ICERR_BADFORMAT
;
if
(
pi
->
fccHandler
==
FOURCC_RLE4
&&
lpbiIn
->
biBitCount
>
4
)
return
ICERR_UNSUPPORTED
;
else
if
(
lpbiIn
->
biBitCount
>
8
)
return
ICERR_UNSUPPORTED
;
}
/* check output format if given */
if
(
lpbiOut
!=
NULL
)
{
if
(
!
isSupportedMRLE
(
lpbiOut
))
return
ICERR_BADFORMAT
;
if
(
lpbiIn
!=
NULL
)
{
if
(
lpbiIn
->
biWidth
!=
lpbiOut
->
biWidth
)
return
ICERR_UNSUPPORTED
;
if
(
lpbiIn
->
biHeight
!=
lpbiOut
->
biHeight
)
return
ICERR_UNSUPPORTED
;
if
(
lpbiIn
->
biBitCount
>
lpbiOut
->
biBitCount
)
return
ICERR_UNSUPPORTED
;
}
}
return
ICERR_OK
;
}
static
LRESULT
CompressBegin
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
)
{
RGBQUAD
*
rgbIn
;
RGBQUAD
*
rgbOut
;
int
i
;
size_t
size
;
TRACE
(
"(%p,%p,%p)
\n
"
,
pi
,
lpbiIn
,
lpbiOut
);
/* pre-condition */
assert
(
pi
!=
NULL
);
/* check parameters -- need both formats */
if
(
lpbiIn
==
NULL
||
lpbiOut
==
NULL
)
return
ICERR_BADPARAM
;
/* And both must be supported */
if
(
CompressQuery
(
pi
,
lpbiIn
,
lpbiOut
)
!=
ICERR_OK
)
return
ICERR_BADFORMAT
;
/* FIXME: cannot compress and decompress at a time! */
if
(
pi
->
bDecompress
)
{
FIXME
(
"cannot compress and decompress at same time!
\n
"
);
return
ICERR_ERROR
;
}
if
(
pi
->
bCompress
)
CompressEnd
(
pi
);
size
=
WIDTHBYTES
(
lpbiOut
->
biWidth
*
16
)
/
2
*
lpbiOut
->
biHeight
;
pi
->
pPrevFrame
=
(
LPWORD
)
GlobalAllocPtr
(
GPTR
,
size
*
sizeof
(
WORD
));
if
(
pi
->
pPrevFrame
==
NULL
)
return
ICERR_MEMORY
;
pi
->
pCurFrame
=
(
LPWORD
)
GlobalAllocPtr
(
GPTR
,
size
*
sizeof
(
WORD
));
if
(
pi
->
pCurFrame
==
NULL
)
{
CompressEnd
(
pi
);
return
ICERR_MEMORY
;
}
pi
->
nPrevFrame
=
-
1
;
pi
->
bCompress
=
TRUE
;
rgbIn
=
(
RGBQUAD
*
)((
LPBYTE
)
lpbiIn
+
lpbiIn
->
biSize
);
rgbOut
=
(
RGBQUAD
*
)((
LPBYTE
)
lpbiOut
+
lpbiOut
->
biSize
);
switch
(
lpbiOut
->
biBitCount
)
{
case
4
:
case
8
:
pi
->
palette_map
=
(
LPBYTE
)
LocalAlloc
(
LPTR
,
lpbiIn
->
biClrUsed
);
if
(
pi
->
palette_map
==
NULL
)
{
CompressEnd
(
pi
);
return
ICERR_MEMORY
;
}
for
(
i
=
0
;
i
<
lpbiIn
->
biClrUsed
;
i
++
)
{
pi
->
palette_map
[
i
]
=
MSRLE32_GetNearestPaletteIndex
(
lpbiOut
->
biClrUsed
,
rgbOut
,
rgbIn
[
i
]);
}
break
;
};
return
ICERR_OK
;
}
static
LRESULT
Compress
(
CodecInfo
*
pi
,
ICCOMPRESS
*
lpic
,
DWORD
dwSize
)
{
int
i
;
TRACE
(
"(%p,%p,%lu)
\n
"
,
pi
,
lpic
,
dwSize
);
/* pre-condition */
assert
(
pi
!=
NULL
);
/* check parameters */
if
(
lpic
==
NULL
||
dwSize
<
sizeof
(
ICCOMPRESS
))
return
ICERR_BADPARAM
;
if
(
!
lpic
->
lpbiOutput
||
!
lpic
->
lpOutput
||
!
lpic
->
lpbiInput
||
!
lpic
->
lpInput
)
return
ICERR_BADPARAM
;
TRACE
(
"lpic={0x%lX,%p,%p,%p,%p,%p,%p,%ld,%lu,%lu,%p,%p}
\n
"
,
lpic
->
dwFlags
,
lpic
->
lpbiOutput
,
lpic
->
lpOutput
,
lpic
->
lpbiInput
,
lpic
->
lpInput
,
lpic
->
lpckid
,
lpic
->
lpdwFlags
,
lpic
->
lFrameNum
,
lpic
->
dwFrameSize
,
lpic
->
dwQuality
,
lpic
->
lpbiPrev
,
lpic
->
lpPrev
);
if
(
!
pi
->
bCompress
)
{
LRESULT
hr
=
CompressBegin
(
pi
,
lpic
->
lpbiInput
,
lpic
->
lpbiOutput
);
if
(
hr
!=
ICERR_OK
)
return
hr
;
}
else
if
(
CompressQuery
(
pi
,
lpic
->
lpbiInput
,
lpic
->
lpbiOutput
)
!=
ICERR_OK
)
return
ICERR_BADFORMAT
;
if
(
lpic
->
lFrameNum
>=
pi
->
nPrevFrame
+
1
)
{
/* we continue in the sequence so we need to initialize
* our internal framedata */
computeInternalFrame
(
pi
,
lpic
->
lpbiInput
,
lpic
->
lpInput
);
}
else
if
(
lpic
->
lFrameNum
==
pi
->
nPrevFrame
)
{
/* Oops, compress same frame again ? Okay, as you wish.
* No need to recompute internal framedata, because we only swapped buffers */
LPWORD
pTmp
=
pi
->
pPrevFrame
;
FIXME
(
": prev=%ld cur=%ld swap
\n
"
,
pi
->
nPrevFrame
,
lpic
->
lFrameNum
);
pi
->
pPrevFrame
=
pi
->
pCurFrame
;
pi
->
pCurFrame
=
pTmp
;
}
else
if
((
lpic
->
dwFlags
&
ICCOMPRESS_KEYFRAME
)
==
0
)
{
LPWORD
pTmp
;
WARN
(
": prev=%ld cur=%ld gone back? -- untested"
,
pi
->
nPrevFrame
,
lpic
->
lFrameNum
);
if
(
lpic
->
lpbiPrev
==
NULL
||
lpic
->
lpPrev
==
NULL
)
return
ICERR_GOTOKEYFRAME
;
/* Need a keyframe if you go back */
if
(
CompressQuery
(
pi
,
lpic
->
lpbiPrev
,
lpic
->
lpbiOutput
)
!=
ICERR_OK
)
return
ICERR_BADFORMAT
;
WARN
(
": prev=%ld cur=%ld compute swapped -- untested
\n
"
,
pi
->
nPrevFrame
,
lpic
->
lFrameNum
);
computeInternalFrame
(
pi
,
lpic
->
lpbiPrev
,
lpic
->
lpPrev
);
/* swap buffers for current and previous frame */
/* Don't free and alloc new -- costs to much time and they are of equal size ! */
pTmp
=
pi
->
pPrevFrame
;
pi
->
pPrevFrame
=
pi
->
pCurFrame
;
pi
->
pCurFrame
=
pTmp
;
pi
->
nPrevFrame
=
lpic
->
lFrameNum
;
}
for
(
i
=
0
;
i
<
3
;
i
++
)
{
SetQuality
(
pi
,
lpic
->
dwQuality
);
lpic
->
lpbiOutput
->
biSizeImage
=
0
;
if
(
lpic
->
lpbiOutput
->
biBitCount
==
4
)
MSRLE32_CompressRLE4
(
pi
,
lpic
->
lpbiInput
,
(
LPBYTE
)
lpic
->
lpInput
,
lpic
->
lpbiOutput
,
(
LPBYTE
)
lpic
->
lpOutput
,
TRUE
);
/*MSRLE32_CompressRLE4(pi, lpic->lpbiInput, (LPBYTE)lpic->lpInput,
lpic->lpbiOutput, (LPBYTE)lpic->lpOutput, (lpic->dwFlags & ICCOMPRESS_KEYFRAME) != 0);*/
else
MSRLE32_CompressRLE8
(
pi
,
lpic
->
lpbiInput
,
(
LPBYTE
)
lpic
->
lpInput
,
lpic
->
lpbiOutput
,
(
LPBYTE
)
lpic
->
lpOutput
,
(
lpic
->
dwFlags
&
ICCOMPRESS_KEYFRAME
)
!=
0
);
if
(
lpic
->
dwFrameSize
==
0
||
lpic
->
lpbiOutput
->
biSizeImage
<
lpic
->
dwFrameSize
)
break
;
if
((
*
lpic
->
lpdwFlags
&
ICCOMPRESS_KEYFRAME
)
==
0
)
{
if
(
lpic
->
lpbiOutput
->
biBitCount
==
4
)
MSRLE32_CompressRLE4
(
pi
,
lpic
->
lpbiInput
,
(
LPBYTE
)
lpic
->
lpInput
,
lpic
->
lpbiOutput
,
(
LPBYTE
)
lpic
->
lpOutput
,
TRUE
);
else
MSRLE32_CompressRLE8
(
pi
,
lpic
->
lpbiInput
,
(
LPBYTE
)
lpic
->
lpInput
,
lpic
->
lpbiOutput
,
(
LPBYTE
)
lpic
->
lpOutput
,
TRUE
);
if
(
lpic
->
dwFrameSize
==
0
||
lpic
->
lpbiOutput
->
biSizeImage
<
lpic
->
dwFrameSize
)
{
WARN
(
"switched to keyframe, was small enough!
\n
"
);
*
lpic
->
lpdwFlags
|=
ICCOMPRESS_KEYFRAME
;
*
lpic
->
lpckid
=
MAKEAVICKID
(
cktypeDIBbits
,
StreamFromFOURCC
(
*
lpic
->
lpckid
));
break
;
}
}
if
(
lpic
->
dwQuality
<
1000
)
break
;
lpic
->
dwQuality
-=
1000
;
/* reduce quality by 10% */
}
{
/* swap buffer for current and previous frame */
/* Don't free and alloc new -- costs to much time and they are of equal size ! */
register
LPWORD
pTmp
=
pi
->
pPrevFrame
;
pi
->
pPrevFrame
=
pi
->
pCurFrame
;
pi
->
pCurFrame
=
pTmp
;
pi
->
nPrevFrame
=
lpic
->
lFrameNum
;
}
return
ICERR_OK
;
}
static
LRESULT
CompressEnd
(
CodecInfo
*
pi
)
{
TRACE
(
"(%p)
\n
"
,
pi
);
if
(
pi
!=
NULL
)
{
if
(
pi
->
pPrevFrame
!=
NULL
)
GlobalFreePtr
(
pi
->
pPrevFrame
);
if
(
pi
->
pCurFrame
!=
NULL
)
GlobalFreePtr
(
pi
->
pCurFrame
);
pi
->
pPrevFrame
=
NULL
;
pi
->
pCurFrame
=
NULL
;
pi
->
nPrevFrame
=
-
1
;
pi
->
bCompress
=
FALSE
;
}
return
ICERR_OK
;
}
static
LRESULT
DecompressGetFormat
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBITMAPINFOHEADER
lpbiOut
)
{
int
size
;
TRACE
(
"(%p,%p,%p)
\n
"
,
pi
,
lpbiIn
,
lpbiOut
);
/* pre-condition */
assert
(
pi
!=
NULL
);
if
(
lpbiIn
==
NULL
)
return
(
lpbiOut
!=
NULL
?
ICERR_BADPARAM
:
0
);
if
(
DecompressQuery
(
pi
,
lpbiIn
,
NULL
)
!=
ICERR_OK
)
return
(
lpbiOut
!=
NULL
?
ICERR_BADFORMAT
:
0
);
size
=
lpbiIn
->
biSize
;
if
(
lpbiOut
!=
NULL
)
{
memcpy
(
lpbiOut
,
lpbiIn
,
size
);
lpbiOut
->
biBitCount
=
32
;
lpbiOut
->
biCompression
=
BI_RGB
;
lpbiOut
->
biSizeImage
=
DIBWIDTHBYTES
(
*
lpbiOut
)
*
lpbiOut
->
biHeight
;
lpbiOut
->
biClrImportant
=
0
;
if
(
lpbiOut
->
biBitCount
<=
8
&&
lpbiOut
->
biClrUsed
==
0
)
lpbiOut
->
biClrUsed
=
1
<<
lpbiOut
->
biBitCount
;
else
lpbiOut
->
biClrUsed
=
0
;
return
size
;
}
else
return
size
;
}
static
LRESULT
DecompressQuery
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
)
{
LRESULT
hr
=
ICERR_OK
;
TRACE
(
"(%p,%p,%p)
\n
"
,
pi
,
lpbiIn
,
lpbiOut
);
/* pre-condition */
assert
(
pi
!=
NULL
);
/* need atleast one format */
if
(
lpbiIn
==
NULL
&&
lpbiOut
==
NULL
)
return
ICERR_BADPARAM
;
/* check input format if given */
if
(
lpbiIn
!=
NULL
)
{
if
(
!
isSupportedMRLE
(
lpbiIn
))
return
ICERR_BADFORMAT
;
}
/* check output format if given */
if
(
lpbiOut
!=
NULL
)
{
if
(
!
isSupportedDIB
(
lpbiOut
))
hr
=
ICERR_BADFORMAT
;
if
(
lpbiIn
!=
NULL
)
{
if
(
lpbiIn
->
biWidth
!=
lpbiOut
->
biWidth
)
hr
=
ICERR_UNSUPPORTED
;
if
(
lpbiIn
->
biHeight
!=
lpbiOut
->
biHeight
)
hr
=
ICERR_UNSUPPORTED
;
if
(
lpbiIn
->
biBitCount
>
lpbiOut
->
biBitCount
)
hr
=
ICERR_UNSUPPORTED
;
}
}
return
hr
;
}
static
LRESULT
DecompressBegin
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPCBITMAPINFOHEADER
lpbiOut
)
{
RGBQUAD
*
rgbIn
;
RGBQUAD
*
rgbOut
;
int
i
;
TRACE
(
"(%p,%p,%p)
\n
"
,
pi
,
lpbiIn
,
lpbiOut
);
/* pre-condition */
assert
(
pi
!=
NULL
);
/* check parameters */
if
(
lpbiIn
==
NULL
||
lpbiOut
==
NULL
)
return
ICERR_BADPARAM
;
if
(
DecompressQuery
(
pi
,
lpbiIn
,
lpbiOut
)
!=
ICERR_OK
)
return
ICERR_BADFORMAT
;
/* FIXME: cannot compress and decompress at a time! */
if
(
pi
->
bCompress
)
{
FIXME
(
"cannot compress and decompress at same time!
\n
"
);
return
ICERR_ERROR
;
}
if
(
pi
->
bDecompress
)
DecompressEnd
(
pi
);
rgbIn
=
(
RGBQUAD
*
)((
LPBYTE
)
lpbiIn
+
lpbiIn
->
biSize
);
rgbOut
=
(
RGBQUAD
*
)((
LPBYTE
)
lpbiOut
+
lpbiOut
->
biSize
);
switch
(
lpbiOut
->
biBitCount
)
{
case
4
:
case
8
:
pi
->
palette_map
=
(
LPBYTE
)
LocalAlloc
(
LPTR
,
lpbiIn
->
biClrUsed
);
if
(
pi
->
palette_map
==
NULL
)
return
ICERR_MEMORY
;
for
(
i
=
0
;
i
<
lpbiIn
->
biClrUsed
;
i
++
)
{
pi
->
palette_map
[
i
]
=
MSRLE32_GetNearestPaletteIndex
(
lpbiOut
->
biClrUsed
,
rgbOut
,
rgbIn
[
i
]);
}
break
;
case
15
:
case
16
:
pi
->
palette_map
=
(
LPBYTE
)
LocalAlloc
(
LPTR
,
lpbiIn
->
biClrUsed
*
2
);
if
(
pi
->
palette_map
==
NULL
)
return
ICERR_MEMORY
;
for
(
i
=
0
;
i
<
lpbiIn
->
biClrUsed
;
i
++
)
{
WORD
color
;
if
(
lpbiOut
->
biBitCount
==
15
)
color
=
((
rgbIn
[
i
].
rgbRed
>>
3
)
<<
10
)
|
((
rgbIn
[
i
].
rgbGreen
>>
3
)
<<
5
)
|
(
rgbIn
[
i
].
rgbBlue
>>
3
);
else
color
=
((
rgbIn
[
i
].
rgbRed
>>
3
)
<<
11
)
|
((
rgbIn
[
i
].
rgbGreen
>>
3
)
<<
5
)
|
(
rgbIn
[
i
].
rgbBlue
>>
3
);
pi
->
palette_map
[
i
*
2
+
1
]
=
color
>>
8
;
pi
->
palette_map
[
i
*
2
+
0
]
=
color
&
0xFF
;
};
break
;
case
24
:
case
32
:
pi
->
palette_map
=
(
LPBYTE
)
LocalAlloc
(
LPTR
,
lpbiIn
->
biClrUsed
*
sizeof
(
RGBQUAD
));
if
(
pi
->
palette_map
==
NULL
)
return
ICERR_MEMORY
;
memcpy
(
pi
->
palette_map
,
rgbIn
,
lpbiIn
->
biClrUsed
*
sizeof
(
RGBQUAD
));
break
;
};
pi
->
bDecompress
=
TRUE
;
return
ICERR_OK
;
}
static
LRESULT
Decompress
(
CodecInfo
*
pi
,
ICDECOMPRESS
*
pic
,
DWORD
dwSize
)
{
TRACE
(
"(%p,%p,%lu)
\n
"
,
pi
,
pic
,
dwSize
);
/* pre-condition */
assert
(
pi
!=
NULL
);
/* check parameters */
if
(
pic
==
NULL
)
return
ICERR_BADPARAM
;
if
(
pic
->
lpbiInput
==
NULL
||
pic
->
lpInput
==
NULL
||
pic
->
lpbiOutput
==
NULL
||
pic
->
lpOutput
==
NULL
)
return
ICERR_BADPARAM
;
/* check formats */
if
(
!
pi
->
bDecompress
)
{
LRESULT
hr
=
DecompressBegin
(
pi
,
pic
->
lpbiInput
,
pic
->
lpbiOutput
);
if
(
hr
!=
ICERR_OK
)
return
hr
;
}
else
if
(
DecompressQuery
(
pi
,
pic
->
lpbiInput
,
pic
->
lpbiOutput
)
!=
ICERR_OK
)
return
ICERR_BADFORMAT
;
assert
(
pic
->
lpbiInput
->
biWidth
==
pic
->
lpbiOutput
->
biWidth
);
assert
(
pic
->
lpbiInput
->
biHeight
==
pic
->
lpbiOutput
->
biHeight
);
pic
->
lpbiOutput
->
biSizeImage
=
DIBWIDTHBYTES
(
*
pic
->
lpbiOutput
)
*
pic
->
lpbiOutput
->
biHeight
;
if
(
pic
->
lpbiInput
->
biBitCount
==
4
)
return
MSRLE32_DecompressRLE4
(
pi
,
pic
->
lpbiOutput
,
pic
->
lpInput
,
pic
->
lpOutput
);
else
return
MSRLE32_DecompressRLE8
(
pi
,
pic
->
lpbiOutput
,
pic
->
lpInput
,
pic
->
lpOutput
);
}
static
LRESULT
DecompressEnd
(
CodecInfo
*
pi
)
{
TRACE
(
"(%p)
\n
"
,
pi
);
/* pre-condition */
assert
(
pi
!=
NULL
);
pi
->
bDecompress
=
FALSE
;
if
(
pi
->
palette_map
!=
NULL
)
{
LocalFree
((
HLOCAL
)
pi
->
palette_map
);
pi
->
palette_map
=
NULL
;
}
return
ICERR_OK
;
}
static
LRESULT
DecompressGetPalette
(
CodecInfo
*
pi
,
LPCBITMAPINFOHEADER
lpbiIn
,
LPBITMAPINFOHEADER
lpbiOut
)
{
int
size
;
TRACE
(
"(%p,%p,%p)
\n
"
,
pi
,
lpbiIn
,
lpbiOut
);
/* pre-condition */
assert
(
pi
!=
NULL
);
/* check parameters */
if
(
lpbiIn
==
NULL
||
lpbiOut
==
NULL
)
return
ICERR_BADPARAM
;
if
(
DecompressQuery
(
pi
,
lpbiIn
,
lpbiOut
)
!=
ICERR_OK
)
return
ICERR_BADFORMAT
;
if
(
lpbiOut
->
biBitCount
>
8
)
return
ICERR_ERROR
;
if
(
lpbiIn
->
biBitCount
<=
8
)
{
if
(
lpbiIn
->
biClrUsed
>
0
)
size
=
lpbiIn
->
biClrUsed
;
else
size
=
(
1
<<
lpbiIn
->
biBitCount
);
lpbiOut
->
biClrUsed
=
size
;
memcpy
((
LPBYTE
)
lpbiOut
+
lpbiOut
->
biSize
,
(
LPBYTE
)
lpbiIn
+
lpbiIn
->
biSize
,
size
*
sizeof
(
RGBQUAD
));
}
/* else could never occur ! */
return
ICERR_OK
;
}
/* DriverProc - entry point for an installable driver */
LRESULT
CALLBACK
MSRLE32_DriverProc
(
DWORD
dwDrvID
,
HDRVR
hDrv
,
UINT
uMsg
,
LPARAM
lParam1
,
LPARAM
lParam2
)
{
CodecInfo
*
pi
=
(
CodecInfo
*
)
dwDrvID
;
TRACE
(
"(%p,%p,0x%04X,0x%08lX,0x%08lX)
\n
"
,
(
LPVOID
)
dwDrvID
,
(
LPVOID
)
hDrv
,
uMsg
,
lParam1
,
lParam2
);
switch
(
uMsg
)
{
/* standard driver messages */
case
DRV_LOAD
:
return
DRVCNF_OK
;
case
DRV_OPEN
:
if
(
lParam2
==
0
)
return
(
LRESULT
)
0xFFFF0000
;
else
return
(
LRESULT
)
Open
((
ICOPEN
*
)
lParam2
);
case
DRV_CLOSE
:
if
(
dwDrvID
!=
0xFFFF0000
&&
(
LPVOID
)
dwDrvID
!=
NULL
)
Close
(
pi
);
return
DRVCNF_OK
;
case
DRV_ENABLE
:
case
DRV_DISABLE
:
return
DRVCNF_OK
;
case
DRV_FREE
:
return
DRVCNF_OK
;
case
DRV_QUERYCONFIGURE
:
return
DRVCNF_CANCEL
;
/* FIXME */
case
DRV_CONFIGURE
:
return
DRVCNF_OK
;
/* FIXME */
case
DRV_INSTALL
:
case
DRV_REMOVE
:
return
DRVCNF_OK
;
/* installable compression manager messages */
case
ICM_CONFIGURE
:
FIXME
(
"ICM_CONFIGURE (%ld)
\n
"
,
lParam1
);
if
(
lParam1
==
-
1
)
return
ICERR_UNSUPPORTED
;
/* FIXME */
else
return
Configure
(
pi
,
(
HWND
)
lParam1
);
case
ICM_ABOUT
:
if
(
lParam1
==
-
1
)
return
ICERR_OK
;
else
return
About
(
pi
,
(
HWND
)
lParam1
);
case
ICM_GETSTATE
:
case
ICM_SETSTATE
:
return
0
;
/* no state */
case
ICM_GETINFO
:
return
GetInfo
(
pi
,
(
ICINFO
*
)
lParam1
,
(
DWORD
)
lParam2
);
case
ICM_GETDEFAULTQUALITY
:
if
((
LPVOID
)
lParam1
!=
NULL
)
{
*
((
LPDWORD
)
lParam1
)
=
MSRLE32_DEFAULTQUALITY
;
return
ICERR_OK
;
}
break
;
case
ICM_GETQUALITY
:
if
((
LPVOID
)
lParam1
!=
NULL
)
{
*
((
LPDWORD
)
lParam1
)
=
pi
->
dwQuality
;
return
ICERR_OK
;
}
break
;
case
ICM_SETQUALITY
:
return
SetQuality
(
pi
,
*
(
LPLONG
)
lParam1
);
break
;
case
ICM_COMPRESS_GET_FORMAT
:
return
CompressGetFormat
(
pi
,
(
LPCBITMAPINFOHEADER
)
lParam1
,
(
LPBITMAPINFOHEADER
)
lParam2
);
case
ICM_COMPRESS_GET_SIZE
:
return
CompressGetSize
(
pi
,
(
LPCBITMAPINFOHEADER
)
lParam1
,
(
LPCBITMAPINFOHEADER
)
lParam2
);
case
ICM_COMPRESS_QUERY
:
return
CompressQuery
(
pi
,
(
LPCBITMAPINFOHEADER
)
lParam1
,
(
LPCBITMAPINFOHEADER
)
lParam2
);
case
ICM_COMPRESS_BEGIN
:
return
CompressBegin
(
pi
,
(
LPCBITMAPINFOHEADER
)
lParam1
,
(
LPCBITMAPINFOHEADER
)
lParam2
);
case
ICM_COMPRESS
:
return
Compress
(
pi
,
(
ICCOMPRESS
*
)
lParam1
,
(
DWORD
)
lParam2
);
case
ICM_COMPRESS_END
:
return
CompressEnd
(
pi
);
case
ICM_DECOMPRESS_GET_FORMAT
:
return
DecompressGetFormat
(
pi
,
(
LPCBITMAPINFOHEADER
)
lParam1
,
(
LPBITMAPINFOHEADER
)
lParam2
);
case
ICM_DECOMPRESS_QUERY
:
return
DecompressQuery
(
pi
,
(
LPCBITMAPINFOHEADER
)
lParam1
,
(
LPCBITMAPINFOHEADER
)
lParam2
);
case
ICM_DECOMPRESS_BEGIN
:
return
DecompressBegin
(
pi
,
(
LPCBITMAPINFOHEADER
)
lParam1
,
(
LPCBITMAPINFOHEADER
)
lParam2
);
case
ICM_DECOMPRESS
:
return
Decompress
(
pi
,
(
ICDECOMPRESS
*
)
lParam1
,
(
DWORD
)
lParam2
);
case
ICM_DECOMPRESS_END
:
return
DecompressEnd
(
pi
);
case
ICM_DECOMPRESS_SET_PALETTE
:
FIXME
(
"(...) -> SetPalette(%p,%p,%p): stub!
\n
"
,
pi
,
(
LPVOID
)
lParam1
,
(
LPVOID
)
lParam2
);
return
ICERR_UNSUPPORTED
;
case
ICM_DECOMPRESS_GET_PALETTE
:
return
DecompressGetPalette
(
pi
,
(
LPBITMAPINFOHEADER
)
lParam1
,
(
LPBITMAPINFOHEADER
)
lParam2
);
case
ICM_GETDEFAULTKEYFRAMERATE
:
if
((
LPVOID
)
lParam1
!=
NULL
)
*
(
LPDWORD
)
lParam1
=
15
;
return
ICERR_OK
;
default:
if
(
uMsg
<
DRV_USER
)
return
DefDriverProc
(
dwDrvID
,
hDrv
,
uMsg
,
lParam1
,
lParam2
);
else
FIXME
(
"Unknown message uMsg=0x%08X lParam1=0x%08lX lParam2=0x%08lX
\n
"
,
uMsg
,
lParam1
,
lParam2
);
};
return
ICERR_UNSUPPORTED
;
}
/* DllMain - library initialization code */
BOOL
WINAPI
MSRLE32_DllMain
(
HINSTANCE
hModule
,
DWORD
dwReason
,
LPVOID
lpReserved
)
{
TRACE
(
"(%p,%ld,%p)
\n
"
,(
LPVOID
)
hModule
,
dwReason
,
lpReserved
);
switch
(
dwReason
)
{
case
DLL_PROCESS_ATTACH
:
if
(
MSRLE32_hModule
==
0
)
MSRLE32_hModule
=
hModule
;
break
;
case
DLL_THREAD_ATTACH
:
break
;
case
DLL_THREAD_DETACH
:
break
;
case
DLL_PROCESS_DETACH
:
break
;
};
return
TRUE
;
}
dlls/msvideo/msrle32/msrle32.spec
0 → 100644
View file @
288b8ee1
init MSRLE32_DllMain
@ stdcall DriverProc(long long long long long) MSRLE32_DriverProc
dlls/msvideo/msrle32/msrle_De.rc
0 → 100644
View file @
288b8ee1
/*
* German resource file for MS-RLE
*
* Copyright 2002 Michael Gnnewig
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
LANGUAGE LANG_GERMAN, SUBLANG_DEFAULT
STRINGTABLE DISCARDABLE
{
IDS_NAME "WINE-MS-RLE"
IDS_DESCRIPTION "Wine MS-RLE Videodekoder"
IDS_ABOUT "Wine MS-RLE Videodekoder\nCopyright 2002 by Michael Gnnewig"
}
dlls/msvideo/msrle32/msrle_En.rc
0 → 100644
View file @
288b8ee1
/*
* English resource file for MS-RLE
*
* Copyright 2002 Michael Gnnewig
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
LANGUAGE LANG_ENGLISH, SUBLANG_DEFAULT
STRINGTABLE DISCARDABLE
{
IDS_NAME "WINE-MS-RLE"
IDS_DESCRIPTION "Wine MS-RLE video codec"
IDS_ABOUT "Wine MS-RLE video codec\nCopyright 2002 by Michael Gnnewig"
}
dlls/msvideo/msrle32/msrle_Fr.rc
0 → 100644
View file @
288b8ee1
/*
* French resource file for MS-RLE
*
* Copyright 2002 Michael Gnnewig
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
LANGUAGE LANG_FRENCH, SUBLANG_DEFAULT
STRINGTABLE DISCARDABLE
{
IDS_NAME "WINE-MS-RLE"
IDS_DESCRIPTION "Wine: dcodeur/encodeur vido MS-RLE"
IDS_ABOUT "Wine: dcodeur/encodeur vido MS-RLE\nCopyright 2002 par Michael Gnnewig"
}
dlls/msvideo/msrle32/msrle_private.h
0 → 100644
View file @
288b8ee1
/*
* Copyright 2002 Michael Gnnewig
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __MSRLE32_PRIVATE_H
#define __MSRLE32_PRIVATE_H
#include "winbase.h"
#include "mmsystem.h"
#include "vfw.h"
#define IDS_NAME 100
#define IDS_DESCRIPTION 101
#define IDS_ABOUT 102
#define MSRLE32_VERSION 0x00010000
/* Version 1.0 build 0 */
#define MSRLE32_DEFAULTQUALITY (75 * ICQUALITY_HIGH) / 100
#define FOURCC_RLE mmioFOURCC('R','L','E',' ')
#define FOURCC_RLE4 mmioFOURCC('R','L','E','4')
#define FOURCC_RLE8 mmioFOURCC('R','L','E','8')
#define FOURCC_MRLE mmioFOURCC('M','R','L','E')
#define WIDTHBYTES(i) ((WORD)((i+31)&(~31))/8)
/* ULONG aligned ! */
#define DIBWIDTHBYTES(bi) WIDTHBYTES((WORD)(bi).biWidth * (WORD)(bi).biBitCount)
typedef
struct
_CodecInfo
{
FOURCC
fccHandler
;
DWORD
dwQuality
;
BOOL
bCompress
;
LONG
nPrevFrame
;
LPWORD
pPrevFrame
;
LPWORD
pCurFrame
;
BOOL
bDecompress
;
LPBYTE
palette_map
;
}
CodecInfo
;
typedef
const
BITMAPINFOHEADER
*
LPCBITMAPINFOHEADER
;
#endif
dlls/msvideo/msrle32/rsrc.rc
0 → 100644
View file @
288b8ee1
/*
* Top level resource file for MS-RLE
*
* Copyright 2002 Michael Günnewig
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "windef.h"
#include "msrle_private.h"
/*
* Everything specific to any language goes
* in one of the specific files.
* Note that you can and may override resources
* which also have a neutral version. This is to
* get localized bitmaps for example.
*/
#include "msrle_En.rc"
#include "msrle_De.rc"
#include "msrle_Fr.rc"
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment