Release 0.3.0

Fri Sep  3 11:52:18 1993  Bob Amstadt

	* [windows/timer.c]
	Changed to use CallWindowProc() rather directly calling callback.

	* [windows/event.c]
	Implemented SetCapture() and ReleaseCapture()

	* [windows/keyboard.c]
	Created stub for GetKeyState()

	* [objects/linedda.c]
	Created stub for LineDDA()

	* [if1632/callback.c]
	Created callback handler for LineDDA callback procedure.

	* [if1632/callback.c]
	Created FreeProcInstance()

Fri Sep  3 08:36:52 1993  David Metcalfe

	* [loader/signal.c]
	Patch to and code for INT 1A

Thu Sep  2 00:31:54 1993  Alexandre Julliard

	* [objects/font.c] [objects/text.c]
	More text support: implemented justification and underlining.

	* [windows/clipping.c] [objects/clipping.c]
	Moved low-level clipping functions to objects/clipping.c.

	* [windows/clipping.c] [windows/event.c] [windows/message.c]
	Implemented window update regions.

	* [windows/dc.c] [objects/dcvalues.c]
	Moved some device-independent DC functions to objects/dcvalues.c.

	* [windows/graphics.c]
	Implemented InvertRect() and GetPixel().

Sat Aug 28 08:40:23 1993  Eric Youngdale

	* [include/neexe.h] [loader/wine.c]
	Added code to handle relocation type 4.

	* [loader/signal.h] [loader/wine.c] [loader/selector.c]
	Added support for dos interrupts.

Thu 26 Aug 19:15:00 1993  Eric Youngdale

	* [loader/selector.c]
	Fixed bug dealing with loading DLLs.

Thu Aug 26 19:22:40 1993  Alexandre Julliard

        * [include/gdi.h] [objects/font.c] [windows/dc.c]
        Beginning of real font support.

        * [windows/graphics.c]
        Implemented PatBlt().

        * [memory/global.c]
        Corrected a bug with linked list handling in GlobalAlloc().

        * [objects/bitmap.c]
        Corrected a bug in BITMAP_SelectObject().

Tue Aug 24 19:22:40 1993  David Metcalfe

        * [controls/Command*] [controls/Label*] [controls[MenuButto*]
	  [controls/SmeMenuButt*]
	Change code to support & as a special character in menu item text.

Tue Aug 24 19:22:40 1993  Alexandre Julliard

	* [include/gdi.h] [windows/dc.c]
	Heavily modified the DC structure for better device-independence.

	* [objects/bitmap.c]
	Implemented bitmap dimensions.

	* [windows/dc.c] [windows/dce.c]
	Implemented DC state saving and restoring.

	* [windows/dc.c]
	Implemented ROP mode.

	* [windows/graphics.c]
	Implemented FillRect().

Mon Aug 23 22:08:34 1993  Bob Amstadt  (bob at pooh)

	* [misc/xt.c]
	Fixed bug in InvalidateRect().  Solitaire attempted to
	clear window before it was realized.

	* [loader/resource.c]
	Began rewrite of LoadBitmap().

	* [loader/wine.c]
	Fixed code which set Argv and Argc global variables.

	* [loader/selector.c]
	Added code to set up command line arguments.

	* [include/neexe.h]
	Fixed error in PSP structure.

Tue Aug 17 20:41:12 1993  Alexandre Julliard

	* [include/gdi.h] [windows/dc.c]
	Implemented device capabilities.

	* [objects/region.c]
	Implemented EqualRgn() and CombineRgn().

	* [windows/clipping.c]
	Implemented Save/RestoreVisRgn().

	* [windows/graphics.c]
	Implemented PaintRgn() and FillRgn().

	* [windows/mapping.c]
	Implemented mapping modes.

Tue Aug 10 14:07:38 1993  Alexandre Julliard

	* [if1632/user.spec] [misc/rect.c]
	Implemented rectangle API functions.

	* [if1632/gdi.spec] [include/gdi.h] [objects/region.c]
	Implemented regions.

	* [windows/class.c]
	Corrected a typo in UnregisterClass().

	* [windows/clipping.c] [windows/dc.c]
	Implemented DC clipping and visible region.

Tue Aug 10 20:57:56 1993  Bob Amstadt  (bob at pooh)

	* [controls/menu.c] [windows/win.c]
	SetMenu(), GetMenu(), CheckMenuItem() implemented

Thu Aug  5 22:33:22 1993  Bob Amstadt  (bob at pooh)

	* [controls/menu.c] [windows/win.c]
	Many improvements menus.  LoadMenu() should work.

Wed Aug  4 14:55:36 1993  Alexandre Julliard

        * [objects/dib.c]
        Started the implementation of device-independent bitmaps.

        * [objects/bitmap.c]
        Added support for multiple bitmap depths.

        * [objects/brush.c]
        Implemented pattern brushes.

        * [windows/dc.c] [windows/graphics.c]
        Implemented some GDI graphics primitives.

Tue Aug  3 21:16:47 1993  Bob Amstadt  (bob at pooh)

	* [controls/menu.c] [windows/win.c] [include/menu.h]
	Code to load class menus from executable file.

	* [if1632/user.spec]
	Fixed specification of SendMessage() and PostMessage.

Mon Jul 26 21:53:24 1993  Alexandre Julliard

	* [if1632/call.S]
	Corrected a bug in KERNEL_InitTask().

	* [include/windows.h]
	Added a lot of constants.

	* [loader/selector.c]
	Corrected a bug in segment allocation in CreateSelectors().

	* [objects/bitmap.c]
	Implemented SelectObject() for bitmaps.

	* [objects/brush.c]
	Implemented hatched brushes and SelectObject().

	* [objects/gdiobj.c]
	Removed linked list (not needed).

	* [objects/palette.c]
	Implemented system palette creation and misc. palette API functions.

	* [windows/timer.c]
	Implemented timers.

	* [windows/dc.c]
	Implemented memory device contexts.

Tue Jul 20 10:38:59 1993  Bob Amstadt  (bob at pooh)

        * [dos.c]
	Split DOS3Call() out of kernel.c.  Added support for get date
	and time functions.

	* [call.S]
	Added function ReturnFromRegisterFunc() to allow DOS calls
	to return values in registers.

	* [regfunc.h]
	Macros to access registers saved on stack.

Tue Jul 20 10:38:59 1993  Alexandre Julliard

        * [win.c]
        Corrected allocation of the WM_CREATE data structure.

        * [dce.c] [dce.h]
        Implemented DCE handling.

        * [bitmap.c] [brush.c] [dc.c] [font.c] [gdi.h] [gdi.spec] 
          [gdiobj.c] [palette.c] [pen.c]
        Implemented the GDI objects data structures and allocation.

        * [windows.h]
        Added several structures and constants for GDI objects.

Mon Jul 19 12:51:10 1993  Bob Amstadt  (bob at pooh)

	* [ldtlib.c]
	Modified system calls to match Linus' new interface for
	the LDT modification.

	* [win.c]
	Fixed bug with WM_CREATE message.

	* [heap.c] [kernel.spec]
	Completed local heap allocation functions.

	* [global.c]
	Created function GlobalQuickAlloc() for easy allocation from DLLs
This commit is contained in:
Alexandre Julliard 1993-09-04 10:09:32 +00:00
parent 75a839a0c0
commit 401710d757
109 changed files with 13913 additions and 961 deletions

1419
ALPHA-diffs Normal file

File diff suppressed because it is too large Load Diff

1
BUGS Normal file
View File

@ -0,0 +1 @@
- EBP and ESP are sometimes corrupted while running 16-bit code.

245
ChangeLog
View File

@ -1,3 +1,248 @@
Fri Sep 3 11:52:18 1993 Bob Amstadt
* [windows/timer.c]
Changed to use CallWindowProc() rather directly calling callback.
* [windows/event.c]
Implemented SetCapture() and ReleaseCapture()
* [windows/keyboard.c]
Created stub for GetKeyState()
* [objects/linedda.c]
Created stub for LineDDA()
* [if1632/callback.c]
Created callback handler for LineDDA callback procedure.
* [if1632/callback.c]
Created FreeProcInstance()
Fri Sep 3 08:36:52 1993 David Metcalfe
* [loader/signal.c]
Patch to and code for INT 1A
Thu Sep 2 00:31:54 1993 Alexandre Julliard
* [objects/font.c] [objects/text.c]
More text support: implemented justification and underlining.
* [windows/clipping.c] [objects/clipping.c]
Moved low-level clipping functions to objects/clipping.c.
* [windows/clipping.c] [windows/event.c] [windows/message.c]
Implemented window update regions.
* [windows/dc.c] [objects/dcvalues.c]
Moved some device-independent DC functions to objects/dcvalues.c.
* [windows/graphics.c]
Implemented InvertRect() and GetPixel().
Sat Aug 28 08:40:23 1993 Eric Youngdale
* [include/neexe.h] [loader/wine.c]
Added code to handle relocation type 4.
* [loader/signal.h] [loader/wine.c] [loader/selector.c]
Added support for dos interrupts.
Thu 26 Aug 19:15:00 1993 Eric Youngdale
* [loader/selector.c]
Fixed bug dealing with loading DLLs.
Thu Aug 26 19:22:40 1993 Alexandre Julliard
* [include/gdi.h] [objects/font.c] [windows/dc.c]
Beginning of real font support.
* [windows/graphics.c]
Implemented PatBlt().
* [memory/global.c]
Corrected a bug with linked list handling in GlobalAlloc().
* [objects/bitmap.c]
Corrected a bug in BITMAP_SelectObject().
Tue Aug 24 19:22:40 1993 David Metcalfe
* [controls/Command*] [controls/Label*] [controls[MenuButto*]
[controls/SmeMenuButt*]
Change code to support & as a special character in menu item text.
Tue Aug 24 19:22:40 1993 Alexandre Julliard
* [include/gdi.h] [windows/dc.c]
Heavily modified the DC structure for better device-independence.
* [objects/bitmap.c]
Implemented bitmap dimensions.
* [windows/dc.c] [windows/dce.c]
Implemented DC state saving and restoring.
* [windows/dc.c]
Implemented ROP mode.
* [windows/graphics.c]
Implemented FillRect().
Mon Aug 23 22:08:34 1993 Bob Amstadt (bob at pooh)
* [misc/xt.c]
Fixed bug in InvalidateRect(). Solitaire attempted to
clear window before it was realized.
* [loader/resource.c]
Began rewrite of LoadBitmap().
* [loader/wine.c]
Fixed code which set Argv and Argc global variables.
* [loader/selector.c]
Added code to set up command line arguments.
* [include/neexe.h]
Fixed error in PSP structure.
Tue Aug 17 20:41:12 1993 Alexandre Julliard
* [include/gdi.h] [windows/dc.c]
Implemented device capabilities.
* [objects/region.c]
Implemented EqualRgn() and CombineRgn().
* [windows/clipping.c]
Implemented Save/RestoreVisRgn().
* [windows/graphics.c]
Implemented PaintRgn() and FillRgn().
* [windows/mapping.c]
Implemented mapping modes.
Tue Aug 10 14:07:38 1993 Alexandre Julliard
* [if1632/user.spec] [misc/rect.c]
Implemented rectangle API functions.
* [if1632/gdi.spec] [include/gdi.h] [objects/region.c]
Implemented regions.
* [windows/class.c]
Corrected a typo in UnregisterClass().
* [windows/clipping.c] [windows/dc.c]
Implemented DC clipping and visible region.
Tue Aug 10 20:57:56 1993 Bob Amstadt (bob at pooh)
* [controls/menu.c] [windows/win.c]
SetMenu(), GetMenu(), CheckMenuItem() implemented
Thu Aug 5 22:33:22 1993 Bob Amstadt (bob at pooh)
* [controls/menu.c] [windows/win.c]
Many improvements menus. LoadMenu() should work.
Wed Aug 4 14:55:36 1993 Alexandre Julliard
* [objects/dib.c]
Started the implementation of device-independent bitmaps.
* [objects/bitmap.c]
Added support for multiple bitmap depths.
* [objects/brush.c]
Implemented pattern brushes.
* [windows/dc.c] [windows/graphics.c]
Implemented some GDI graphics primitives.
Tue Aug 3 21:16:47 1993 Bob Amstadt (bob at pooh)
* [controls/menu.c] [windows/win.c] [include/menu.h]
Code to load class menus from executable file.
* [if1632/user.spec]
Fixed specification of SendMessage() and PostMessage.
Mon Jul 26 21:53:24 1993 Alexandre Julliard
* [if1632/call.S]
Corrected a bug in KERNEL_InitTask().
* [include/windows.h]
Added a lot of constants.
* [loader/selector.c]
Corrected a bug in segment allocation in CreateSelectors().
* [objects/bitmap.c]
Implemented SelectObject() for bitmaps.
* [objects/brush.c]
Implemented hatched brushes and SelectObject().
* [objects/gdiobj.c]
Removed linked list (not needed).
* [objects/palette.c]
Implemented system palette creation and misc. palette API functions.
* [windows/timer.c]
Implemented timers.
* [windows/dc.c]
Implemented memory device contexts.
Tue Jul 20 10:38:59 1993 Bob Amstadt (bob at pooh)
* [dos.c]
Split DOS3Call() out of kernel.c. Added support for get date
and time functions.
* [call.S]
Added function ReturnFromRegisterFunc() to allow DOS calls
to return values in registers.
* [regfunc.h]
Macros to access registers saved on stack.
Tue Jul 20 10:38:59 1993 Alexandre Julliard
* [win.c]
Corrected allocation of the WM_CREATE data structure.
* [dce.c] [dce.h]
Implemented DCE handling.
* [bitmap.c] [brush.c] [dc.c] [font.c] [gdi.h] [gdi.spec]
[gdiobj.c] [palette.c] [pen.c]
Implemented the GDI objects data structures and allocation.
* [windows.h]
Added several structures and constants for GDI objects.
Mon Jul 19 12:51:10 1993 Bob Amstadt (bob at pooh)
* [ldtlib.c]
Modified system calls to match Linus' new interface for
the LDT modification.
* [win.c]
Fixed bug with WM_CREATE message.
* [heap.c] [kernel.spec]
Completed local heap allocation functions.
* [global.c]
Created function GlobalQuickAlloc() for easy allocation from DLLs
Tue Jul 13 20:31:31 1993 Bob Amstadt (bob at pooh) Tue Jul 13 20:31:31 1993 Bob Amstadt (bob at pooh)
* [global.c] * [global.c]

View File

@ -1,64 +1,33 @@
CFLAGS=-g -DDEBUG_RESOURCE -I./ ######################################################################
# These variables are inherited by the sub-makefiles
DEBUGOPTS=
COPTS=-O2 -m486
INCLUDE_DIR=include
###################################################################### ######################################################################
# FILES: # These definitions are for the top level
#
# Be very careful if you change the order of the files listed
# here. if1632.o must linked first to guarrantee that it sits at a low
# enough address. I intend to change this requirement someday, but
# for now live with it.
#
DLL_LENGTH=256
BUILDOBJS=dll_kernel.o dll_user.o dll_gdi.o dll_unixlib.o \
dll_win87em.o dll_shell.o \
dll_kernel_tab.o dll_user_tab.o dll_gdi_tab.o dll_unixlib_tab.o \
dll_win87em_tab.o dll_shell_tab.o
MUST_BE_LINKED_FIRST=if1632.o $(BUILDOBJS)
OBJS=$(MUST_BE_LINKED_FIRST) \
callback.o dump.o global.o heap.o ldt.o kernel.o relay.o resource.o \
selector.o message.o user.o wine.o class.o win.o widgets.o event.o xt.o
TARGET=wine TARGET=wine
LIBS=-L. -L/usr/X386/lib -lldt -lXt -lX11 LIBS=-L. -L/usr/X386/lib -lXext -lXaw -lXt -lXmu -lX11 -lm
OBJS=if1632/if1632.o controls/controls.o loader/loader.o \
memory/memory.o misc/misc.o objects/objects.o windows/windows.o
SUBDIRS=if1632 controls loader memory misc objects windows
all: $(TARGET) all: $(TARGET)
dummy:
clean: clean:
rm -f *.o *~ *.s dll_* *.a rm -f *~ *.o
@for i in tools $(SUBDIRS); do (cd $$i && $(MAKE) clean) || exit; done
ci: $(TARGET): dummy
ci Makefile README *.c *.h *.S build-spec.txt *.spec @for i in tools $(SUBDIRS); \
do (cd $$i && echo $$i && $(MAKE) INCLUDE_DIR=../$(INCLUDE_DIR) \
$(TARGET): $(OBJS) libldt.a COPTS="$(COPTS)" DEBUGOPTS="$(DEBUGOPTS)") || exit; done
$(CC) $(LDFLAGS) -o $(TARGET) $(OBJS) $(LIBS) $(CC) $(LDFLAGS) -o $(TARGET) $(OBJS) $(LIBS)
build: build.c depend:
cc -g -o build build.c @for i in tools $(SUBDIRS); \
do (cd $$i && echo $$i && \
libldt.a: ldtlib.c $(MAKE) INCLUDE_DIR=../$(INCLUDE_DIR) depend) \
$(CC) -O6 -c ldtlib.c || exit; done
ar rcs libldt.a ldtlib.o
dll_kernel.S dll_kernel_tab.c: build kernel.spec
build kernel.spec
dll_user.S dll_user_tab.c: build user.spec
build user.spec
dll_gdi.S dll_gdi_tab.c: build gdi.spec
build gdi.spec
dll_unixlib.S dll_unixlib_tab.c: build unixlib.spec
build unixlib.spec
dll_win87em.S dll_win87em_tab.c: build win87em.spec
build win87em.spec
dll_shell.S dll_shell_tab.c: build shell.spec
build shell.spec
wintcl.o: wintcl.c windows.h
cc -c -I. -g wintcl.c

94
README
View File

@ -2,10 +2,70 @@ Copyright Robert J. Amstadt, 1993. All code is provided without
warranty. It is my intent to cover this code with the Gnu Public warranty. It is my intent to cover this code with the Gnu Public
License. License.
So here goes release 0.2.0 of the Windows loader. It will do some INSTALLATION:
relocations and then run the program. I have successfully loaded
the Windows solitaire game. Try it. It currently stops a call to Uncompress and untar this archive into the directory of your
GetObject(). choice. This release requires a Linux version 0.99 pl12 kernel with
ALPHA-diffs and sognal-diffs. Apply ALPHA-diffs first, and then
signal-diffs.
To build Wine, first do a "make depend" and then a "make". The
executable "wine" will be built.
WHAT'S NEW with version 0.3.0: (see ChangeLog for details)
- Mouse capture
- Text justification and underlining
- Clipping
- LoadBitmap() completed
- Code generated by the Borland compiler should now work
WHAT'S NEW with version 0.2.8: (see ChangeLog for details)
- Text functions from Alexandre
- INT 21h from Eric
- Menu improvements from David
- Bug fixes and GetProcAddress() stub from me
WHAT'S NEW with version 0.2.7: (see ChangeLog for details)
- sol.exe gets further. I did some debugging and now solitaire
stops when it tries to call GetTextExtent(). Any volunteers?
- Many DC updates from Alexandre.
- Menu updates to support underlining characters from David Metcalfe.
WHAT'S NEW with version 0.2.6: (see ChangeLog for details)
- More region updates from Alexandre
WHAT'S NEW with version 0.2.5: (see ChangeLog for details)
- Regions implemented by Alexandre
- More menuing code from me
WHAT'S NEW with version 0.2.4: (see ChangeLog for details)
- Many improvements to GDI from Alexandre
- Many improvements to menu handling by me.
WHAT'S NEW with version 0.2.3: (see ChangeLog for details)
- Bug fixes with SendMessage() and PostMessage()
- Preliminary menu support
WHAT'S NEW with version 0.2.2: (see ChangeLog for details)
- Misc bug fixes
- More bitmap code
- Timers
- Memory DC's
WHAT'S NEW with version 0.2.1:
- I have placed things into sub-directories. The organization is
not finalized. I imagine that the directory structure will
change as is necessary. Files in the ./misc directory need
to be split apart and placed in apropriate directories.
- Tons of code from Alexandre. He has constructed the framework
for handling GDI objects. He has also provided code for DCEs.
- Local heap functions have been completed.
- Bug fixes in global.c and win.c
- New function GlobalQuickAlloc() combines GlobalAlloc() and
GlobalLock() into a single function call.
- New patch kit for Linux 0.99 pl11 kernel. Thanks to Linus
who has graciously included our patches into the ALPHA patch
release cycle.
WHAT'S NEW with version 0.2.0: WHAT'S NEW with version 0.2.0:
- Alexandre Julliard has provided a replacement for the Tcl code. - Alexandre Julliard has provided a replacement for the Tcl code.
@ -76,33 +136,9 @@ TODO:
- GlobalAlloc of code segments. - GlobalAlloc of code segments.
- Rewrite global memory support including kernel mods to allow - Rewrite global memory support including kernel mods to allow
application to mess with page map. application to mess with page map.
- complete and improve local heap allocation.
- Handle self-loading applications. - Handle self-loading applications.
- Resource loading - Resource loading
- Lots and lots of API fiunctions.
INSTALLATION:
Uncompress and untar this archive into the directory of your
choice. The file "ldt.tar" contains a necessary kernel patch against
Linux 0.99.10. "ldt.tar" is unchanged from the version released
with release 0.0.2. In the directory /usr/src/linux (or whereever
you keep your kernel sources), untar this file it contains three files:
kernel/ldt.c
- This is source for a new system call.
include/linux/ldt.h
- This contains structures defining the system call
interface.
ldt.patch
- This is a patch that must be applied to the kernel.
It updates two header files, and the kernel Makefile.
Or follow the same procedure with "ldt512.tar". This file contains
Eric Youngdales patches for ALPHA-pl11. These patches give the
emulator 512 ldt entries instead of the 32 available with the older
patch kit.
BUILD: BUILD:

19
controls/Makefile Normal file
View File

@ -0,0 +1,19 @@
CFLAGS=$(COPTS) $(DEBUGOPTS) -I$(INCLUDE_DIR)
OBJS=menu.o widgets.o SmeMenuButto.o WinLabel.o WinCommand.o WinMenuButto.o
# WinButton.o
default: controls.o
controls.o: $(OBJS)
$(LD) -r -o controls.o $(OBJS)
clean:
rm -f *.o *~ *.s dll_* *.a
depend:
$(CC) $(CFLAGS) -M *.c > .depend
ifeq (.depend,$(wildcard .depend))
include .depend
endif

117
controls/SmeMenuButtP.h Normal file
View File

@ -0,0 +1,117 @@
/*
* $XConsortium: SmeMenuButtP.h,v 1.6 89/12/11 15:20:15 kit Exp $
*
* Copyright 1989 Massachusetts Institute of Technology
*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, provided that
* the above copyright notice appear in all copies and that both that
* copyright notice and this permission notice appear in supporting
* documentation, and that the name of M.I.T. not be used in advertising or
* publicity pertaining to distribution of the software without specific,
* written prior permission. M.I.T. makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
* BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*
* Author: Chris D. Peterson, MIT X Consortium
*
* Modifications for Wine
*
* 8/23/93 David Metcalfe (david@prism.demon.co.uk)
* Added code to translate ampersand to underlined char
*/
/*
* SmeP.h - Private definitions for Sme object
*
*/
#ifndef _XawSmeMenuButtP_h
#define _XawSmeMenuButtP_h
/***********************************************************************
*
* Sme Object Private Data
*
***********************************************************************/
#include <X11/Xaw/SmeP.h>
#include "SmeMenuButto.h"
/************************************************************
*
* New fields for the Sme Object class record.
*
************************************************************/
typedef struct _SmeMenuButtonClassPart {
XtPointer extension;
} SmeMenuButtonClassPart;
/* Full class record declaration */
typedef struct _SmeMenuButtonClassRec {
RectObjClassPart rect_class;
SmeClassPart sme_class;
SmeMenuButtonClassPart sme_bsb_class;
} SmeMenuButtonClassRec;
extern SmeMenuButtonClassRec smeMenuButtonClassRec;
/* New fields for the Sme Object record */
typedef struct {
/* resources */
String label; /* The entry label. */
int vert_space; /* extra vert space to leave, as a percentage
of the font height of the label. */
Pixmap left_bitmap, right_bitmap; /* bitmaps to show. */
Dimension left_margin, right_margin; /* left and right margins. */
Pixel foreground; /* foreground color. */
XFontStruct * font; /* The font to show label in. */
XtJustify justify; /* Justification for the label. */
String menu_name; /* Menu to activate */
Boolean inactive; /* True if can't be selected */
/* private resources. */
Boolean set_values_area_cleared; /* Remember if we need to unhighlight. */
GC norm_gc; /* noral color gc. */
GC rev_gc; /* reverse color gc. */
GC norm_gray_gc; /* Normal color (grayed out) gc. */
GC invert_gc; /* gc for flipping colors. */
Dimension left_bitmap_width; /* size of each bitmap. */
Dimension left_bitmap_height;
Dimension right_bitmap_width;
Dimension right_bitmap_height;
int ul_pos; /* Offset in chars of underlined character */
/* in label */
} SmeMenuButtonPart;
/****************************************************************
*
* Full instance record declaration
*
****************************************************************/
typedef struct _SmeMenuButtonRec {
ObjectPart object;
RectObjPart rectangle;
SmePart sme;
SmeMenuButtonPart sme_bsb;
} SmeMenuButtonRec;
/************************************************************
*
* Private declarations.
*
************************************************************/
#endif /* _XawSmeMenuButtP_h */

758
controls/SmeMenuButto.c Normal file
View File

@ -0,0 +1,758 @@
/* $XConsortium: SmeMenuButton.c,v 1.16 91/03/15 15:59:41 gildea Exp $ */
/*
* Copyright 1989 Massachusetts Institute of Technology
*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, provided that
* the above copyright notice appear in all copies and that both that
* copyright notice and this permission notice appear in supporting
* documentation, and that the name of M.I.T. not be used in advertising or
* publicity pertaining to distribution of the software without specific,
* written prior permission. M.I.T. makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
* BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/*
* SmeMenuButton.c - Source code file for BSB Menu Entry object.
*
* Date: September 26, 1989
*
* By: Chris D. Peterson
* MIT X Consortium
* kit@expo.lcs.mit.edu
*
* Modifications for Wine
*
* 8/23/93 David Metcalfe (david@prism.demon.co.uk)
* Added code to translate ampersand to underlined char
*/
#include <X11/IntrinsicP.h>
#include <X11/StringDefs.h>
#include <X11/Xos.h>
#include <X11/Xmu/Drawing.h>
#include <X11/Xaw/XawInit.h>
#include <X11/Xaw/SimpleMenu.h>
#include "SmeMenuButtP.h"
#include <X11/Xaw/Cardinals.h>
#include <stdio.h>
#define ONE_HUNDRED 100
#define offset(field) XtOffsetOf(SmeMenuButtonRec, sme_bsb.field)
static XtResource resources[] = {
{XtNlabel, XtCLabel, XtRString, sizeof(String),
offset(label), XtRString, NULL},
{XtNvertSpace, XtCVertSpace, XtRInt, sizeof(int),
offset(vert_space), XtRImmediate, (XtPointer) 25},
{XtNleftBitmap, XtCLeftBitmap, XtRBitmap, sizeof(Pixmap),
offset(left_bitmap), XtRImmediate, (XtPointer)None},
{XtNjustify, XtCJustify, XtRJustify, sizeof(XtJustify),
offset(justify), XtRImmediate, (XtPointer) XtJustifyLeft},
{XtNrightBitmap, XtCRightBitmap, XtRBitmap, sizeof(Pixmap),
offset(right_bitmap), XtRImmediate, (XtPointer)None},
{XtNleftMargin, XtCHorizontalMargins, XtRDimension, sizeof(Dimension),
offset(left_margin), XtRImmediate, (XtPointer) 15},
{XtNrightMargin, XtCHorizontalMargins, XtRDimension, sizeof(Dimension),
offset(right_margin), XtRImmediate, (XtPointer) 5},
{XtNforeground, XtCForeground, XtRPixel, sizeof(Pixel),
offset(foreground), XtRString, XtDefaultForeground},
{XtNfont, XtCFont, XtRFontStruct, sizeof(XFontStruct *),
offset(font), XtRString, XtDefaultFont},
{XtNmenuName, XtCMenuName, XtRString, sizeof(String),
offset(menu_name), XtRString, (XtPointer) NULL},
{XtNinactive, XtCInactive, XtRBoolean, sizeof(Boolean),
offset(inactive), XtRImmediate, (XtPointer) FALSE },
};
#undef offset
/*
* Semi Public function definitions.
*/
static void Redisplay(), Destroy(), Initialize(), FlipColors();
static void ClassInitialize();
static void PopupMenu(), Unhighlight();
static Boolean SetValues();
static XtGeometryResult QueryGeometry();
/*
* Private Function Definitions.
*/
static void GetDefaultSize(), DrawBitmaps(), GetBitmapInfo();
static void CreateGCs(), DestroyGCs();
static void RemoveAmpersand();
#define superclass (&smeClassRec)
SmeMenuButtonClassRec smeMenuButtonClassRec = {
{
/* superclass */ (WidgetClass) superclass,
/* class_name */ "SmeMenuButton",
/* size */ sizeof(SmeMenuButtonRec),
/* class_initializer */ ClassInitialize,
/* class_part_initialize*/ NULL,
/* Class init'ed */ FALSE,
/* initialize */ Initialize,
/* initialize_hook */ NULL,
/* realize */ NULL,
/* actions */ NULL,
/* num_actions */ ZERO,
/* resources */ resources,
/* resource_count */ XtNumber(resources),
/* xrm_class */ NULLQUARK,
/* compress_motion */ FALSE,
/* compress_exposure */ FALSE,
/* compress_enterleave*/ FALSE,
/* visible_interest */ FALSE,
/* destroy */ Destroy,
/* resize */ NULL,
/* expose */ Redisplay,
/* set_values */ SetValues,
/* set_values_hook */ NULL,
/* set_values_almost */ XtInheritSetValuesAlmost,
/* get_values_hook */ NULL,
/* accept_focus */ NULL,
/* intrinsics version */ XtVersion,
/* callback offsets */ NULL,
/* tm_table */ NULL,
/* query_geometry */ QueryGeometry,
/* display_accelerator*/ NULL,
/* extension */ NULL
},{
/* Menu Entry Fields */
/* highlight */ FlipColors,
/* unhighlight */ Unhighlight,
/* notify */ XtInheritNotify,
/* extension */ NULL
}, {
/* BSB Menu entry Fields */
/* extension */ NULL
}
};
WidgetClass smeMenuButtonObjectClass = (WidgetClass) &smeMenuButtonClassRec;
/************************************************************
*
* Semi-Public Functions.
*
************************************************************/
/* Function Name: ClassInitialize
* Description: Initializes the SmeMenuButtonObject.
* Arguments: none.
* Returns: none.
*/
static void
ClassInitialize()
{
XawInitializeWidgetSet();
XtAddConverter( XtRString, XtRJustify, XmuCvtStringToJustify, NULL, 0 );
}
/* Function Name: Initialize
* Description: Initializes the simple menu widget
* Arguments: request - the widget requested by the argument list.
* new - the new widget with both resource and non
* resource values.
* Returns: none.
*/
/* ARGSUSED */
static void
Initialize(request, new)
Widget request, new;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) new;
if (entry->sme_bsb.label == NULL)
entry->sme_bsb.label = XtName(new);
else
entry->sme_bsb.label = XtNewString( entry->sme_bsb.label );
RemoveAmpersand(new);
GetDefaultSize(new, &(entry->rectangle.width), &(entry->rectangle.height));
CreateGCs(new);
entry->sme_bsb.left_bitmap_width = entry->sme_bsb.left_bitmap_height = 0;
entry->sme_bsb.right_bitmap_width = entry->sme_bsb.right_bitmap_height = 0;
GetBitmapInfo(new, TRUE); /* Left Bitmap Info */
GetBitmapInfo(new, FALSE); /* Right Bitmap Info */
}
/* Function Name: Destroy
* Description: Called at destroy time, cleans up.
* Arguments: w - the simple menu widget.
* Returns: none.
*/
static void
Destroy(w)
Widget w;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
DestroyGCs(w);
if (entry->sme_bsb.label != XtName(w))
XtFree(entry->sme_bsb.label);
}
/* Function Name: Redisplay
* Description: Redisplays the contents of the widget.
* Arguments: w - the simple menu widget.
* event - the X event that caused this redisplay.
* region - the region the needs to be repainted.
* Returns: none.
*/
/* ARGSUSED */
static void
Redisplay(w, event, region)
Widget w;
XEvent * event;
Region region;
{
GC gc;
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
int font_ascent, font_descent, y_loc;
int ul_x_loc, ul_y_loc, ul_width;
entry->sme_bsb.set_values_area_cleared = FALSE;
font_ascent = entry->sme_bsb.font->max_bounds.ascent;
font_descent = entry->sme_bsb.font->max_bounds.descent;
y_loc = entry->rectangle.y;
if (XtIsSensitive(w) && XtIsSensitive( XtParent(w) ) ) {
if ( w == XawSimpleMenuGetActiveEntry(XtParent(w)) ) {
XFillRectangle(XtDisplayOfObject(w), XtWindowOfObject(w),
entry->sme_bsb.norm_gc, 0, y_loc,
(unsigned int) entry->rectangle.width,
(unsigned int) entry->rectangle.height);
gc = entry->sme_bsb.rev_gc;
}
else
gc = entry->sme_bsb.norm_gc;
}
else
gc = entry->sme_bsb.norm_gray_gc;
if (entry->sme_bsb.label != NULL) {
int x_loc = entry->sme_bsb.left_margin;
int len = strlen(entry->sme_bsb.label);
char * label = entry->sme_bsb.label;
switch(entry->sme_bsb.justify) {
int width, t_width;
case XtJustifyCenter:
t_width = XTextWidth(entry->sme_bsb.font, label, len);
width = entry->rectangle.width - (entry->sme_bsb.left_margin +
entry->sme_bsb.right_margin);
x_loc += (width - t_width)/2;
break;
case XtJustifyRight:
t_width = XTextWidth(entry->sme_bsb.font, label, len);
x_loc = entry->rectangle.width - (entry->sme_bsb.right_margin +
t_width);
break;
case XtJustifyLeft:
default:
break;
}
y_loc += ((int)entry->rectangle.height -
(font_ascent + font_descent)) / 2 + font_ascent;
XDrawString(XtDisplayOfObject(w), XtWindowOfObject(w), gc,
x_loc, y_loc, label, len);
if (entry->sme_bsb.ul_pos != -1)
{
ul_x_loc = x_loc + XTextWidth(entry->sme_bsb.font,
entry->sme_bsb.label, entry->sme_bsb.ul_pos);
ul_y_loc = entry->rectangle.y + (entry->rectangle.height +
font_ascent + font_descent) / 2;
ul_width = XTextWidth(entry->sme_bsb.font,
entry->sme_bsb.label + entry->sme_bsb.ul_pos, 1);
XDrawLine(XtDisplayOfObject(w), XtWindowOfObject(w), gc,
ul_x_loc, ul_y_loc, ul_x_loc + ul_width - 1, ul_y_loc);
}
}
DrawBitmaps(w, gc);
}
/* Function Name: SetValues
* Description: Relayout the menu when one of the resources is changed.
* Arguments: current - current state of the widget.
* request - what was requested.
* new - what the widget will become.
* Returns: none
*/
/* ARGSUSED */
static Boolean
SetValues(current, request, new)
Widget current, request, new;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) new;
SmeMenuButtonObject old_entry = (SmeMenuButtonObject) current;
Boolean ret_val = FALSE;
if (old_entry->sme_bsb.label != entry->sme_bsb.label) {
if (old_entry->sme_bsb.label != XtName( new ) )
XtFree( (char *) old_entry->sme_bsb.label );
if (entry->sme_bsb.label != XtName(new) )
entry->sme_bsb.label = XtNewString( entry->sme_bsb.label );
RemoveAmpersand(new);
ret_val = True;
}
if (entry->rectangle.sensitive != old_entry->rectangle.sensitive )
ret_val = TRUE;
if (entry->sme_bsb.left_bitmap != old_entry->sme_bsb.left_bitmap) {
GetBitmapInfo(new, TRUE);
ret_val = TRUE;
}
if (entry->sme_bsb.right_bitmap != old_entry->sme_bsb.right_bitmap) {
GetBitmapInfo(new, FALSE);
ret_val = TRUE;
}
if ( (old_entry->sme_bsb.font != entry->sme_bsb.font) ||
(old_entry->sme_bsb.foreground != entry->sme_bsb.foreground) ) {
DestroyGCs(current);
CreateGCs(new);
ret_val = TRUE;
}
if (ret_val) {
GetDefaultSize(new,
&(entry->rectangle.width), &(entry->rectangle.height));
entry->sme_bsb.set_values_area_cleared = TRUE;
}
return(ret_val);
}
/* Function Name: QueryGeometry.
* Description: Returns the preferred geometry for this widget.
* Arguments: w - the menu entry object.
* itended, return_val - the intended and return geometry info.
* Returns: A Geometry Result.
*
* See the Intrinsics manual for details on what this function is for.
*
* I just return the height and width of the label plus the margins.
*/
static XtGeometryResult
QueryGeometry(w, intended, return_val)
Widget w;
XtWidgetGeometry *intended, *return_val;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
Dimension width, height;
XtGeometryResult ret_val = XtGeometryYes;
XtGeometryMask mode = intended->request_mode;
GetDefaultSize(w, &width, &height );
if ( ((mode & CWWidth) && (intended->width != width)) ||
!(mode & CWWidth) ) {
return_val->request_mode |= CWWidth;
return_val->width = width;
ret_val = XtGeometryAlmost;
}
if ( ((mode & CWHeight) && (intended->height != height)) ||
!(mode & CWHeight) ) {
return_val->request_mode |= CWHeight;
return_val->height = height;
ret_val = XtGeometryAlmost;
}
if (ret_val == XtGeometryAlmost) {
mode = return_val->request_mode;
if ( ((mode & CWWidth) && (width == entry->rectangle.width)) &&
((mode & CWHeight) && (height == entry->rectangle.height)) )
return(XtGeometryNo);
}
return(ret_val);
}
/* Function Name: FlipColors
* Description: Invert the colors of the current entry.
* Arguments: w - the bsb menu entry widget.
* Returns: none.
*/
static void
FlipColors(w)
Widget w;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
if (entry->sme_bsb.set_values_area_cleared || entry->sme_bsb.inactive)
return;
XFillRectangle(XtDisplayOfObject(w), XtWindowOfObject(w),
entry->sme_bsb.invert_gc, 0, (int) entry->rectangle.y,
(unsigned int) entry->rectangle.width,
(unsigned int) entry->rectangle.height);
}
/************************************************************
*
* Private Functions.
*
************************************************************/
/* Function Name: GetDefaultSize
* Description: Calculates the Default (preferred) size of
* this menu entry.
* Arguments: w - the menu entry widget.
* width, height - default sizes (RETURNED).
* Returns: none.
*/
static void
GetDefaultSize(w, width, height)
Widget w;
Dimension * width, * height;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
if (entry->sme_bsb.label == NULL)
*width = 0;
else
*width = XTextWidth(entry->sme_bsb.font, entry->sme_bsb.label,
strlen(entry->sme_bsb.label));
*width += entry->sme_bsb.left_margin + entry->sme_bsb.right_margin;
*height = (entry->sme_bsb.font->max_bounds.ascent +
entry->sme_bsb.font->max_bounds.descent);
*height = ((int)*height * ( ONE_HUNDRED +
entry->sme_bsb.vert_space )) / ONE_HUNDRED;
}
/* Function Name: DrawBitmaps
* Description: Draws left and right bitmaps.
* Arguments: w - the simple menu widget.
* gc - graphics context to use for drawing.
* Returns: none
*/
static void
DrawBitmaps(w, gc)
Widget w;
GC gc;
{
int x_loc, y_loc;
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
if ( (entry->sme_bsb.left_bitmap == None) &&
(entry->sme_bsb.right_bitmap == None) ) return;
/*
* Draw Left Bitmap.
*/
if (entry->sme_bsb.left_bitmap != None) {
x_loc = (int)(entry->sme_bsb.left_margin -
entry->sme_bsb.left_bitmap_width) / 2;
y_loc = entry->rectangle.y + (int)(entry->rectangle.height -
entry->sme_bsb.left_bitmap_height) / 2;
XCopyPlane(XtDisplayOfObject(w), entry->sme_bsb.left_bitmap,
XtWindowOfObject(w), gc, 0, 0,
entry->sme_bsb.left_bitmap_width,
entry->sme_bsb.left_bitmap_height, x_loc, y_loc, 1);
}
/*
* Draw Right Bitmap.
*/
if (entry->sme_bsb.right_bitmap != None) {
x_loc = entry->rectangle.width -
(int)(entry->sme_bsb.right_margin +
entry->sme_bsb.right_bitmap_width) / 2;
y_loc = entry->rectangle.y + (int)(entry->rectangle.height -
entry->sme_bsb.right_bitmap_height) / 2;
XCopyPlane(XtDisplayOfObject(w), entry->sme_bsb.right_bitmap,
XtWindowOfObject(w), gc, 0, 0,
entry->sme_bsb.right_bitmap_width,
entry->sme_bsb.right_bitmap_height, x_loc, y_loc, 1);
}
}
/* Function Name: GetBitmapInfo
* Description: Gets the bitmap information from either of the bitmaps.
* Arguments: w - the bsb menu entry widget.
* is_left - TRUE if we are testing left bitmap,
* FALSE if we are testing the right bitmap.
* Returns: none
*/
static void
GetBitmapInfo(w, is_left)
Widget w;
Boolean is_left;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
unsigned int depth, bw;
Window root;
int x, y;
unsigned int width, height;
char buf[BUFSIZ];
if (is_left) {
if (entry->sme_bsb.left_bitmap != None) {
if (!XGetGeometry(XtDisplayOfObject(w),
entry->sme_bsb.left_bitmap, &root,
&x, &y, &width, &height, &bw, &depth)) {
sprintf(buf, "SmeMenuButton Object: %s %s \"%s\".", "Could not",
"get Left Bitmap geometry information for menu entry ",
XtName(w));
XtAppError(XtWidgetToApplicationContext(w), buf);
}
if (depth != 1) {
sprintf(buf, "SmeMenuButton Object: %s \"%s\"%s.",
"Left Bitmap of entry ",
XtName(w), " is not one bit deep.");
XtAppError(XtWidgetToApplicationContext(w), buf);
}
entry->sme_bsb.left_bitmap_width = (Dimension) width;
entry->sme_bsb.left_bitmap_height = (Dimension) height;
}
}
else if (entry->sme_bsb.right_bitmap != None) {
if (!XGetGeometry(XtDisplayOfObject(w),
entry->sme_bsb.right_bitmap, &root,
&x, &y, &width, &height, &bw, &depth)) {
sprintf(buf, "SmeMenuButton Object: %s %s \"%s\".", "Could not",
"get Right Bitmap geometry information for menu entry ",
XtName(w));
XtAppError(XtWidgetToApplicationContext(w), buf);
}
if (depth != 1) {
sprintf(buf, "SmeMenuButton Object: %s \"%s\"%s.",
"Right Bitmap of entry ", XtName(w),
" is not one bit deep.");
XtAppError(XtWidgetToApplicationContext(w), buf);
}
entry->sme_bsb.right_bitmap_width = (Dimension) width;
entry->sme_bsb.right_bitmap_height = (Dimension) height;
}
}
/* Function Name: CreateGCs
* Description: Creates all gc's for the simple menu widget.
* Arguments: w - the simple menu widget.
* Returns: none.
*/
static void
CreateGCs(w)
Widget w;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
XGCValues values;
XtGCMask mask;
values.foreground = XtParent(w)->core.background_pixel;
values.background = entry->sme_bsb.foreground;
values.font = entry->sme_bsb.font->fid;
values.graphics_exposures = FALSE;
mask = GCForeground | GCBackground | GCFont | GCGraphicsExposures;
entry->sme_bsb.rev_gc = XtGetGC(w, mask, &values);
values.foreground = entry->sme_bsb.foreground;
values.background = XtParent(w)->core.background_pixel;
entry->sme_bsb.norm_gc = XtGetGC(w, mask, &values);
values.fill_style = FillTiled;
values.tile = XmuCreateStippledPixmap(XtScreenOfObject(w),
entry->sme_bsb.foreground,
XtParent(w)->core.background_pixel,
XtParent(w)->core.depth);
values.graphics_exposures = FALSE;
mask |= GCTile | GCFillStyle;
entry->sme_bsb.norm_gray_gc = XtGetGC(w, mask, &values);
values.foreground ^= values.background;
values.background = 0;
values.function = GXxor;
mask = GCForeground | GCBackground | GCGraphicsExposures | GCFunction;
entry->sme_bsb.invert_gc = XtGetGC(w, mask, &values);
}
/* Function Name: DestroyGCs
* Description: Removes all gc's for the simple menu widget.
* Arguments: w - the simple menu widget.
* Returns: none.
*/
static void
DestroyGCs(w)
Widget w;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
XtReleaseGC(w, entry->sme_bsb.norm_gc);
XtReleaseGC(w, entry->sme_bsb.norm_gray_gc);
XtReleaseGC(w, entry->sme_bsb.rev_gc);
XtReleaseGC(w, entry->sme_bsb.invert_gc);
}
static void
PopupMenu(w)
Widget w;
{
SmeMenuButtonObject mbw = (SmeMenuButtonObject) w;
Widget menu, temp;
Arg arglist[2];
Cardinal num_args;
int menu_x, menu_y, menu_width, menu_height, button_width;
Position button_x, button_y;
if (mbw->sme_bsb.menu_name == NULL || strlen(mbw->sme_bsb.menu_name) == 0)
return;
temp = w;
while(temp != NULL) {
menu = XtNameToWidget(temp, mbw->sme_bsb.menu_name);
if (menu == NULL)
temp = XtParent(temp);
else
break;
}
if (menu == NULL) {
char error_buf[BUFSIZ];
sprintf(error_buf, "MenuButton: %s %s.",
"Could not find menu widget named", mbw->sme_bsb.menu_name);
XtAppWarning(XtWidgetToApplicationContext(w), error_buf);
return;
}
if (!XtIsRealized(menu))
XtRealizeWidget(menu);
menu_width = menu->core.width + 2 * menu->core.border_width;
button_width = mbw->rectangle.width + 2 * mbw->rectangle.border_width;
menu_height = menu->core.height + 2 * menu->core.border_width;
XtTranslateCoords(w, 0, 0, &button_x, &button_y);
menu_x = button_x + button_width;
menu_y = button_y;
if (menu_x >= 0) {
int scr_width = WidthOfScreen(XtScreen(menu));
if (menu_x + menu_width > scr_width)
menu_x = scr_width - menu_width;
}
if (menu_x < 0)
menu_x = 0;
if (menu_y >= 0) {
int scr_height = HeightOfScreen(XtScreen(menu));
if (menu_y + menu_height > scr_height)
menu_y = scr_height - menu_height;
}
if (menu_y < 0)
menu_y = 0;
num_args = 0;
XtSetArg(arglist[num_args], XtNx, menu_x); num_args++;
XtSetArg(arglist[num_args], XtNy, menu_y); num_args++;
XtSetValues(menu, arglist, num_args);
XtPopupSpringLoaded(menu);
}
static void
Unhighlight(w)
Widget w;
{
SmeMenuButtonObject mbw = (SmeMenuButtonObject) w;
Display *display;
Screen *screen;
Window win, rootwin;
int rootwin_x, rootwin_y;
int win_x, win_y;
unsigned int mask;
Position left, right, top, bottom;
if (mbw->sme_bsb.inactive)
return;
display = XtDisplayOfObject(w);
screen = XtScreenOfObject(w);
XQueryPointer(display, RootWindowOfScreen(screen),
&rootwin, &win, &rootwin_x, &rootwin_y,
&win_x, &win_y, &mask);
XtTranslateCoords(w, 0, 0, &left, &top);
XtTranslateCoords(w, mbw->rectangle.width, mbw->rectangle.height,
&right, &bottom);
if (rootwin_x >= right && rootwin_y >= top && rootwin_y < bottom)
{
PopupMenu(w);
}
FlipColors(w);
}
static void
RemoveAmpersand(w)
Widget w;
{
SmeMenuButtonObject entry = (SmeMenuButtonObject) w;
entry->sme_bsb.ul_pos = strcspn(entry->sme_bsb.label, "&");
if (entry->sme_bsb.ul_pos == strlen(entry->sme_bsb.label))
{
entry->sme_bsb.ul_pos = -1;
return;
}
/* Remove ampersand from label */
strcpy(entry->sme_bsb.label + entry->sme_bsb.ul_pos,
entry->sme_bsb.label + entry->sme_bsb.ul_pos + 1);
}

100
controls/SmeMenuButto.h Normal file
View File

@ -0,0 +1,100 @@
/*
* $XConsortium: SmeMenuButton.h,v 1.5 89/12/11 15:20:14 kit Exp $
*
* Copyright 1989 Massachusetts Institute of Technology
*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, provided that
* the above copyright notice appear in all copies and that both that
* copyright notice and this permission notice appear in supporting
* documentation, and that the name of M.I.T. not be used in advertising or
* publicity pertaining to distribution of the software without specific,
* written prior permission. M.I.T. makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
* BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/*
* SmeMenuButton.h - Public Header file for SmeMenuButton object.
*
* This is the public header file for the Athena BSB Sme object.
* It is intended to be used with the simple menu widget. This object
* provides bitmap - string - bitmap style entries.
*
* Date: April 3, 1989
*
* By: Chris D. Peterson
* MIT X Consortium
* kit@expo.lcs.mit.edu
*
* Modifications for Wine
*
* 8/23/93 David Metcalfe (david@prism.demon.co.uk)
* Added code to translate ampersand to underlined char
*/
#ifndef _SmeMenuButto_h
#define _SmeMenuButto_h
#include <X11/Xmu/Converters.h>
#include <X11/Xaw/Sme.h>
/****************************************************************
*
* SmeMenuButton object
*
****************************************************************/
/* BSB Menu Entry Resources:
Name Class RepType Default Value
---- ----- ------- -------------
callback Callback Callback NULL
destroyCallback Callback Pointer NULL
font Font XFontStruct * XtDefaultFont
foreground Foreground Pixel XtDefaultForeground
height Height Dimension 0
label Label String Name of entry
leftBitmap LeftBitmap Pixmap None
leftMargin HorizontalMargins Dimension 4
rightBitmap RightBitmap Pixmap None
rightMargin HorizontalMargins Dimension 4
sensitive Sensitive Boolean True
vertSpace VertSpace int 25
width Width Dimension 0
x Position Position 0n
y Position Position 0
menuName MenuName String "menu"
inactive Inactive Boolean False
*/
typedef struct _SmeMenuButtonClassRec *SmeMenuButtonObjectClass;
typedef struct _SmeMenuButtonRec *SmeMenuButtonObject;
extern WidgetClass smeMenuButtonObjectClass;
#define XtNleftBitmap "leftBitmap"
#define XtNleftMargin "leftMargin"
#define XtNrightBitmap "rightBitmap"
#define XtNrightMargin "rightMargin"
#define XtNvertSpace "vertSpace"
#define XtNmenuName "menuName"
#define XtNinactive "inactive"
#define XtCLeftBitmap "LeftBitmap"
#define XtCHorizontalMargins "HorizontalMargins"
#define XtCRightBitmap "RightBitmap"
#define XtCVertSpace "VertSpace"
#define XtCMenuName "MenuName"
#define XtCInactive "Inactive"
#endif /* _SmeMenuButto_h */

567
controls/WinCommand.c Normal file
View File

@ -0,0 +1,567 @@
/***********************************************************
Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
Permission to use, copy, modify, and distribute this software and its
documentation for any purpose and without fee is hereby granted,
provided that the above copyright notice appear in all copies and that
both that copyright notice and this permission notice appear in
supporting documentation, and that the names of Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
******************************************************************/
/*
* Modifications for Wine
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinCommand
*/
/*
* WinCommand.c - WinCommand button widget
*/
#include <stdio.h>
#include <X11/IntrinsicP.h>
#include <X11/StringDefs.h>
#include <X11/Xmu/Misc.h>
#include <X11/Xaw/XawInit.h>
#include "WinCommandP.h"
#include <X11/Xmu/Converters.h>
#define DEFAULT_HIGHLIGHT_THICKNESS 2
#define DEFAULT_SHAPE_HIGHLIGHT 32767
/****************************************************************
*
* Full class record constant
*
****************************************************************/
/* Private Data */
static char defaultTranslations[] =
"<EnterWindow>: highlight() \n\
<LeaveWindow>: reset() \n\
<Btn1Down>: set() \n\
<Btn1Up>: notify() unset() ";
#define offset(field) XtOffsetOf(WinCommandRec, field)
static XtResource resources[] = {
{XtNcallback, XtCCallback, XtRCallback, sizeof(XtPointer),
offset(wincommand.callbacks), XtRCallback, (XtPointer)NULL},
{XtNhighlightThickness, XtCThickness, XtRDimension, sizeof(Dimension),
offset(wincommand.highlight_thickness), XtRImmediate,
(XtPointer) DEFAULT_SHAPE_HIGHLIGHT},
{XtNshapeStyle, XtCShapeStyle, XtRShapeStyle, sizeof(int),
offset(wincommand.shape_style), XtRImmediate,
(XtPointer)XawShapeRectangle},
{XtNcornerRoundPercent, XtCCornerRoundPercent,
XtRDimension, sizeof(Dimension),
offset(wincommand.corner_round), XtRImmediate, (XtPointer) 25},
};
#undef offset
static Boolean SetValues();
static void Initialize(), Redisplay(), Set(), Reset(), Notify(), Unset();
static void Highlight(), Unhighlight(), Destroy(), PaintWinCommandWidget();
static void ClassInitialize();
static Boolean ShapeButton();
static void Realize(), Resize();
static XtActionsRec actionsList[] = {
{"set", Set},
{"notify", Notify},
{"highlight", Highlight},
{"reset", Reset},
{"unset", Unset},
{"unhighlight", Unhighlight}
};
#define SuperClass ((WinLabelWidgetClass)&winLabelClassRec)
WinCommandClassRec winCommandClassRec = {
{
(WidgetClass) SuperClass, /* superclass */
"WinCommand", /* class_name */
sizeof(WinCommandRec), /* size */
ClassInitialize, /* class_initialize */
NULL, /* class_part_initialize */
FALSE, /* class_inited */
Initialize, /* initialize */
NULL, /* initialize_hook */
Realize, /* realize */
actionsList, /* actions */
XtNumber(actionsList), /* num_actions */
resources, /* resources */
XtNumber(resources), /* resource_count */
NULLQUARK, /* xrm_class */
FALSE, /* compress_motion */
TRUE, /* compress_exposure */
TRUE, /* compress_enterleave */
FALSE, /* visible_interest */
Destroy, /* destroy */
Resize, /* resize */
Redisplay, /* expose */
SetValues, /* set_values */
NULL, /* set_values_hook */
XtInheritSetValuesAlmost, /* set_values_almost */
NULL, /* get_values_hook */
NULL, /* accept_focus */
XtVersion, /* version */
NULL, /* callback_private */
defaultTranslations, /* tm_table */
XtInheritQueryGeometry, /* query_geometry */
XtInheritDisplayAccelerator, /* display_accelerator */
NULL /* extension */
}, /* CoreClass fields initialization */
{
XtInheritChangeSensitive /* change_sensitive */
}, /* SimpleClass fields initialization */
{
0, /* field not used */
}, /* WinLabelClass fields initialization */
{
0, /* field not used */
}, /* WinCommandClass fields initialization */
};
/* for public consumption */
WidgetClass winCommandWidgetClass = (WidgetClass) &winCommandClassRec;
/****************************************************************
*
* Private Procedures
*
****************************************************************/
static GC
Get_GC(cbw, fg, bg)
WinCommandWidget cbw;
Pixel fg, bg;
{
XGCValues values;
values.foreground = fg;
values.background = bg;
values.font = cbw->winlabel.font->fid;
values.cap_style = CapProjecting;
if (cbw->wincommand.highlight_thickness > 1 )
values.line_width = cbw->wincommand.highlight_thickness;
else
values.line_width = 0;
return XtGetGC((Widget)cbw,
(GCForeground|GCBackground|GCFont|GCLineWidth|GCCapStyle),
&values);
}
/* ARGSUSED */
static void
Initialize(request, new, args, num_args)
Widget request, new;
ArgList args; /* unused */
Cardinal *num_args; /* unused */
{
WinCommandWidget cbw = (WinCommandWidget) new;
int shape_event_base, shape_error_base;
if (cbw->wincommand.shape_style != XawShapeRectangle
&& !XShapeQueryExtension(XtDisplay(new), &shape_event_base,
&shape_error_base))
cbw->wincommand.shape_style = XawShapeRectangle;
if (cbw->wincommand.highlight_thickness == DEFAULT_SHAPE_HIGHLIGHT) {
if (cbw->wincommand.shape_style != XawShapeRectangle)
cbw->wincommand.highlight_thickness = 0;
else
cbw->wincommand.highlight_thickness = DEFAULT_HIGHLIGHT_THICKNESS;
}
cbw->wincommand.normal_GC = Get_GC(cbw, cbw->winlabel.foreground,
cbw->core.background_pixel);
cbw->wincommand.inverse_GC = Get_GC(cbw, cbw->core.background_pixel,
cbw->winlabel.foreground);
XtReleaseGC(new, cbw->winlabel.normal_GC);
cbw->winlabel.normal_GC = cbw->wincommand.normal_GC;
cbw->wincommand.set = FALSE;
cbw->wincommand.highlighted = HighlightNone;
}
static Region
HighlightRegion(cbw)
WinCommandWidget cbw;
{
static Region outerRegion = NULL, innerRegion, emptyRegion;
XRectangle rect;
if (cbw->wincommand.highlight_thickness == 0 ||
cbw->wincommand.highlight_thickness >
(Dimension) ((Dimension) Min(cbw->core.width, cbw->core.height)/2))
return(NULL);
if (outerRegion == NULL) {
/* save time by allocating scratch regions only once. */
outerRegion = XCreateRegion();
innerRegion = XCreateRegion();
emptyRegion = XCreateRegion();
}
rect.x = rect.y = 0;
rect.width = cbw->core.width;
rect.height = cbw->core.height;
XUnionRectWithRegion( &rect, emptyRegion, outerRegion );
rect.x = rect.y = cbw->wincommand.highlight_thickness;
rect.width -= cbw->wincommand.highlight_thickness * 2;
rect.height -= cbw->wincommand.highlight_thickness * 2;
XUnionRectWithRegion( &rect, emptyRegion, innerRegion );
XSubtractRegion( outerRegion, innerRegion, outerRegion );
return outerRegion;
}
/***************************
*
* Action Procedures
*
***************************/
/* ARGSUSED */
static void
Set(w,event,params,num_params)
Widget w;
XEvent *event;
String *params; /* unused */
Cardinal *num_params; /* unused */
{
WinCommandWidget cbw = (WinCommandWidget)w;
if (cbw->wincommand.set)
return;
cbw->wincommand.set= TRUE;
if (XtIsRealized(w))
PaintWinCommandWidget(w, (Region) NULL, TRUE);
}
/* ARGSUSED */
static void
Unset(w,event,params,num_params)
Widget w;
XEvent *event;
String *params; /* unused */
Cardinal *num_params;
{
WinCommandWidget cbw = (WinCommandWidget)w;
if (!cbw->wincommand.set)
return;
cbw->wincommand.set = FALSE;
if (XtIsRealized(w)) {
XClearWindow(XtDisplay(w), XtWindow(w));
PaintWinCommandWidget(w, (Region) NULL, TRUE);
}
}
/* ARGSUSED */
static void
Reset(w,event,params,num_params)
Widget w;
XEvent *event;
String *params; /* unused */
Cardinal *num_params; /* unused */
{
WinCommandWidget cbw = (WinCommandWidget)w;
if (cbw->wincommand.set) {
cbw->wincommand.highlighted = HighlightNone;
Unset(w, event, params, num_params);
}
else
Unhighlight(w, event, params, num_params);
}
/* ARGSUSED */
static void
Highlight(w,event,params,num_params)
Widget w;
XEvent *event;
String *params;
Cardinal *num_params;
{
WinCommandWidget cbw = (WinCommandWidget)w;
if ( *num_params == (Cardinal) 0)
cbw->wincommand.highlighted = HighlightWhenUnset;
else {
if ( *num_params != (Cardinal) 1)
XtWarning("Too many parameters passed to highlight action table.");
switch (params[0][0]) {
case 'A':
case 'a':
cbw->wincommand.highlighted = HighlightAlways;
break;
default:
cbw->wincommand.highlighted = HighlightWhenUnset;
break;
}
}
if (XtIsRealized(w))
PaintWinCommandWidget(w, HighlightRegion(cbw), TRUE);
}
/* ARGSUSED */
static void
Unhighlight(w,event,params,num_params)
Widget w;
XEvent *event;
String *params; /* unused */
Cardinal *num_params; /* unused */
{
WinCommandWidget cbw = (WinCommandWidget)w;
cbw->wincommand.highlighted = HighlightNone;
if (XtIsRealized(w))
PaintWinCommandWidget(w, HighlightRegion(cbw), TRUE);
}
/* ARGSUSED */
static void
Notify(w,event,params,num_params)
Widget w;
XEvent *event;
String *params; /* unused */
Cardinal *num_params; /* unused */
{
WinCommandWidget cbw = (WinCommandWidget)w;
/* check to be sure state is still Set so that user can cancel
the action (e.g. by moving outside the window, in the default
bindings.
*/
if (cbw->wincommand.set)
XtCallCallbackList(w, cbw->wincommand.callbacks, NULL);
}
/*
* Repaint the widget window
*/
/************************
*
* REDISPLAY (DRAW)
*
************************/
/* ARGSUSED */
static void
Redisplay(w, event, region)
Widget w;
XEvent *event;
Region region;
{
PaintWinCommandWidget(w, region, FALSE);
}
/* Function Name: PaintWinCommandWidget
* Description: Paints the wincommand widget.
* Arguments: w - the wincommand widget.
* region - region to paint (passed to the superclass).
* change - did it change either set or highlight state?
* Returns: none
*/
static void
PaintWinCommandWidget(w, region, change)
Widget w;
Region region;
Boolean change;
{
WinCommandWidget cbw = (WinCommandWidget) w;
Boolean very_thick;
GC norm_gc, rev_gc;
very_thick = cbw->wincommand.highlight_thickness >
(Dimension)((Dimension) Min(cbw->core.width,
cbw->core.height)/2);
if (cbw->wincommand.set) {
cbw->winlabel.normal_GC = cbw->wincommand.inverse_GC;
XFillRectangle(XtDisplay(w), XtWindow(w), cbw->wincommand.normal_GC,
0, 0, cbw->core.width, cbw->core.height);
region = NULL; /* Force label to repaint text. */
}
else
cbw->winlabel.normal_GC = cbw->wincommand.normal_GC;
if (cbw->wincommand.highlight_thickness <= 0)
{
(*SuperClass->core_class.expose) (w, (XEvent *) NULL, region);
return;
}
/*
* If we are set then use the same colors as if we are not highlighted.
*/
if (cbw->wincommand.set == (cbw->wincommand.highlighted == HighlightNone)) {
norm_gc = cbw->wincommand.inverse_GC;
rev_gc = cbw->wincommand.normal_GC;
}
else {
norm_gc = cbw->wincommand.normal_GC;
rev_gc = cbw->wincommand.inverse_GC;
}
if ( !( (!change && (cbw->wincommand.highlighted == HighlightNone)) ||
((cbw->wincommand.highlighted == HighlightWhenUnset) &&
(cbw->wincommand.set))) ) {
if (very_thick) {
cbw->winlabel.normal_GC = norm_gc; /* Give the label the right GC. */
XFillRectangle(XtDisplay(w),XtWindow(w), rev_gc,
0, 0, cbw->core.width, cbw->core.height);
}
else {
/* wide lines are centered on the path, so indent it */
int offset = cbw->wincommand.highlight_thickness/2;
XDrawRectangle(XtDisplay(w),XtWindow(w), rev_gc, offset, offset,
cbw->core.width - cbw->wincommand.highlight_thickness,
cbw->core.height - cbw->wincommand.highlight_thickness);
}
}
(*SuperClass->core_class.expose) (w, (XEvent *) NULL, region);
}
static void
Destroy(w)
Widget w;
{
WinCommandWidget cbw = (WinCommandWidget) w;
/* so WinLabel can release it */
if (cbw->winlabel.normal_GC == cbw->wincommand.normal_GC)
XtReleaseGC( w, cbw->wincommand.inverse_GC );
else
XtReleaseGC( w, cbw->wincommand.normal_GC );
}
/*
* Set specified arguments into widget
*/
/* ARGSUSED */
static Boolean
SetValues (current, request, new)
Widget current, request, new;
{
WinCommandWidget oldcbw = (WinCommandWidget) current;
WinCommandWidget cbw = (WinCommandWidget) new;
Boolean redisplay = False;
if ( oldcbw->core.sensitive != cbw->core.sensitive && !cbw->core.sensitive) {
/* about to become insensitive */
cbw->wincommand.set = FALSE;
cbw->wincommand.highlighted = HighlightNone;
redisplay = TRUE;
}
if ( (oldcbw->winlabel.foreground != cbw->winlabel.foreground) ||
(oldcbw->core.background_pixel != cbw->core.background_pixel) ||
(oldcbw->wincommand.highlight_thickness !=
cbw->wincommand.highlight_thickness) ||
(oldcbw->winlabel.font != cbw->winlabel.font) )
{
if (oldcbw->winlabel.normal_GC == oldcbw->wincommand.normal_GC)
/* WinLabel has release one of these */
XtReleaseGC(new, cbw->wincommand.inverse_GC);
else
XtReleaseGC(new, cbw->wincommand.normal_GC);
cbw->wincommand.normal_GC = Get_GC(cbw, cbw->winlabel.foreground,
cbw->core.background_pixel);
cbw->wincommand.inverse_GC = Get_GC(cbw, cbw->core.background_pixel,
cbw->winlabel.foreground);
XtReleaseGC(new, cbw->winlabel.normal_GC);
cbw->winlabel.normal_GC = (cbw->wincommand.set
? cbw->wincommand.inverse_GC
: cbw->wincommand.normal_GC);
redisplay = True;
}
if ( XtIsRealized(new)
&& oldcbw->wincommand.shape_style != cbw->wincommand.shape_style
&& !ShapeButton(cbw, TRUE))
{
cbw->wincommand.shape_style = oldcbw->wincommand.shape_style;
}
return (redisplay);
}
static void ClassInitialize()
{
XawInitializeWidgetSet();
XtSetTypeConverter( XtRString, XtRShapeStyle, XmuCvtStringToShapeStyle,
NULL, 0, XtCacheNone, NULL );
}
static Boolean
ShapeButton(cbw, checkRectangular)
WinCommandWidget cbw;
Boolean checkRectangular;
{
Dimension corner_size;
if ( (cbw->wincommand.shape_style == XawShapeRoundedRectangle) ) {
corner_size = (cbw->core.width < cbw->core.height) ? cbw->core.width
: cbw->core.height;
corner_size = (int) (corner_size * cbw->wincommand.corner_round) / 100;
}
if (checkRectangular || cbw->wincommand.shape_style != XawShapeRectangle) {
if (!XmuReshapeWidget((Widget) cbw, cbw->wincommand.shape_style,
corner_size, corner_size)) {
cbw->wincommand.shape_style = XawShapeRectangle;
return(False);
}
}
return(TRUE);
}
static void Realize(w, valueMask, attributes)
Widget w;
Mask *valueMask;
XSetWindowAttributes *attributes;
{
(*winCommandWidgetClass->core_class.superclass->core_class.realize)
(w, valueMask, attributes);
ShapeButton( (WinCommandWidget) w, FALSE);
}
static void Resize(w)
Widget w;
{
if (XtIsRealized(w))
ShapeButton( (WinCommandWidget) w, FALSE);
(*winCommandWidgetClass->core_class.superclass->core_class.resize)(w);
}

100
controls/WinCommand.h Normal file
View File

@ -0,0 +1,100 @@
/***********************************************************
Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
Permission to use, copy, modify, and distribute this software and its
documentation for any purpose and without fee is hereby granted,
provided that the above copyright notice appear in all copies and that
both that copyright notice and this permission notice appear in
supporting documentation, and that the names of Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
******************************************************************/
/*
* Modifications for Wine
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinCommand
*/
#ifndef _WinCommand_h
#define _WinCommand_h
#include "WinLabel.h"
/* Command widget resources:
Name Class RepType Default Value
---- ----- ------- -------------
accelerators Accelerators AcceleratorTable NULL
ancestorSensitive AncestorSensitive Boolean True
background Background Pixel XtDefaultBackground
backgroundPixmap Pixmap Pixmap XtUnspecifiedPixmap
bitmap Pixmap Pixmap None
borderColor BorderColor Pixel XtDefaultForeground
borderPixmap Pixmap Pixmap XtUnspecifiedPixmap
borderWidth BorderWidth Dimension 1
callback Callback XtCallbackList NULL
colormap Colormap Colormap parent's colormap
cornerRoundPercent CornerRoundPercent Dimension 25
cursor Cursor Cursor None
cursorName Cursor String NULL
depth Depth int parent's depth
destroyCallback Callback XtCallbackList NULL
encoding Encoding UnsignedChar XawTextEncoding8bit
font Font XFontStruct* XtDefaultFont
foreground Foreground Pixel XtDefaultForeground
height Height Dimension text height
highlightThickness Thickness Dimension 0 if shaped, else 2
insensitiveBorder Insensitive Pixmap Gray
internalHeight Height Dimension 2
internalWidth Width Dimension 4
justify Justify XtJustify XtJustifyCenter
label Label String NULL
leftBitmap LeftBitmap Pixmap None
mappedWhenManaged MappedWhenManaged Boolean True
pointerColor Foreground Pixel XtDefaultForeground
pointerColorBackground Background Pixel XtDefaultBackground
resize Resize Boolean True
screen Screen Screen parent's Screen
sensitive Sensitive Boolean True
shapeStyle ShapeStyle ShapeStyle Rectangle
translations Translations TranslationTable see doc or source
width Width Dimension text width
x Position Position 0
y Position Position 0
*/
#define XtNhighlightThickness "highlightThickness"
#define XtNshapeStyle "shapeStyle"
#define XtCShapeStyle "ShapeStyle"
#define XtRShapeStyle "ShapeStyle"
#define XtNcornerRoundPercent "cornerRoundPercent"
#define XtCCornerRoundPercent "CornerRoundPercent"
#define XawShapeRectangle XmuShapeRectangle
#define XawShapeOval XmuShapeOval
#define XawShapeEllipse XmuShapeEllipse
#define XawShapeRoundedRectangle XmuShapeRoundedRectangle
extern WidgetClass winCommandWidgetClass;
typedef struct _WinCommandClassRec *WinCommandWidgetClass;
typedef struct _WinCommandRec *WinCommandWidget;
#endif /* _WinCommand_h */
/* DON'T ADD STUFF AFTER THIS */

118
controls/WinCommandP.h Normal file
View File

@ -0,0 +1,118 @@
/***********************************************************
Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
Permission to use, copy, modify, and distribute this software and its
documentation for any purpose and without fee is hereby granted,
provided that the above copyright notice appear in all copies and that
both that copyright notice and this permission notice appear in
supporting documentation, and that the names of Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
******************************************************************/
/*
* Modifications for Wine
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Convrted to WinCommand
*/
/*
* WinCommandP.h - Private definitions for WinCommand widget
*
*/
#ifndef _WinCommandP_h
#define _WinCommandP_h
#include "WinCommand.h"
#include "WinLabelP.h"
/***********************************************************************
*
* WinCommand Widget Private Data
*
***********************************************************************/
typedef enum {
HighlightNone, /* Do not highlight. */
HighlightWhenUnset, /* Highlight only when unset, this is
to preserve current command widget
functionality. */
HighlightAlways /* Always highlight, lets the toggle widget
and other subclasses do the right thing. */
} XtCommandHighlight;
/************************************
*
* Class structure
*
***********************************/
/* New fields for the WinCommand widget class record */
typedef struct _WinCommandClass
{
int makes_compiler_happy; /* not used */
} WinCommandClassPart;
/* Full class record declaration */
typedef struct _WinCommandClassRec {
CoreClassPart core_class;
SimpleClassPart simple_class;
WinLabelClassPart winlabel_class;
WinCommandClassPart wincommand_class;
} WinCommandClassRec;
extern WinCommandClassRec winCommandClassRec;
/***************************************
*
* Instance (widget) structure
*
**************************************/
/* New fields for the WinCommand widget record */
typedef struct {
/* resources */
Dimension highlight_thickness;
XtCallbackList callbacks;
/* private state */
Pixmap gray_pixmap;
GC normal_GC;
GC inverse_GC;
Boolean set;
XtCommandHighlight highlighted;
/* more resources */
int shape_style;
Dimension corner_round;
} WinCommandPart;
/* XtEventsPtr eventTable;*/
/* Full widget declaration */
typedef struct _WinCommandRec {
CorePart core;
SimplePart simple;
WinLabelPart winlabel;
WinCommandPart wincommand;
} WinCommandRec;
#endif /* _WinCommandP_h */

691
controls/WinLabel.c Normal file
View File

@ -0,0 +1,691 @@
/***********************************************************
Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
Permission to use, copy, modify, and distribute this software and its
documentation for any purpose and without fee is hereby granted,
provided that the above copyright notice appear in all copies and that
both that copyright notice and this permission notice appear in
supporting documentation, and that the names of Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
******************************************************************/
/*
* Modifications for Wine
*
* 8/23/93 David Metcalfe (david@prism.demon.co.uk)
* Added code to translate ampersand to underlined char
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinLabel
*/
/*
* WinLabel.c - WinLabel widget
*
*/
#include <X11/IntrinsicP.h>
#include <X11/StringDefs.h>
#include <X11/Xos.h>
#include <X11/Xaw/XawInit.h>
#include "WinLabelP.h"
#include <X11/Xmu/Converters.h>
#include <X11/Xmu/Drawing.h>
#include <stdio.h>
#include <ctype.h>
#define streq(a,b) (strcmp( (a), (b) ) == 0)
#define MULTI_LINE_LABEL 32767
#ifdef CRAY
#define WORD64
#endif
/****************************************************************
*
* Full class record constant
*
****************************************************************/
/* Private Data */
#define offset(field) XtOffsetOf(WinLabelRec, field)
static XtResource resources[] = {
{XtNforeground, XtCForeground, XtRPixel, sizeof(Pixel),
offset(winlabel.foreground), XtRString, XtDefaultForeground},
{XtNfont, XtCFont, XtRFontStruct, sizeof(XFontStruct *),
offset(winlabel.font),XtRString, XtDefaultFont},
{XtNlabel, XtCLabel, XtRString, sizeof(String),
offset(winlabel.label), XtRString, NULL},
{XtNencoding, XtCEncoding, XtRUnsignedChar, sizeof(unsigned char),
offset(winlabel.encoding), XtRImmediate,
(XtPointer)XawTextEncoding8bit},
{XtNjustify, XtCJustify, XtRJustify, sizeof(XtJustify),
offset(winlabel.justify), XtRImmediate, (XtPointer)XtJustifyCenter},
{XtNinternalWidth, XtCWidth, XtRDimension, sizeof(Dimension),
offset(winlabel.internal_width), XtRImmediate, (XtPointer)4},
{XtNinternalHeight, XtCHeight, XtRDimension, sizeof(Dimension),
offset(winlabel.internal_height), XtRImmediate, (XtPointer)4},
{XtNleftBitmap, XtCLeftBitmap, XtRBitmap, sizeof(Pixmap),
offset(winlabel.left_bitmap), XtRImmediate, (XtPointer) None},
{XtNbitmap, XtCPixmap, XtRBitmap, sizeof(Pixmap),
offset(winlabel.pixmap), XtRImmediate, (XtPointer)None},
{XtNresize, XtCResize, XtRBoolean, sizeof(Boolean),
offset(winlabel.resize), XtRImmediate, (XtPointer)True},
};
#undef offset
static void Initialize();
static void Resize();
static void Redisplay();
static Boolean SetValues();
static void ClassInitialize();
static void Destroy();
static XtGeometryResult QueryGeometry();
WinLabelClassRec winLabelClassRec = {
{
/* core_class fields */
#define superclass (&simpleClassRec)
/* superclass */ (WidgetClass) superclass,
/* class_name */ "WinLabel",
/* widget_size */ sizeof(WinLabelRec),
/* class_initialize */ ClassInitialize,
/* class_part_initialize */ NULL,
/* class_inited */ FALSE,
/* initialize */ Initialize,
/* initialize_hook */ NULL,
/* realize */ XtInheritRealize,
/* actions */ NULL,
/* num_actions */ 0,
/* resources */ resources,
/* num_resources */ XtNumber(resources),
/* xrm_class */ NULLQUARK,
/* compress_motion */ TRUE,
/* compress_exposure */ TRUE,
/* compress_enterleave */ TRUE,
/* visible_interest */ FALSE,
/* destroy */ Destroy,
/* resize */ Resize,
/* expose */ Redisplay,
/* set_values */ SetValues,
/* set_values_hook */ NULL,
/* set_values_almost */ XtInheritSetValuesAlmost,
/* get_values_hook */ NULL,
/* accept_focus */ NULL,
/* version */ XtVersion,
/* callback_private */ NULL,
/* tm_table */ NULL,
/* query_geometry */ QueryGeometry,
/* display_accelerator */ XtInheritDisplayAccelerator,
/* extension */ NULL
},
/* Simple class fields initialization */
{
/* change_sensitive */ XtInheritChangeSensitive
}
};
WidgetClass winLabelWidgetClass = (WidgetClass)&winLabelClassRec;
/****************************************************************
*
* Private Procedures
*
****************************************************************/
static void ClassInitialize()
{
XawInitializeWidgetSet();
XtAddConverter( XtRString, XtRJustify, XmuCvtStringToJustify, NULL, 0 );
}
#ifndef WORD64
#define TXT16 XChar2b
#else
#define TXT16 char
static XChar2b *buf2b;
static int buf2blen = 0;
_WinLabelWidth16(fs, str, n)
XFontStruct *fs;
char *str;
int n;
{
int i;
XChar2b *ptr;
if (n > buf2blen) {
buf2b = (XChar2b *)XtRealloc((char *)buf2b, n * sizeof(XChar2b));
buf2blen = n;
}
for (ptr = buf2b, i = n; --i >= 0; ptr++) {
ptr->byte1 = *str++;
ptr->byte2 = *str++;
}
return XTextWidth16(fs, buf2b, n);
}
_WinLabelDraw16(dpy, d, gc, x, y, str, n)
Display *dpy;
Drawable d;
GC gc;
int x, y;
char *str;
int n;
{
int i;
XChar2b *ptr;
if (n > buf2blen) {
buf2b = (XChar2b *)XtRealloc((char *)buf2b, n * sizeof(XChar2b));
buf2blen = n;
}
for (ptr = buf2b, i = n; --i >= 0; ptr++) {
ptr->byte1 = *str++;
ptr->byte2 = *str++;
}
XDrawString16(dpy, d, gc, x, y, buf2b, n);
}
#define XTextWidth16 _WinLabelWidth16
#define XDrawString16 _WinLabelDraw16
#endif /* WORD64 */
/*
* Calculate width and height of displayed text in pixels
*/
static void SetTextWidthAndHeight(lw)
WinLabelWidget lw;
{
register XFontStruct *fs = lw->winlabel.font;
char *nl;
if (lw->winlabel.pixmap != None) {
Window root;
int x, y;
unsigned int width, height, bw, depth;
if (XGetGeometry(XtDisplay(lw), lw->winlabel.pixmap, &root, &x, &y,
&width, &height, &bw, &depth)) {
lw->winlabel.label_height = height;
lw->winlabel.label_width = width;
lw->winlabel.label_len = depth;
return;
}
}
lw->winlabel.label_height = fs->max_bounds.ascent + fs->max_bounds.descent;
if (lw->winlabel.label == NULL) {
lw->winlabel.label_len = 0;
lw->winlabel.label_width = 0;
}
else if ((nl = index(lw->winlabel.label, '\n')) != NULL) {
char *label;
lw->winlabel.label_len = MULTI_LINE_LABEL;
lw->winlabel.label_width = 0;
for (label = lw->winlabel.label; nl != NULL; nl = index(label, '\n')) {
int width;
if (lw->winlabel.encoding)
width = XTextWidth16(fs, (TXT16*)label, (int)(nl - label)/2);
else
width = XTextWidth(fs, label, (int)(nl - label));
if (width > (int)lw->winlabel.label_width)
lw->winlabel.label_width = width;
label = nl + 1;
if (*label)
lw->winlabel.label_height +=
fs->max_bounds.ascent + fs->max_bounds.descent;
}
if (*label) {
int width = XTextWidth(fs, label, strlen(label));
if (lw->winlabel.encoding)
width = XTextWidth16(fs, (TXT16*)label, (int)strlen(label)/2);
else
width = XTextWidth(fs, label, strlen(label));
if (width > (int) lw->winlabel.label_width)
lw->winlabel.label_width = width;
}
} else {
lw->winlabel.label_len = strlen(lw->winlabel.label);
if (lw->winlabel.encoding)
lw->winlabel.label_width =
XTextWidth16(fs, (TXT16*)lw->winlabel.label,
(int) lw->winlabel.label_len/2);
else
lw->winlabel.label_width =
XTextWidth(fs, lw->winlabel.label,
(int) lw->winlabel.label_len);
}
}
static void GetnormalGC(lw)
WinLabelWidget lw;
{
XGCValues values;
values.foreground = lw->winlabel.foreground;
values.background = lw->core.background_pixel;
values.font = lw->winlabel.font->fid;
values.graphics_exposures = False;
lw->winlabel.normal_GC = XtGetGC(
(Widget)lw,
(unsigned) GCForeground | GCBackground | GCFont | GCGraphicsExposures,
&values);
}
static void GetgrayGC(lw)
WinLabelWidget lw;
{
XGCValues values;
values.foreground = lw->winlabel.foreground;
values.background = lw->core.background_pixel;
values.font = lw->winlabel.font->fid;
values.fill_style = FillTiled;
values.tile = XmuCreateStippledPixmap(XtScreen((Widget)lw),
lw->winlabel.foreground,
lw->core.background_pixel,
lw->core.depth);
values.graphics_exposures = False;
lw->winlabel.stipple = values.tile;
lw->winlabel.gray_GC = XtGetGC((Widget)lw,
(unsigned) GCForeground | GCBackground |
GCFont | GCTile | GCFillStyle |
GCGraphicsExposures,
&values);
}
static void compute_bitmap_offsets (lw)
WinLabelWidget lw;
{
/*
* label will be displayed at (internal_width, internal_height + lbm_y)
*/
if (lw->winlabel.lbm_height != 0) {
lw->winlabel.lbm_y = (((int) lw->core.height) -
((int) lw->winlabel.internal_height * 2) -
((int) lw->winlabel.lbm_height)) / 2;
} else {
lw->winlabel.lbm_y = 0;
}
}
static void set_bitmap_info (lw)
WinLabelWidget lw;
{
Window root;
int x, y;
unsigned int bw, depth;
if (!(lw->winlabel.left_bitmap &&
XGetGeometry (XtDisplay(lw), lw->winlabel.left_bitmap, &root, &x, &y,
&lw->winlabel.lbm_width, &lw->winlabel.lbm_height,
&bw, &depth))) {
lw->winlabel.lbm_width = lw->winlabel.lbm_height = 0;
}
compute_bitmap_offsets (lw);
}
static void
RemoveAmpersand(w)
Widget w;
{
WinLabelWidget lw = (WinLabelWidget) w;
lw->winlabel.ul_pos = strcspn(lw->winlabel.label, "&");
if (lw->winlabel.ul_pos == strlen(lw->winlabel.label))
{
lw->winlabel.ul_pos = -1;
return;
}
/* Remove ampersand from label */
strcpy(lw->winlabel.label + lw->winlabel.ul_pos,
lw->winlabel.label + lw->winlabel.ul_pos + 1);
}
/* ARGSUSED */
static void Initialize(request, new)
Widget request, new;
{
WinLabelWidget lw = (WinLabelWidget) new;
if (lw->winlabel.label == NULL)
lw->winlabel.label = XtNewString(lw->core.name);
else {
lw->winlabel.label = XtNewString(lw->winlabel.label);
}
RemoveAmpersand(new);
GetnormalGC(lw);
GetgrayGC(lw);
SetTextWidthAndHeight(lw);
if (lw->core.height == 0)
lw->core.height = lw->winlabel.label_height +
2*lw->winlabel.internal_height;
set_bitmap_info (lw); /* need core.height */
if (lw->core.width == 0) /* need winlabel.lbm_width */
lw->core.width = (lw->winlabel.label_width +
2 * lw->winlabel.internal_width
+ LEFT_OFFSET(lw));
lw->winlabel.label_x = lw->winlabel.label_y = 0;
(*XtClass(new)->core_class.resize) ((Widget)lw);
} /* Initialize */
/*
* Repaint the widget window
*/
/* ARGSUSED */
static void Redisplay(w, event, region)
Widget w;
XEvent *event;
Region region;
{
WinLabelWidget lw = (WinLabelWidget) w;
GC gc;
int ul_x_loc, ul_y_loc, ul_width;
if (region != NULL) {
int x = lw->winlabel.label_x;
unsigned int width = lw->winlabel.label_width;
if (lw->winlabel.lbm_width) {
if (lw->winlabel.label_x > (x = lw->winlabel.internal_width))
width += lw->winlabel.label_x - x;
}
if (XRectInRegion(region, x, lw->winlabel.label_y,
width, lw->winlabel.label_height) == RectangleOut)
return;
}
gc = XtIsSensitive((Widget)lw) ? lw->winlabel.normal_GC
: lw->winlabel.gray_GC;
#ifdef notdef
if (region != NULL) XSetRegion(XtDisplay(w), gc, region);
#endif /*notdef*/
if (lw->winlabel.pixmap == None) {
int len = lw->winlabel.label_len;
char *label = lw->winlabel.label;
Position y = lw->winlabel.label_y +
lw->winlabel.font->max_bounds.ascent;
/* display left bitmap */
if (lw->winlabel.left_bitmap && lw->winlabel.lbm_width != 0) {
XCopyPlane (XtDisplay(w), lw->winlabel.left_bitmap, XtWindow(w), gc,
0, 0, lw->winlabel.lbm_width, lw->winlabel.lbm_height,
(int) lw->winlabel.internal_width,
(int) lw->winlabel.internal_height +
lw->winlabel.lbm_y,
(unsigned long) 1L);
}
if (len == MULTI_LINE_LABEL) {
char *nl;
while ((nl = index(label, '\n')) != NULL) {
if (lw->winlabel.encoding)
XDrawString16(XtDisplay(w), XtWindow(w), gc,
lw->winlabel.label_x, y,
(TXT16*)label, (int)(nl - label)/2);
else
XDrawString(XtDisplay(w), XtWindow(w), gc,
lw->winlabel.label_x, y, label,
(int)(nl - label));
y += lw->winlabel.font->max_bounds.ascent +
lw->winlabel.font->max_bounds.descent;
label = nl + 1;
}
len = strlen(label);
}
if (len) {
if (lw->winlabel.encoding)
XDrawString16(XtDisplay(w), XtWindow(w), gc,
lw->winlabel.label_x, y, (TXT16*)label, len/2);
else
XDrawString(XtDisplay(w), XtWindow(w), gc,
lw->winlabel.label_x, y, label, len);
if (lw->winlabel.ul_pos != -1)
{
/* Don't bother with two byte chars at present */
if (!lw->winlabel.encoding)
{
ul_x_loc = lw->winlabel.label_x +
XTextWidth(lw->winlabel.font,
lw->winlabel.label, lw->winlabel.ul_pos);
ul_y_loc = lw->winlabel.label_height +
lw->winlabel.internal_height + 1;
ul_width = XTextWidth(lw->winlabel.font,
lw->winlabel.label + lw->winlabel.ul_pos, 1);
XDrawLine(XtDisplayOfObject(w), XtWindowOfObject(w), gc,
ul_x_loc, ul_y_loc, ul_x_loc + ul_width - 1, ul_y_loc);
}
}
}
} else if (lw->winlabel.label_len == 1) { /* depth */
XCopyPlane(XtDisplay(w), lw->winlabel.pixmap, XtWindow(w), gc,
0, 0, lw->winlabel.label_width, lw->winlabel.label_height,
lw->winlabel.label_x, lw->winlabel.label_y, 1L);
} else {
XCopyArea(XtDisplay(w), lw->winlabel.pixmap, XtWindow(w), gc,
0, 0, lw->winlabel.label_width, lw->winlabel.label_height,
lw->winlabel.label_x, lw->winlabel.label_y);
}
#ifdef notdef
if (region != NULL) XSetClipMask(XtDisplay(w), gc, (Pixmap)None);
#endif /* notdef */
}
static void _Reposition(lw, width, height, dx, dy)
register WinLabelWidget lw;
Dimension width, height;
Position *dx, *dy;
{
Position newPos;
Position leftedge = lw->winlabel.internal_width + LEFT_OFFSET(lw);
switch (lw->winlabel.justify) {
case XtJustifyLeft :
newPos = leftedge;
break;
case XtJustifyRight :
newPos = width -
(lw->winlabel.label_width + lw->winlabel.internal_width);
break;
case XtJustifyCenter :
default:
newPos = (int)(width - lw->winlabel.label_width) / 2;
break;
}
if (newPos < (Position)leftedge)
newPos = leftedge;
*dx = newPos - lw->winlabel.label_x;
lw->winlabel.label_x = newPos;
*dy = (newPos = (int)(height - lw->winlabel.label_height) / 2)
- lw->winlabel.label_y;
lw->winlabel.label_y = newPos;
return;
}
static void Resize(w)
Widget w;
{
WinLabelWidget lw = (WinLabelWidget)w;
Position dx, dy;
_Reposition(lw, w->core.width, w->core.height, &dx, &dy);
compute_bitmap_offsets (lw);
}
/*
* Set specified arguments into widget
*/
#define PIXMAP 0
#define WIDTH 1
#define HEIGHT 2
#define NUM_CHECKS 3
static Boolean SetValues(current, request, new, args, num_args)
Widget current, request, new;
ArgList args;
Cardinal *num_args;
{
WinLabelWidget curlw = (WinLabelWidget) current;
WinLabelWidget reqlw = (WinLabelWidget) request;
WinLabelWidget newlw = (WinLabelWidget) new;
int i;
Boolean was_resized = False, redisplay = False, checks[NUM_CHECKS];
for (i = 0; i < NUM_CHECKS; i++)
checks[i] = FALSE;
for (i = 0; i < *num_args; i++) {
if (streq(XtNbitmap, args[i].name))
checks[PIXMAP] = TRUE;
if (streq(XtNwidth, args[i].name))
checks[WIDTH] = TRUE;
if (streq(XtNheight, args[i].name))
checks[HEIGHT] = TRUE;
}
if (newlw->winlabel.label == NULL) {
newlw->winlabel.label = newlw->core.name;
}
/*
* resize on bitmap change
*/
if (curlw->winlabel.left_bitmap != newlw->winlabel.left_bitmap) {
was_resized = True;
}
if (curlw->winlabel.encoding != newlw->winlabel.encoding)
was_resized = True;
if (curlw->winlabel.label != newlw->winlabel.label) {
if (curlw->winlabel.label != curlw->core.name)
XtFree( (char *)curlw->winlabel.label );
if (newlw->winlabel.label != newlw->core.name) {
newlw->winlabel.label = XtNewString( newlw->winlabel.label );
}
RemoveAmpersand(new);
was_resized = True;
}
if (was_resized || (curlw->winlabel.font != newlw->winlabel.font) ||
(curlw->winlabel.justify != newlw->winlabel.justify)
|| checks[PIXMAP]) {
SetTextWidthAndHeight(newlw);
was_resized = True;
}
/* recalculate the window size if something has changed. */
if (newlw->winlabel.resize && was_resized) {
if ((curlw->core.height == reqlw->core.height) && !checks[HEIGHT])
newlw->core.height = (newlw->winlabel.label_height +
2 * newlw->winlabel.internal_height);
set_bitmap_info (newlw);
if ((curlw->core.width == reqlw->core.width) && !checks[WIDTH])
newlw->core.width = (newlw->winlabel.label_width +
LEFT_OFFSET(newlw) +
2 * newlw->winlabel.internal_width);
}
if (curlw->winlabel.foreground != newlw->winlabel.foreground
|| curlw->core.background_pixel != newlw->core.background_pixel
|| curlw->winlabel.font->fid != newlw->winlabel.font->fid) {
XtReleaseGC(new, curlw->winlabel.normal_GC);
XtReleaseGC(new, curlw->winlabel.gray_GC);
XmuReleaseStippledPixmap( XtScreen(current), curlw->winlabel.stipple );
GetnormalGC(newlw);
GetgrayGC(newlw);
redisplay = True;
}
if ((curlw->winlabel.internal_width != newlw->winlabel.internal_width)
|| (curlw->winlabel.internal_height != newlw->winlabel.internal_height)
|| was_resized) {
/* Resize() will be called if geometry changes succeed */
Position dx, dy;
_Reposition(newlw, curlw->core.width, curlw->core.height, &dx, &dy);
}
return was_resized || redisplay ||
XtIsSensitive(current) != XtIsSensitive(new);
}
static void Destroy(w)
Widget w;
{
WinLabelWidget lw = (WinLabelWidget)w;
XtFree( lw->winlabel.label );
XtReleaseGC( w, lw->winlabel.normal_GC );
XtReleaseGC( w, lw->winlabel.gray_GC);
XmuReleaseStippledPixmap( XtScreen(w), lw->winlabel.stipple );
}
static XtGeometryResult QueryGeometry(w, intended, preferred)
Widget w;
XtWidgetGeometry *intended, *preferred;
{
register WinLabelWidget lw = (WinLabelWidget)w;
preferred->request_mode = CWWidth | CWHeight;
preferred->width = (lw->winlabel.label_width +
2 * lw->winlabel.internal_width +
LEFT_OFFSET(lw));
preferred->height = lw->winlabel.label_height +
2*lw->winlabel.internal_height;
if ( ((intended->request_mode & (CWWidth | CWHeight))
== (CWWidth | CWHeight)) &&
intended->width == preferred->width &&
intended->height == preferred->height)
return XtGeometryYes;
else if (preferred->width == w->core.width &&
preferred->height == w->core.height)
return XtGeometryNo;
else
return XtGeometryAlmost;
}

106
controls/WinLabel.h Normal file
View File

@ -0,0 +1,106 @@
/***********************************************************
Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
Permission to use, copy, modify, and distribute this software and its
documentation for any purpose and without fee is hereby granted,
provided that the above copyright notice appear in all copies and that
both that copyright notice and this permission notice appear in
supporting documentation, and that the names of Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
******************************************************************/
/*
* Modifications for Wine
*
* 8/23/93 David Metcalfe (david@prism.demon.co.uk)
* Added code to translate ampersand to underlined char
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinLabel
*/
#ifndef _WinLabel_h
#define _WinLabel_h
/***********************************************************************
*
* WinLabel Widget
*
***********************************************************************/
#include <X11/Xaw/Simple.h>
/* Resources:
Name Class RepType Default Value
---- ----- ------- -------------
background Background Pixel XtDefaultBackground
bitmap Pixmap Pixmap None
border BorderColor Pixel XtDefaultForeground
borderWidth BorderWidth Dimension 1
cursor Cursor Cursor None
cursorName Cursor String NULL
destroyCallback Callback XtCallbackList NULL
encoding Encoding unsigned char XawTextEncoding8bit
font Font XFontStruct* XtDefaultFont
foreground Foreground Pixel XtDefaultForeground
height Height Dimension text height
insensitiveBorder Insensitive Pixmap Gray
internalHeight Height Dimension 2
internalWidth Width Dimension 4
justify Justify XtJustify XtJustifyCenter
label Label String NULL
leftBitmap LeftBitmap Pixmap None
mappedWhenManaged MappedWhenManaged Boolean True
pointerColor Foreground Pixel XtDefaultForeground
pointerColorBackground Background Pixel XtDefaultBackground
resize Resize Boolean True
sensitive Sensitive Boolean True
width Width Dimension text width
x Position Position 0
y Position Position 0
*/
#define XawTextEncoding8bit 0
#define XawTextEncodingChar2b 1
#define XtNleftBitmap "leftBitmap"
#define XtCLeftBitmap "LeftBitmap"
#define XtNencoding "encoding"
#define XtCEncoding "Encoding"
#ifndef _XtStringDefs_h_
#define XtNbitmap "bitmap"
#define XtNforeground "foreground"
#define XtNlabel "label"
#define XtNfont "font"
#define XtNinternalWidth "internalWidth"
#define XtNinternalHeight "internalHeight"
#define XtNresize "resize"
#define XtCResize "Resize"
#define XtCBitmap "Bitmap"
#endif
/* Class record constants */
extern WidgetClass winLabelWidgetClass;
typedef struct _WinLabelClassRec *WinLabelWidgetClass;
typedef struct _WinLabelRec *WinLabelWidget;
#endif /* _WinLabel_h */
/* DON'T ADD STUFF AFTER THIS #endif */

114
controls/WinLabelP.h Normal file
View File

@ -0,0 +1,114 @@
/***********************************************************
Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
Permission to use, copy, modify, and distribute this software and its
documentation for any purpose and without fee is hereby granted,
provided that the above copyright notice appear in all copies and that
both that copyright notice and this permission notice appear in
supporting documentation, and that the names of Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
******************************************************************/
/*
* Modifications for Wine
*
* 8/23/93 David Metcalfe (david@prism.demon.co.uk)
* Added code to translate ampersand to underlined char
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinLabel
*/
/*
* WinLabelP.h - Private definitions for WinLabel widget
*
*/
#ifndef _WinLabelP_h
#define _WinLabelP_h
/***********************************************************************
*
* WinLabel Widget Private Data
*
***********************************************************************/
#include "WinLabel.h"
#include <X11/Xaw/SimpleP.h>
/* New fields for the WinLabel widget class record */
typedef struct {int foo;} WinLabelClassPart;
/* Full class record declaration */
typedef struct _WinLabelClassRec {
CoreClassPart core_class;
SimpleClassPart simple_class;
WinLabelClassPart winlabel_class;
} WinLabelClassRec;
extern WinLabelClassRec winLabelClassRec;
/* New fields for the WinLabel widget record */
typedef struct {
/* resources */
Pixel foreground;
XFontStruct *font;
char *label;
XtJustify justify;
Dimension internal_width;
Dimension internal_height;
Pixmap pixmap;
Boolean resize;
unsigned char encoding;
Pixmap left_bitmap;
/* private state */
GC normal_GC;
GC gray_GC;
Pixmap stipple;
Position label_x;
Position label_y;
Dimension label_width;
Dimension label_height;
Dimension label_len;
int lbm_y; /* where in label */
unsigned int lbm_width, lbm_height; /* size of pixmap */
int ul_pos; /* Offset in chars of underlined character */
/* in label */
} WinLabelPart;
/****************************************************************
*
* Full instance record declaration
*
****************************************************************/
typedef struct _WinLabelRec {
CorePart core;
SimplePart simple;
WinLabelPart winlabel;
} WinLabelRec;
#define LEFT_OFFSET(lw) ((lw)->winlabel.left_bitmap \
? (lw)->winlabel.lbm_width + \
(lw)->winlabel.internal_width \
: 0)
#endif /* _WinLabelP_h */

100
controls/WinMenuButtP.h Normal file
View File

@ -0,0 +1,100 @@
/*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, provided that
* the above copyright notice appear in all copies and that both that
* copyright notice and this permission notice appear in supporting
* documentation, and that the name of M.I.T. not be used in advertising or
* publicity pertaining to distribution of the software without specific,
* written prior permission. M.I.T. makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
* BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/*
* Modifications for Wine
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinMenuButton
*/
/***********************************************************************
*
* WinMenuButton Widget
*
***********************************************************************/
/*
* WinMenuButtP.h - Private Header file for WinMenuButton widget.
*
* This is the private header file for the WinMenuButton widget.
* It is intended to provide an easy method of activating pulldown menus.
*
* Date: May 2, 1989
*
* By: Chris D. Peterson
* MIT X Consortium
* kit@expo.lcs.mit.edu
*/
#ifndef _WinMenuButtonP_h
#define _WinMenuButtonP_h
#include "WinMenuButto.h"
#include "WinCommandP.h"
/************************************
*
* Class structure
*
***********************************/
/* New fields for the WinMenuButton widget class record */
typedef struct _WinMenuButtonClass
{
int makes_compiler_happy; /* not used */
} WinMenuButtonClassPart;
/* Full class record declaration */
typedef struct _WinMenuButtonClassRec {
CoreClassPart core_class;
SimpleClassPart simple_class;
WinLabelClassPart winLabel_class;
WinCommandClassPart winCommand_class;
WinMenuButtonClassPart winMenuButton_class;
} WinMenuButtonClassRec;
extern WinMenuButtonClassRec winMenuButtonClassRec;
/***************************************
*
* Instance (widget) structure
*
**************************************/
/* New fields for the WinMenuButton widget record */
typedef struct {
/* resources */
String menu_name;
} WinMenuButtonPart;
/* Full widget declaration */
typedef struct _WinMenuButtonRec {
CorePart core;
SimplePart simple;
WinLabelPart winlabel;
WinCommandPart wincommand;
WinMenuButtonPart winmenu_button;
} WinMenuButtonRec;
#endif /* _WinMenuButtonP_h */

215
controls/WinMenuButto.c Normal file
View File

@ -0,0 +1,215 @@
/*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, provided that
* the above copyright notice appear in all copies and that both that
* copyright notice and this permission notice appear in supporting
* documentation, and that the name of M.I.T. not be used in advertising or
* publicity pertaining to distribution of the software without specific,
* written prior permission. M.I.T. makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
* BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*
*/
/*
* Modifications for Wine
*
* 8/27/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinMenuButton
*/
/***********************************************************************
*
* WinMenuButton Widget
*
***********************************************************************/
/*
* WinMenuButto.c - Source code for WinMenuButton widget.
*
* This is the source code for the WinMenuButton widget.
* It is intended to provide an easy method of activating pulldown menus.
*
* Date: May 2, 1989
*
* By: Chris D. Peterson
* MIT X Consortium
* kit@expo.lcs.mit.edu
*/
#include <stdio.h>
#include <X11/IntrinsicP.h>
#include <X11/StringDefs.h>
#include <X11/Xaw/XawInit.h>
#include "WinMenuButtP.h"
static void ClassInitialize();
static void PopupMenu();
#define superclass ((WinCommandWidgetClass)&winCommandClassRec)
static char defaultTranslations[] =
"<EnterWindow>: highlight() \n\
<LeaveWindow>: reset() \n\
<BtnDown>: reset() PopupMenu() ";
/****************************************************************
*
* Full class record constant
*
****************************************************************/
/* Private Data */
#define offset(field) XtOffsetOf(WinMenuButtonRec, field)
static XtResource resources[] = {
{
XtNmenuName, XtCMenuName, XtRString, sizeof(String),
offset(winmenu_button.menu_name), XtRString, (XtPointer)"menu"},
};
#undef offset
static XtActionsRec actionsList[] =
{
{"PopupMenu", PopupMenu}
};
WinMenuButtonClassRec winMenuButtonClassRec = {
{
(WidgetClass) superclass, /* superclass */
"WinMenuButton", /* class_name */
sizeof(WinMenuButtonRec), /* size */
ClassInitialize, /* class_initialize */
NULL, /* class_part_initialize */
FALSE, /* class_inited */
NULL, /* initialize */
NULL, /* initialize_hook */
XtInheritRealize, /* realize */
actionsList, /* actions */
XtNumber(actionsList), /* num_actions */
resources, /* resources */
XtNumber(resources), /* resource_count */
NULLQUARK, /* xrm_class */
FALSE, /* compress_motion */
TRUE, /* compress_exposure */
TRUE, /* compress_enterleave */
FALSE, /* visible_interest */
NULL, /* destroy */
XtInheritResize, /* resize */
XtInheritExpose, /* expose */
NULL, /* set_values */
NULL, /* set_values_hook */
XtInheritSetValuesAlmost, /* set_values_almost */
NULL, /* get_values_hook */
NULL, /* accept_focus */
XtVersion, /* version */
NULL, /* callback_private */
defaultTranslations, /* tm_table */
XtInheritQueryGeometry, /* query_geometry */
XtInheritDisplayAccelerator, /* display_accelerator */
NULL /* extension */
}, /* CoreClass fields initialization */
{
XtInheritChangeSensitive /* change_sensitive */
}, /* SimpleClass fields initialization */
{
0, /* field not used */
}, /* WinLabelClass fields initialization */
{
0, /* field not used */
}, /* WinCommandClass fields initialization */
{
0, /* field not used */
}, /* WinMenuButtonClass fields initialization */
};
/* for public consumption */
WidgetClass winMenuButtonWidgetClass = (WidgetClass) &winMenuButtonClassRec;
/****************************************************************
*
* Private Procedures
*
****************************************************************/
static void ClassInitialize()
{
XawInitializeWidgetSet();
XtRegisterGrabAction(PopupMenu, True, ButtonPressMask | ButtonReleaseMask,
GrabModeAsync, GrabModeAsync);
}
/* ARGSUSED */
static void
PopupMenu(w, event, params, num_params)
Widget w;
XEvent * event;
String * params;
Cardinal * num_params;
{
WinMenuButtonWidget mbw = (WinMenuButtonWidget) w;
Widget menu, temp;
Arg arglist[2];
Cardinal num_args;
int menu_x, menu_y, menu_width, menu_height, button_height;
Position button_x, button_y;
temp = w;
while(temp != NULL) {
menu = XtNameToWidget(temp, mbw->winmenu_button.menu_name);
if (menu == NULL)
temp = XtParent(temp);
else
break;
}
if (menu == NULL) {
char error_buf[BUFSIZ];
sprintf(error_buf, "MenuButton: %s %s.",
"Could not find menu widget named", mbw->winmenu_button.menu_name);
XtAppWarning(XtWidgetToApplicationContext(w), error_buf);
return;
}
if (!XtIsRealized(menu))
XtRealizeWidget(menu);
menu_width = menu->core.width + 2 * menu->core.border_width;
button_height = w->core.height + 2 * w->core.border_width;
menu_height = menu->core.height + 2 * menu->core.border_width;
XtTranslateCoords(w, 0, 0, &button_x, &button_y);
menu_x = button_x;
menu_y = button_y + button_height;
if (menu_x >= 0) {
int scr_width = WidthOfScreen(XtScreen(menu));
if (menu_x + menu_width > scr_width)
menu_x = scr_width - menu_width;
}
if (menu_x < 0)
menu_x = 0;
if (menu_y >= 0) {
int scr_height = HeightOfScreen(XtScreen(menu));
if (menu_y + menu_height > scr_height)
menu_y = scr_height - menu_height;
}
if (menu_y < 0)
menu_y = 0;
num_args = 0;
XtSetArg(arglist[num_args], XtNx, menu_x); num_args++;
XtSetArg(arglist[num_args], XtNy, menu_y); num_args++;
XtSetValues(menu, arglist, num_args);
XtPopupSpringLoaded(menu);
}

91
controls/WinMenuButto.h Normal file
View File

@ -0,0 +1,91 @@
/*
* Copyright 1989 Massachusetts Institute of Technology
*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, provided that
* the above copyright notice appear in all copies and that both that
* copyright notice and this permission notice appear in supporting
* documentation, and that the name of M.I.T. not be used in advertising or
* publicity pertaining to distribution of the software without specific,
* written prior permission. M.I.T. makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
* BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/*
* Modifications for Wine
*
* 8/23/93 David Metcalfe (david@prism.demon.co.uk)
* Converted to WinMenuButton
*/
/***********************************************************************
*
* WinMenuButton Widget
*
***********************************************************************/
/*
* WinMenuButton.h - Public Header file for WinMenuButton widget.
*
* This is the public header file for the WinMenuButton widget.
* It is intended to provide an easy method of activating pulldown menus.
*
* Date: May 2, 1989
*
* By: Chris D. Peterson
* MIT X Consortium
* kit@expo.lcs.mit.edu
*/
#ifndef _WinMenuButton_h
#define _WinMenuButton_h
#include "WinCommand.h"
/* Resources:
Name Class RepType Default Value
---- ----- ------- -------------
background Background Pixel XtDefaultBackground
bitmap Pixmap Pixmap None
border BorderColor Pixel XtDefaultForeground
borderWidth BorderWidth Dimension 1
callback Callback Pointer NULL
cursor Cursor Cursor None
destroyCallback Callback Pointer NULL
font Font XFontStruct* XtDefaultFont
foreground Foreground Pixel XtDefaultForeground
height Height Dimension text height
highlightThickness Thickness Dimension 2
insensitiveBorder Insensitive Pixmap Gray
internalHeight Height Dimension 2
internalWidth Width Dimension 4
justify Justify XtJustify XtJustifyCenter
label Label String NULL
mappedWhenManaged MappedWhenManaged Boolean True
menuName MenuName String "menu"
resize Resize Boolean True
sensitive Sensitive Boolean True
width Width Dimension text width
x Position Position 0
y Position Position 0
*/
#define XtNmenuName "menuName"
#define XtCMenuName "MenuName"
extern WidgetClass winMenuButtonWidgetClass;
typedef struct _WinMenuButtonClassRec *WinMenuButtonWidgetClass;
typedef struct _WinMenuButtonRec *WinMenuButtonWidget;
#endif /* _WinMenuButton_h -- DON'T ADD STUFF AFTER THIS */

569
controls/menu.c Normal file
View File

@ -0,0 +1,569 @@
static char RCSId[] = "$Id$";
static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Xaw/SmeBSB.h>
#include <X11/Xaw/SmeLine.h>
#include <X11/Xaw/SimpleMenu.h>
#include "WinMenuButto.h"
#include "SmeMenuButto.h"
#include "windows.h"
#include "menu.h"
#include "heap.h"
#include "win.h"
#include "bitmaps/check_bitmap"
#include "bitmaps/nocheck_bitmap"
static LPMENUBAR firstMenu = NULL;
static MENUITEM *parentItem;
static MENUITEM *siblingItem;
static int lastLevel;
static int menuId = 0;
static Pixmap checkBitmap = XtUnspecifiedPixmap;
static Pixmap nocheckBitmap = XtUnspecifiedPixmap;
/**********************************************************************
* MENU_CheckWidget
*/
void
MENU_CheckWidget(Widget w, Boolean check)
{
if (checkBitmap == XtUnspecifiedPixmap)
{
Display *display = XtDisplayOfObject(w);
checkBitmap = XCreateBitmapFromData(display,
DefaultRootWindow(display),
check_bitmap_bits,
check_bitmap_width,
check_bitmap_height);
nocheckBitmap = XCreateBitmapFromData(display,
DefaultRootWindow(display),
nocheck_bitmap_bits,
nocheck_bitmap_width,
nocheck_bitmap_height);
}
if (check)
XtVaSetValues(w, XtNleftBitmap, checkBitmap, NULL);
else
XtVaSetValues(w, XtNleftBitmap, nocheckBitmap, NULL);
}
/**********************************************************************
* MENU_ParseMenu
*/
WORD *
MENU_ParseMenu(WORD *first_item,
int level,
int limit,
int (*action)(WORD *item, int level, void *app_data),
void *app_data)
{
WORD *item;
WORD *next_item;
int i;
level++;
next_item = first_item;
i = 0;
do
{
i++;
item = next_item;
(*action)(item, level, app_data);
if (*item & MF_POPUP)
{
MENU_POPUPITEM *popup_item = (MENU_POPUPITEM *) item;
next_item = (WORD *) (popup_item->item_text +
strlen(popup_item->item_text) + 1);
next_item = MENU_ParseMenu(next_item, level, 0, action, app_data);
}
else
{
MENU_NORMALITEM *normal_item = (MENU_NORMALITEM *) item;
next_item = (WORD *) (normal_item->item_text +
strlen(normal_item->item_text) + 1);
}
}
while (!(*item & MF_END) && i != limit);
return next_item;
}
/**********************************************************************
* MENU_FindMenuBar
*/
LPMENUBAR
MENU_FindMenuBar(MENUITEM *this_item)
{
MENUITEM *root;
LPMENUBAR menu;
/*
* Find root item on menu bar.
*/
for (root = this_item; root->parent != NULL; root = root->parent)
;
for ( ; root->prev != NULL; root = root->prev)
;
/*
* Find menu bar for the root item.
*/
for (menu = firstMenu;
menu != NULL && menu->firstItem != root;
menu = menu->next)
;
return menu;
}
/**********************************************************************
* MENU_SelectionCallback
*/
static void
MENU_SelectionCallback(Widget w, XtPointer client_data, XtPointer call_data)
{
MENUITEM *this_item = (MENUITEM *) client_data;
LPMENUBAR menu;
WND *wndPtr;
if (this_item->menu_w != NULL || (this_item->item_flags & MF_DISABLED))
return;
/*
* Find menu bar for the root item.
*/
menu = MENU_FindMenuBar(this_item);
if (menu != NULL)
{
wndPtr = (WND *) GlobalLock(menu->ownerWnd);
if (wndPtr == NULL)
return;
#ifdef DEBUG_MENU
printf("Selected '%s' (%d).\n",
this_item->item_text, this_item->item_id);
#endif
CallWindowProc(wndPtr->lpfnWndProc, menu->ownerWnd, WM_COMMAND,
this_item->item_id, 0);
GlobalUnlock(menu->ownerWnd);
}
}
/**********************************************************************
* MENU_CreateItems
*/
int
MENU_CreateItems(WORD *item, int level, void *app_data)
{
MENU_POPUPITEM *popup_item;
MENU_NORMALITEM *normal_item;
MENUITEM *this_item;
Arg this_args[10];
int n_args = 0;
LPMENUBAR menu = (LPMENUBAR) app_data;
if (menu->nItems == 0)
this_item = menu->firstItem;
else
this_item = (MENUITEM *) GlobalQuickAlloc(sizeof(MENUITEM));
if (this_item == NULL)
return 0;
if (level > lastLevel)
{
parentItem = siblingItem;
siblingItem = NULL;
}
while (level < lastLevel)
{
siblingItem = parentItem;
if (siblingItem != NULL)
parentItem = siblingItem->parent;
else
parentItem = NULL;
lastLevel--;
}
lastLevel = level;
this_item->next = NULL;
this_item->prev = siblingItem;
this_item->child = NULL;
this_item->parent = parentItem;
if (siblingItem != NULL)
siblingItem->next = this_item;
if (parentItem != NULL && parentItem->child == NULL)
parentItem->child = this_item;
siblingItem = this_item;
if (*item & MF_POPUP)
{
popup_item = (MENU_POPUPITEM *) item;
this_item->item_flags = popup_item->item_flags;
this_item->item_id = -1;
this_item->item_text = popup_item->item_text;
#ifdef DEBUG_MENU
printf("%d: popup %s\n", level, this_item->item_text);
#endif
}
else
{
normal_item = (MENU_NORMALITEM *) item;
this_item->item_flags = normal_item->item_flags;
this_item->item_id = normal_item->item_id;
this_item->item_text = normal_item->item_text;
#ifdef DEBUG_MENU
printf("%d: normal %s (%04x)\n", level, this_item->item_text,
this_item->item_flags);
#endif
}
if (level == 1)
{
menu->nItems++;
if (this_item->prev != NULL)
{
XtSetArg(this_args[n_args], XtNhorizDistance, 10);
n_args++;
XtSetArg(this_args[n_args], XtNfromHoriz, this_item->prev->w);
n_args++;
}
if (this_item->item_flags & MF_POPUP)
{
sprintf(this_item->menu_name, "Menu%d", menuId++);
XtSetArg(this_args[n_args], XtNmenuName, this_item->menu_name);
n_args++;
this_item->w = XtCreateManagedWidget(this_item->item_text,
winMenuButtonWidgetClass,
menu->parentWidget,
this_args, n_args);
this_item->menu_w = XtCreatePopupShell(this_item->menu_name,
simpleMenuWidgetClass,
this_item->w,
NULL, 0);
}
else
{
this_item->w = XtCreateManagedWidget(this_item->item_text,
winCommandWidgetClass,
menu->parentWidget,
this_args, n_args);
this_item->menu_w = NULL;
XtAddCallback(this_item->w, XtNcallback, MENU_SelectionCallback,
(XtPointer) this_item);
}
if (menu->firstItem == NULL)
menu->firstItem = this_item;
}
else
{
if ((this_item->item_flags & MF_MENUBREAK) ||
(strlen(this_item->item_text) == 0))
{
XtSetArg(this_args[n_args], XtNheight, 10);
n_args++;
this_item->w = XtCreateManagedWidget("separator",
smeLineObjectClass,
this_item->parent->menu_w,
this_args, n_args);
}
else
{
XtSetArg(this_args[n_args], XtNmenuName, this_item->menu_name);
n_args++;
this_item->w = XtCreateManagedWidget(this_item->item_text,
smeMenuButtonObjectClass,
this_item->parent->menu_w,
this_args, n_args);
if (this_item->item_flags & MF_POPUP)
{
sprintf(this_item->menu_name, "Menu%d", menuId++);
this_item->menu_w = XtCreatePopupShell(this_item->menu_name,
simpleMenuWidgetClass,
this_item->parent->menu_w,
NULL, 0);
}
else
{
this_item->menu_w = NULL;
XtAddCallback(this_item->w, XtNcallback,
MENU_SelectionCallback, (XtPointer) this_item);
}
}
}
if (this_item->w != NULL)
{
if (this_item->item_flags & MF_GRAYED)
XtSetSensitive(this_item->w, False);
if (this_item->item_flags & MF_DISABLED)
XtVaSetValues(this_item->w, XtNinactive, True, NULL);
if (this_item->item_flags & MF_CHECKED)
MENU_CheckWidget(this_item->w, True);
}
return 1;
}
/**********************************************************************
* MENU_UseMenu
*/
LPMENUBAR
MENU_UseMenu(Widget parent, HANDLE instance, HWND wnd, HMENU hmenu, int width)
{
LPMENUBAR menubar;
MENUITEM *menu;
MENU_HEADER *menu_desc;
menu = (MENUITEM *) GlobalLock(hmenu);
if (hmenu == 0 || menu == NULL)
{
return NULL;
}
menubar = MENU_FindMenuBar(menu);
if (menubar == NULL)
{
GlobalUnlock(hmenu);
return NULL;
}
menubar->nItems = 0;
menubar->parentWidget = parent;
menubar->ownerWnd = wnd;
menu_desc = (MENU_HEADER *) GlobalLock(menubar->menuDescription);
parentItem = NULL;
siblingItem = NULL;
lastLevel = 0;
MENU_ParseMenu((WORD *) (menu_desc + 1), 0, 0, MENU_CreateItems, menubar);
menubar->menuBarWidget = menubar->firstItem->w;
menubar->next = firstMenu;
firstMenu = menubar;
return menubar;
}
/**********************************************************************
* MENU_CreateMenuBar
*/
LPMENUBAR
MENU_CreateMenuBar(Widget parent, HANDLE instance, HWND wnd,
char *menu_name, int width)
{
LPMENUBAR menubar;
HMENU hmenu;
MENUITEM *menu;
MENU_HEADER *menu_desc;
#ifdef DEBUG_MENU
printf("CreateMenuBar: instance %02x, menu '%s', width %d\n",
instance, menu_name, width);
#endif
hmenu = LoadMenu(instance, menu_name);
return MENU_UseMenu(parent, instance, wnd, hmenu, width);
}
/**********************************************************************
* MENU_FindItem
*/
MENUITEM *
MENU_FindItem(MENUITEM *menu, WORD item_id, WORD flags)
{
MENUITEM *item;
WORD position;
if (flags & MF_BYPOSITION)
{
item = menu;
for (position = 0; item != NULL && position != item_id; position++)
item = item->next;
if (position == item_id)
return item;
}
else
{
for ( ; menu != NULL; menu = menu->next)
{
if (menu->item_id == item_id && menu->child == NULL)
return menu;
if (menu->child != NULL)
{
item = MENU_FindItem(menu->child, item_id, flags);
if (item != NULL)
return item;
}
}
}
return NULL;
}
/**********************************************************************
* MENU_CollapseMenu
*/
static void
MENU_CollapseBranch(MENUITEM *item, Boolean first_flag)
{
MENUITEM *next_item;
for ( ; item != NULL; item = next_item)
{
next_item = item->next;
if (item->child != NULL)
MENU_CollapseBranch(item->child, False);
if (item->w != NULL)
XtDestroyWidget(item->w);
if (item->menu_w != NULL)
XtDestroyWidget(item->menu_w);
if (first_flag)
{
item->prev = NULL;
item->child = NULL;
item->next = NULL;
item->parent = NULL;
item->item_flags = 0;
item->item_id = 0;
item->item_text = NULL;
item->w = NULL;
item->menu_w = NULL;
first_flag = False;
}
else
{
GlobalFree((unsigned int) item);
}
}
}
void
MENU_CollapseMenu(LPMENUBAR menubar)
{
MENU_CollapseBranch(menubar->firstItem, True);
menubar->nItems = 0;
menubar->parentWidget = NULL;
menubar->ownerWnd = 0;
menubar->menuBarWidget = NULL;
}
/**********************************************************************
* CheckMenu
*/
BOOL
CheckMenu(HMENU hmenu, WORD item_id, WORD check_flags)
{
MENUITEM *item;
Pixmap left_bitmap;
if ((item = (MENUITEM *) GlobalLock(hmenu)) == NULL)
return -1;
item = MENU_FindItem(item, item_id, check_flags);
if (item == NULL)
{
GlobalUnlock(hmenu);
return -1;
}
XtVaGetValues(item->w, XtNleftBitmap, &left_bitmap, NULL);
MENU_CheckWidget(item->w, (check_flags & MF_CHECKED));
if (left_bitmap == XtUnspecifiedPixmap)
return MF_UNCHECKED;
else
return MF_CHECKED;
}
/**********************************************************************
* LoadMenu
*/
HMENU
LoadMenu(HINSTANCE instance, char *menu_name)
{
HANDLE hmenubar;
LPMENUBAR menu;
HANDLE hmenu_desc;
HMENU hmenu;
MENU_HEADER *menu_desc;
#ifdef DEBUG_MENU
printf("LoadMenu: instance %02x, menu '%s'\n",
instance, menu_name);
#endif
if (menu_name == NULL ||
(hmenu_desc = RSC_LoadMenu(instance, menu_name)) == 0 ||
(menu_desc = (MENU_HEADER *) GlobalLock(hmenu_desc)) == NULL)
{
return 0;
}
hmenubar = GlobalAlloc(GMEM_MOVEABLE, sizeof(MENUBAR));
menu = (LPMENUBAR) GlobalLock(hmenubar);
if (menu == NULL)
{
GlobalFree(hmenu_desc);
GlobalFree(hmenubar);
return 0;
}
hmenu = GlobalAlloc(GMEM_MOVEABLE, sizeof(MENUITEM));
if (hmenu == 0)
{
GlobalFree(hmenu_desc);
GlobalFree(hmenubar);
return 0;
}
menu->menuDescription = hmenu_desc;
menu->nItems = 0;
menu->parentWidget = NULL;
menu->firstItem = (MENUITEM *) GlobalLock(hmenu);
menu->ownerWnd = 0;
menu->menuBarWidget = NULL;
menu->firstItem->next = NULL;
menu->firstItem->prev = NULL;
menu->firstItem->child = NULL;
menu->firstItem->parent = NULL;
menu->firstItem->item_flags = 0;
menu->firstItem->item_id = 0;
menu->firstItem->item_text = NULL;
menu->firstItem->w = NULL;
menu->firstItem->menu_w = NULL;
menu->next = firstMenu;
firstMenu = menu;
return GlobalHandleFromPointer(menu->firstItem);
}

View File

@ -1,9 +0,0 @@
# $Id: gdi.spec,v 1.3 1993/07/04 04:04:21 root Exp root $
#
name gdi
id 3
length 490
27 pascal Rectangle(word word word word word) Rectangle(1 2 3 4 5)
82 pascal GetObject(word word ptr) RSC_GetObject(1 2 3)
87 pascal GetStockObject(word) GetStockObject(1)

43
if1632/Makefile Normal file
View File

@ -0,0 +1,43 @@
CFLAGS=$(COPTS) $(DEBUGOPTS) -I$(INCLUDE_DIR)
BUILDOBJS=dll_kernel.o dll_user.o dll_gdi.o dll_unixlib.o \
dll_win87em.o dll_shell.o \
dll_kernel_tab.o dll_user_tab.o dll_gdi_tab.o dll_unixlib_tab.o \
dll_win87em_tab.o dll_shell_tab.o
MUST_BE_LINKED_FIRST=call.o $(BUILDOBJS)
OBJS=$(MUST_BE_LINKED_FIRST) callback.o relay.o
default: if1632.o
if1632.o: $(OBJS)
$(LD) -r -o if1632.o $(OBJS)
clean:
rm -f *.o *~ *.s dll_* *.a
dll_kernel.S dll_kernel_tab.c: ../tools/build kernel.spec
../tools/build kernel.spec
dll_user.S dll_user_tab.c: ../tools/build user.spec
../tools/build user.spec
dll_gdi.S dll_gdi_tab.c: ../tools/build gdi.spec
../tools/build gdi.spec
dll_unixlib.S dll_unixlib_tab.c: ../tools/build unixlib.spec
../tools/build unixlib.spec
dll_win87em.S dll_win87em_tab.c: ../tools/build win87em.spec
../tools/build win87em.spec
dll_shell.S dll_shell_tab.c: ../tools/build shell.spec
../tools/build shell.spec
depend:
$(CC) $(CFLAGS) -M *.c > .depend
ifeq (.depend,$(wildcard .depend))
include .depend
endif

View File

@ -35,7 +35,7 @@ offset:
.word 0 .word 0
.text .text
/********************************************************************** /**********************************************************************
* int CallToInit16(unsigned long csip, unsigned long sssp, * int CallToInit16(unsigned long csip, unsigned long sssp,
* unsigned short ds) * unsigned short ds)
@ -93,6 +93,7 @@ _CallToInit16:
movl %eax,%esp movl %eax,%esp
movw 14(%ebp),%ax movw 14(%ebp),%ax
movw %ax,%ss movw %ax,%ss
movl %esp,%eax
movl %eax,%ebp movl %eax,%ebp
/* /*
@ -100,7 +101,7 @@ _CallToInit16:
*/ */
.byte 0x66 .byte 0x66
lcall %fs:(%edx) lcall %fs:(%edx)
/* /*
* Restore old stack and segment registers. * Restore old stack and segment registers.
* *
@ -135,7 +136,7 @@ _CallToInit16:
.align 2,0x90 .align 2,0x90
leave leave
ret ret
/********************************************************************** /**********************************************************************
* int CallTo16(unsigned long csip, unsigned short ds) * int CallTo16(unsigned long csip, unsigned short ds)
* *
@ -180,7 +181,7 @@ _CallTo16:
movw %ax,%ds movw %ax,%ds
.byte 0x66 .byte 0x66
lcall %fs:(%edx) lcall %fs:(%edx)
/* /*
* Restore old stack and segment registers. * Restore old stack and segment registers.
* *
@ -217,7 +218,7 @@ _CallTo16:
.align 2,0x90 .align 2,0x90
leave leave
ret ret
/********************************************************************** /**********************************************************************
* CallTo32() * CallTo32()
* *
@ -276,7 +277,7 @@ _CallTo32:
pushw _IF1632_Saved16_esp pushw _IF1632_Saved16_esp
pushl %eax pushl %eax
call _DLLRelay call _DLLRelay
/* /*
* Restore registers, but do not destroy return value. * Restore registers, but do not destroy return value.
*/ */
@ -321,19 +322,14 @@ noargs:
.byte 0x66 .byte 0x66
lret lret
/********************************************************************** /**********************************************************************
* KERNEL_InitTask() * ReturnFromRegisterFunc()
*
* This interface functions is special because it returns all
* of its values in registers. Thus we can't just fall back through
* the C functions that called us. Instead we simply abandon
* the 32-bit stack, set up the registers and return.
*/ */
.globl _KERNEL_InitTask .globl _ReturnFromRegisterFunc
_KERNEL_InitTask: _ReturnFromRegisterFunc:
/* /*
* Restore stack * Restore 16-bit stack
*/ */
movw _IF1632_Saved16_ss,%ss movw _IF1632_Saved16_ss,%ss
movl _IF1632_Saved16_esp,%esp movl _IF1632_Saved16_esp,%esp
@ -349,32 +345,25 @@ _KERNEL_InitTask:
.align 2,0x90 .align 2,0x90
leave leave
/* /*
* Now we need to ditch the parameter bytes that were left on the * This leaves us with a stack that has number of arguments,
* stack. We do this by effectively popping the number of bytes, * the return address, the saved registers, and the return
* and the return address, removing the parameters and then putting * address again.
* the return address back on the stack.
* Normally this field is filled in by the relevant function in
* the emulation library, since it should know how many bytes to
* expect.
*/ */
popw %gs:nbytes popw %ax /* Throw away the number of arguments */
cmpw $0,%gs:nbytes popl %eax /* Throw away first copy of return address */
je noargs_2 popw %es
popw %gs:offset popw %ds
popw %gs:selector popw %di
addw %gs:nbytes,%esp popw %si
pushw %gs:selector popw %bp
pushw %gs:offset popw %ax /* Throw away pushed stack pointer */
noargs_2: popw %bx
popw %dx
popw %cx
popw %ax
/* /*
* Last, we need to load the return values. * Return to original caller.
*/ */
movl $0,%esi
movw $1,%ax
movw %gs:_WIN_StackSize,%cx
movw $1,%dx
movw 0x80,%bx
.byte 0x66 .byte 0x66
lret lret

View File

@ -108,6 +108,27 @@ CALLBACK_MakeProcInstance(void *func, int instance)
return tp->thunk; return tp->thunk;
} }
/**********************************************************************
* FreeProcInstance (KERNEL.52)
*/
void FreeProcInstance(FARPROC func)
{
int handle;
void *new_func;
struct thunk_s *tp;
int i;
tp = (struct thunk_s *) MakeProcThunks->base_addr;
for (i = 0; i < 0x10000 / sizeof(*tp); i++, tp++)
{
if ((void *) tp->thunk == (void *) func)
{
tp->used = 0;
break;
}
}
}
/********************************************************************** /**********************************************************************
* CallWindowProc (USER.122) * CallWindowProc (USER.122)
*/ */
@ -126,3 +147,15 @@ LONG CallWindowProc( FARPROC func, HWND hwnd, WORD message,
else else
return WIDGETS_Call32WndProc( func, hwnd, message, wParam, lParam ); return WIDGETS_Call32WndProc( func, hwnd, message, wParam, lParam );
} }
/**********************************************************************
* CallLineDDAProc
*/
void CallLineDDAProc(FARPROC func, short xPos, short yPos, long lParam)
{
PushOn16( CALLBACK_SIZE_WORD, xPos );
PushOn16( CALLBACK_SIZE_WORD, yPos );
PushOn16( CALLBACK_SIZE_LONG, lParam );
CallTo16((unsigned int) func,
FindDataSegmentForCode((unsigned long) func));
}

10
if1632/findfunc Executable file
View File

@ -0,0 +1,10 @@
#! /bin/sh
name="blah"
while [ "$name" != "" ]
do
echo -n 'Function: '
read name
grep -i $name *.spec
done

170
if1632/gdi.spec Normal file
View File

@ -0,0 +1,170 @@
# $Id: gdi.spec,v 1.3 1993/07/04 04:04:21 root Exp root $
#
name gdi
id 3
length 490
1 pascal SetBkColor(word long) SetBkColor(1 2)
2 pascal SetBkMode(word word) SetBkMode(1 2)
3 pascal SetMapMode(word word) SetMapMode(1 2)
4 pascal SetROP2(word word) SetROP2(1 2)
5 pascal SetRelAbs(word word) SetRelAbs(1 2)
6 pascal SetPolyFillMode(word word) SetPolyFillMode(1 2)
7 pascal SetStretchBltMode(word word) SetStretchBltMode(1 2)
8 pascal SetTextCharacterExtra(word s_word) SetTextCharacterExtra(1 2)
9 pascal SetTextColor(word long) SetTextColor(1 2)
10 pascal SetTextJustification(word s_word s_word) SetTextJustification(1 2 3)
11 pascal SetWindowOrg(word s_word s_word) SetWindowOrg(1 2 3)
12 pascal SetWindowExt(word s_word s_word) SetWindowExt(1 2 3)
13 pascal SetViewportOrg(word s_word s_word) SetViewportOrg(1 2 3)
14 pascal SetViewportExt(word s_word s_word) SetViewportExt(1 2 3)
15 pascal OffsetWindowOrg(word s_word s_word) OffsetWindowOrg(1 2 3)
16 pascal ScaleWindowExt(word s_word s_word s_word s_word)
ScaleWindowExt(1 2 3 4 5)
17 pascal OffsetViewportOrg(word s_word s_word) OffsetViewportOrg(1 2 3)
18 pascal ScaleViewportExt(word s_word s_word s_word s_word)
ScaleViewportExt(1 2 3 4 5)
19 pascal LineTo(word s_word s_word) LineTo(1 2 3)
20 pascal MoveTo(word s_word s_word) MoveTo(1 2 3)
21 pascal ExcludeClipRect(word s_word s_word s_word s_word)
ExcludeClipRect(1 2 3 4 5)
22 pascal IntersectClipRect(word s_word s_word s_word s_word)
IntersectClipRect(1 2 3 4 5)
23 pascal Arc(word s_word s_word s_word s_word s_word s_word s_word s_word)
Arc(1 2 3 4 5 6 7 8 9)
24 pascal Ellipse(word s_word s_word s_word s_word) Ellipse(1 2 3 4 5)
26 pascal Pie(word s_word s_word s_word s_word s_word s_word s_word s_word)
Pie(1 2 3 4 5 6 7 8 9)
27 pascal Rectangle(word s_word s_word s_word s_word) Rectangle(1 2 3 4 5)
29 pascal PatBlt(word s_word s_word s_word s_word long) PatBlt(1 2 3 4 5 6)
30 pascal SaveDC(word) SaveDC(1)
31 pascal SetPixel(word s_word s_word long) SetPixel(1 2 3 4)
32 pascal OffsetClipRgn(word s_word s_word) OffsetClipRgn(1 2 3)
33 pascal TextOut(word s_word s_word ptr word) TextOut(1 2 3 4 5)
34 pascal BitBlt( word s_word s_word s_word s_word word s_word s_word long)
BitBlt(1 2 3 4 5 6 7 8 9)
39 pascal RestoreDC(word s_word) RestoreDC(1 2)
40 pascal FillRgn(word word word) FillRgn(1 2 3)
43 pascal PaintRgn(word word) PaintRgn(1 2)
44 pascal SelectClipRgn(word word) SelectClipRgn(1 2)
45 pascal SelectObject(word word) SelectObject(1 2)
47 pascal CombineRgn(word word word word) CombineRgn(1 2 3 4)
48 pascal CreateBitmap(word word word word ptr) CreateBitmap(1 2 3 4 5)
49 pascal CreateBitmapIndirect(ptr) CreateBitmapIndirect(1)
50 pascal CreateBrushIndirect(ptr) CreateBrushIndirect(1)
51 pascal CreateCompatibleBitmap(word word word) CreateCompatibleBitmap(1 2 3)
52 pascal CreateCompatibleDC(word) CreateCompatibleDC(1)
53 pascal CreateDC(ptr ptr ptr ptr) CreateDC(1 2 3 4)
54 pascal CreateEllipticRgn(s_word s_word s_word s_word)
CreateEllipticRgn(1 2 3 4)
55 pascal CreateEllipticRgnIndirect(ptr) CreateEllipticRgnIndirect(1)
56 pascal CreateFont(s_word s_word s_word s_word s_word word word word
word word word word word ptr)
CreateFont(1 2 3 4 5 6 7 8 9 10 11 12 13 14)
57 pascal CreateFontIndirect(ptr) CreateFontIndirect(1)
58 pascal CreateHatchBrush(word long) CreateHatchBrush(1 2)
60 pascal CreatePatternBrush(word) CreatePatternBrush(1)
61 pascal CreatePen(s_word s_word long) CreatePen(1 2 3)
62 pascal CreatePenIndirect(ptr) CreatePenIndirect(1)
63 pascal CreatePolygonRgn(ptr word word) CreatePolygonRgn(1 2 3)
64 pascal CreateRectRgn(s_word s_word s_word s_word) CreateRectRgn(1 2 3 4)
65 pascal CreateRectRgnIndirect(ptr) CreateRectRgnIndirect(1)
66 pascal CreateSolidBrush(long) CreateSolidBrush(1)
67 pascal DPtoLP(word ptr s_word) DPtoLP(1 2 3)
68 pascal DeleteDC(word) DeleteDC(1)
69 pascal DeleteObject(word) DeleteObject(1)
72 pascal EqualRgn(word word) EqualRgn(1 2)
73 pascal ExcludeVisRect(word s_word s_word s_word s_word)
ExcludeVisRect(1 2 3 4 5)
74 pascal GetBitmapBits(word long ptr) GetBitmapBits(1 2 3)
75 pascal GetBkColor(word) GetBkColor(1)
76 pascal GetBkMode(word) GetBkMode(1)
77 pascal GetClipBox(word ptr) GetClipBox(1 2)
78 pascal GetCurrentPosition(word) GetCurrentPosition(1)
79 pascal GetDCOrg(word) GetDCOrg(1)
80 pascal GetDeviceCaps(word s_word) GetDeviceCaps(1 2)
81 pascal GetMapMode(word) GetMapMode(1)
82 pascal GetObject(word word ptr) GetObject(1 2 3)
83 pascal GetPixel(word s_word s_word) GetPixel(1 2 3)
84 pascal GetPolyFillMode(word) GetPolyFillMode(1)
85 pascal GetROP2(word) GetROP2(1)
86 pascal GetRelAbs(word) GetRelAbs(1)
87 pascal GetStockObject(word) GetStockObject(1)
88 pascal GetStretchBltMode(word) GetStretchBltMode(1)
89 pascal GetTextCharacterExtra(word) GetTextCharacterExtra(1)
90 pascal GetTextColor(word) GetTextColor(1)
91 pascal GetTextExtent(word ptr s_word) GetTextExtent(1 2 3)
93 pascal GetTextMetrics(word ptr) GetTextMetrics(1 2)
94 pascal GetViewportExt(word) GetViewportExt(1)
95 pascal GetViewportOrg(word) GetViewportOrg(1)
96 pascal GetWindowExt(word) GetWindowExt(1)
97 pascal GetWindowOrg(word) GetWindowOrg(1)
98 pascal IntersectVisRect(word s_word s_word s_word s_word)
IntersectVisRect(1 2 3 4 5)
99 pascal LPtoDP(word ptr s_word) LPtoDP(1 2 3)
100 pascal LineDDA(s_word s_word s_word s_word ptr long)
LineDDA(1 2 3 4 5 6)
101 pascal OffsetRgn(word s_word s_word) OffsetRgn(1 2 3)
102 pascal OffsetVisRgn(word s_word s_word) OffsetVisRgn(1 2 3)
103 pascal PtVisible(word s_word s_word) PtVisible(1 2 3)
104 pascal RectVisibleOld(word ptr) RectVisible(1 2)
105 pascal SelectVisRgn(word word) SelectVisRgn(1 2)
106 pascal SetBitmapBits(word long ptr) SetBitmapBits(1 2 3)
117 pascal SetDCOrg(word s_word s_word) SetDCOrg(1 2 3)
129 pascal SaveVisRgn(word) SaveVisRgn(1)
130 pascal RestoreVisRgn(word) RestoreVisRgn(1)
131 pascal InquireVisRgn(word) InquireVisRgn(1)
134 pascal GetRgnBox(word ptr) GetRgnBox(1 2)
148 pascal SetBrushOrg(word s_word s_word) SetBrushOrg(1 2 3)
149 pascal GetBrushOrg(word) GetBrushOrg(1)
150 pascal UnrealizeObject(word) UnrealizeObject(1)
161 pascal PtInRegion(word s_word s_word) PtInRegion(1 2 3)
162 pascal GetBitmapDimension(word) GetBitmapDimension(1)
163 pascal SetBitmapDimension(word s_word s_word) SetBitmapDimension(1 2 3)
172 pascal SetRectRgn(word s_word s_word s_word s_word) SetRectRgn(1 2 3 4 5)
173 pascal GetClipRgn(word) GetClipRgn(1)
179 pascal GetDCState(word) GetDCState(1)
180 pascal SetDCState(word word) SetDCState(1 2)
181 pascal RectInRegionOld(word ptr) RectInRegion(1 2)
345 pascal GetTextAlign(word) GetTextAlign(1)
346 pascal SetTextAlign(word word) SetTextAlign(1 2)
348 pascal Chord(word s_word s_word s_word s_word s_word s_word s_word s_word)
Chord(1 2 3 4 5 6 7 8 9)
360 pascal CreatePalette(ptr) CreatePalette(1)
363 pascal GetPaletteEntries(word word word ptr) GetPaletteEntries(1 2 3 4)
364 pascal SetPaletteEntries(word word word ptr) SetPaletteEntries(1 2 3 4)
370 pascal GetNearestPaletteIndex(word long) GetNearestPaletteIndex(1 2)
411 pascal GetCurLogFont(word) GetCurLogFont(1)
440 pascal SetDIBits(word word word word ptr ptr word) SetDIBits(1 2 3 4 5 6 7)
441 pascal GetDIBits(word word word word ptr ptr word) GetDIBits(1 2 3 4 5 6 7)
442 pascal CreateDIBitmap(word ptr long ptr ptr word)
CreateDIBitmap(1 2 3 4 5 6)
444 pascal CreateRoundRectRgn(s_word s_word s_word s_word s_word s_word)
CreateRoundRectRgn(1 2 3 4 5 6)
445 pascal CreateDIBPatternBrush(word word) CreateDIBPatternBrush(1 2)
451 pascal CreatePolyPolygonRgn(ptr ptr word word)
CreatePolyPolygonRgn(1 2 3 4)
465 pascal RectVisible(word ptr) RectVisible(1 2)
466 pascal RectInRegion(word ptr) RectInRegion(1 2)
468 pascal GetBitmapDimensionEx(word ptr) GetBitmapDimensionEx(1 2)
469 pascal GetBrushOrgEx(word ptr) GetBrushOrgEx(1 2)
470 pascal GetCurrentPositionEx(word ptr) GetCurrentPositionEx(1 2)
471 pascal GetTextExtentPoint(word ptr s_word ptr) GetTextExtentPoint(1 2 3 4)
472 pascal GetViewportExtEx(word ptr) GetViewportExtEx(1 2)
473 pascal GetViewportOrgEx(word ptr) GetViewportOrgEx(1 2)
474 pascal GetWindowExtEx(word ptr) GetWindowExtEx(1 2)
475 pascal GetWindowOrgEx(word ptr) GetWindowOrgEx(1 2)
476 pascal OffsetViewportOrgEx(word s_word s_word ptr)
OffsetViewportOrgEx(1 2 3 4)
477 pascal OffsetWindowOrgEx(word s_word s_word ptr) OffsetWindowOrgEx(1 2 3 4)
478 pascal SetBitmapDimensionEx(word s_word s_word ptr)
SetBitmapDimensionEx(1 2 3 4)
479 pascal SetViewportExtEx(word s_word s_word ptr) SetViewportExtEx(1 2 3 4)
480 pascal SetViewportOrgEx(word s_word s_word ptr) SetViewportOrgEx(1 2 3 4)
481 pascal SetWindowExtEx(word s_word s_word ptr) SetWindowExtEx(1 2 3 4)
482 pascal SetWindowOrgEx(word s_word s_word ptr) SetWindowOrgEx(1 2 3 4)
483 pascal MoveToEx(word s_word s_word ptr) MoveToEx(1 2 3 4)
484 pascal ScaleViewportExtEx(word s_word s_word s_word s_word ptr)
ScaleViewportExtEx(1 2 3 4 5 6)
485 pascal ScaleWindowExtEx(word s_word s_word s_word s_word ptr)
ScaleWindowExtEx(1 2 3 4 5 6)

View File

@ -5,7 +5,17 @@ id 1
length 410 length 410
3 return GetVersion 0 0x301 3 return GetVersion 0 0x301
5 pascal LocalAlloc(word word) HEAP_LocalAlloc(1 2) 4 pascal LocalInit(word word word) LocalInit(1 2 3)
5 pascal LocalAlloc(word word) LocalAlloc(1 2)
6 pascal LocalReAlloc(word word word) LocalReAlloc(1 2 3)
7 pascal LocalFree(word) LocalFree(1)
8 pascal LocalLock(word) LocalLock(1)
9 pascal LocalUnlock(word) LocalUnlock(1)
10 pascal LocalSize(word) LocalSize(1)
11 pascal LocalHandle(word) ReturnArg(1)
12 pascal LocalFlags(word) LocalFlags(1)
13 pascal LocalCompact(word) LocalCompact(1)
14 return LocalNotify 4 0
15 pascal GlobalAlloc(word long) GlobalAlloc(1 2) 15 pascal GlobalAlloc(word long) GlobalAlloc(1 2)
16 pascal GlobalReAlloc(word long word) GlobalReAlloc(1 2 3) 16 pascal GlobalReAlloc(word long word) GlobalReAlloc(1 2 3)
17 pascal GlobalFree(word) GlobalFree(1) 17 pascal GlobalFree(word) GlobalFree(1)
@ -19,13 +29,22 @@ length 410
25 pascal GlobalCompact(long) GlobalCompact(1) 25 pascal GlobalCompact(long) GlobalCompact(1)
30 pascal WaitEvent(word) KERNEL_WaitEvent(1) 30 pascal WaitEvent(word) KERNEL_WaitEvent(1)
49 pascal GetModuleFileName(word ptr s_word) KERNEL_GetModuleFileName(1 2 3) 49 pascal GetModuleFileName(word ptr s_word) KERNEL_GetModuleFileName(1 2 3)
50 pascal GetProcAddress(word ptr) GetProcAddress(1 2)
51 pascal MakeProcInstance(ptr word) CALLBACK_MakeProcInstance(1 2) 51 pascal MakeProcInstance(ptr word) CALLBACK_MakeProcInstance(1 2)
91 pascal InitTask() KERNEL_InitTask() 52 pascal FreeProcInstance(ptr) FreeProcInstance(1)
91 register InitTask(word word word word word
word word word word word)
KERNEL_InitTask()
102 register DOS3Call(word word word word word 102 register DOS3Call(word word word word word
word word word word word) word word word word word)
KERNEL_DOS3Call(1 2 3 4 5 6 7 8 9 10) KERNEL_DOS3Call()
111 pascal GlobalWire(word) GlobalLock(1) 111 pascal GlobalWire(word) GlobalLock(1)
112 pascal GlobalUnWire(word) GlobalUnlock(1) 112 pascal GlobalUnWire(word) GlobalUnlock(1)
121 return LocalShrink 4 0
127 pascal GetPrivateProfileInt(ptr ptr s_word ptr)
GetPrivateProfileInt(1 2 3 4)
128 pascal GetPrivateProfileString(ptr ptr ptr ptr s_word ptr)
GetPrivateProfileString(1 2 3 4 5 6)
131 pascal GetDOSEnvironment() GetDOSEnvironment() 131 pascal GetDOSEnvironment() GetDOSEnvironment()
132 return GetWinFlags 0 0x413 132 return GetWinFlags 0 0x413
154 return GlobalNotify 4 0 154 return GlobalNotify 4 0

View File

@ -31,6 +31,10 @@ struct dll_name_table_entry_s dll_builtin_table[N_BUILTINS] =
unsigned short *Stack16Frame; unsigned short *Stack16Frame;
extern unsigned long IF1632_Saved16_esp;
extern unsigned long IF1632_Saved16_ebp;
extern unsigned short IF1632_Saved16_ss;
/********************************************************************** /**********************************************************************
* DLLRelay * DLLRelay
* *
@ -61,6 +65,7 @@ DLLRelay(unsigned int func_num, unsigned int seg_off)
void *arg_ptr; void *arg_ptr;
int (*func_ptr)(); int (*func_ptr)();
int i; int i;
int ret_val;
/* /*
* Determine address of arguments. * Determine address of arguments.
@ -75,18 +80,35 @@ DLLRelay(unsigned int func_num, unsigned int seg_off)
ordinal = func_num & 0xffff; ordinal = func_num & 0xffff;
dll_p = &dll_builtin_table[dll_id].dll_table[ordinal]; dll_p = &dll_builtin_table[dll_id].dll_table[ordinal];
#ifdef RELAY_DEBUG #ifdef DEBUG_RELAY
{ {
unsigned int *ret_addr; unsigned int *ret_addr;
unsigned short *stack_p; unsigned short *stack_p;
ret_addr = (unsigned int *) ((char *) seg_off + 0x14); ret_addr = (unsigned int *) ((char *) seg_off + 0x14);
printf("RELAY: Calling %s.%d, 16-bit stack at %04x:%04x, ", printf("Calling %s (%s.%d), 16-bit stack at %04x:%04x, ",
dll_p->export_name,
dll_builtin_table[dll_id].dll_name, ordinal, dll_builtin_table[dll_id].dll_name, ordinal,
seg_off >> 16, seg_off & 0xffff); seg_off >> 16, seg_off & 0xffff);
printf("return to %08x\n", *ret_addr); printf("return to %08x\n", *ret_addr);
printf(" ESP %08x, EBP %08x, SS %04x\n",
IF1632_Saved16_esp, IF1632_Saved16_ebp,
IF1632_Saved16_ss);
#ifdef STACK_DEBUG if (strcmp("GetMessage", dll_p->export_name) == 0 &&
seg_off == 0x00972526 &&
*ret_addr == 0x004700cd &&
IF1632_Saved16_esp == 0x2526 &&
IF1632_Saved16_ebp == 0x2534 &&
IF1632_Saved16_ss == 0x0097)
printf("ACK!!\n");
#if 0
IF1632_Saved16_esp &= 0x0000ffff;
IF1632_Saved16_ebp &= 0x0000ffff;
#endif
#ifdef DEBUG_STACK
stack_p = (unsigned short *) seg_off; stack_p = (unsigned short *) seg_off;
for (i = 0; i < 24; i++, stack_p++) for (i = 0; i < 24; i++, stack_p++)
{ {
@ -95,9 +117,9 @@ DLLRelay(unsigned int func_num, unsigned int seg_off)
printf("\n"); printf("\n");
} }
printf("\n"); printf("\n");
#endif /* STACK_DEBUG */ #endif /* DEBUG_STACK */
} }
#endif /* RELAY_DEBUG */ #endif /* DEBUG_RELAY */
/* /*
* Make sure we have a handler defined for this call. * Make sure we have a handler defined for this call.
@ -155,12 +177,21 @@ DLLRelay(unsigned int func_num, unsigned int seg_off)
/* /*
* Call the handler * Call the handler
*/ */
return (*func_ptr)(arg_table[0], arg_table[1], arg_table[2], ret_val = (*func_ptr)(arg_table[0], arg_table[1], arg_table[2],
arg_table[3], arg_table[4], arg_table[5], arg_table[3], arg_table[4], arg_table[5],
arg_table[6], arg_table[7], arg_table[8], arg_table[6], arg_table[7], arg_table[8],
arg_table[9], arg_table[10], arg_table[11], arg_table[9], arg_table[10], arg_table[11],
arg_table[12], arg_table[13], arg_table[14], arg_table[12], arg_table[13], arg_table[14],
arg_table[15]); arg_table[15]);
#ifdef DEBUG_RELAY
printf("Returning %08.8x from %s (%s.%d)\n",
ret_val,
dll_p->export_name,
dll_builtin_table[dll_id].dll_name, ordinal);
#endif
return ret_val;
} }
/********************************************************************** /**********************************************************************

85
if1632/user.spec Normal file
View File

@ -0,0 +1,85 @@
# $Id: user.spec,v 1.3 1993/07/04 04:04:21 root Exp root $
#
name user
id 2
length 540
1 pascal MessageBox(word ptr ptr word) MessageBox(1 2 3 4)
5 pascal InitApp(word) USER_InitApp(1)
6 pascal PostQuitMessage(word) PostQuitMessage(1)
10 pascal SetTimer(word word word ptr) SetTimer(1 2 3 4)
11 pascal SetSystemTimer(word word word ptr) SetSystemTimer(1 2 3 4)
12 pascal KillTimer(word word) KillTimer(1 2)
13 pascal GetTickCount() GetTickCount()
14 return GetTimerResolution 0 1000
15 pascal GetCurrentTime() GetTickCount()
18 pascal SetCapture(word) SetCapture(1)
19 pascal ReleaseCapture() ReleaseCapture()
31 pascal IsIconic(word) IsIconic(1)
33 pascal GetClientRect(word ptr) GetClientRect(1 2)
39 pascal BeginPaint(word ptr) BeginPaint(1 2)
40 pascal EndPaint(word ptr) EndPaint(1 2)
41 pascal CreateWindow(ptr ptr long s_word s_word s_word s_word word word word ptr)
CreateWindow(1 2 3 4 5 6 7 8 9 10 11)
42 pascal ShowWindow(word word) ShowWindow(1 2)
53 pascal DestroyWindow(word) DestroyWindow(1)
57 pascal RegisterClass(ptr) RegisterClass(1)
66 pascal GetDC(word) GetDC(1)
68 pascal ReleaseDC(word word) ReleaseDC(1 2)
72 pascal SetRect(ptr s_word s_word s_word s_word) SetRect(1 2 3 4 5)
73 pascal SetRectEmpty(ptr) SetRectEmpty(1)
74 pascal CopyRect(ptr ptr) CopyRect(1 2)
75 pascal IsRectEmpty(ptr) IsRectEmpty(1)
76 pascal PtInRect(ptr long) PtInRect(1 2)
77 pascal OffsetRect(ptr s_word s_word) OffsetRect(1 2 3)
78 pascal InflateRect(ptr s_word s_word) InflateRect(1 2 3)
79 pascal IntersectRect(ptr ptr ptr) IntersectRect(1 2 3)
80 pascal UnionRect(ptr ptr ptr) UnionRect(1 2 3)
81 pascal FillRect(word ptr word) FillRect(1 2 3)
82 pascal InvertRect(word ptr) InvertRect(1 2)
85 pascal DrawText(word ptr s_word ptr word) DrawText(1 2 3 4 5)
102 pascal AdjustWindowRect(ptr long word) AdjustWindowRect(1 2 3)
104 pascal MessageBeep(word) MessageBeep(1)
106 pascal GetKeyState(word) GetKeyState(1)
107 pascal DefWindowProc(word word word long) DefWindowProc(1 2 3 4)
108 pascal GetMessage(ptr word word word) GetMessage(1 2 3 4)
109 pascal PeekMessage(ptr word word word word) PeekMessage(1 2 3 4 5)
110 pascal PostMessage(word word word long) PostMessage(1 2 3 4)
111 pascal SendMessage(word word word long) SendMessage(1 2 3 4)
113 pascal TranslateMessage(ptr) TranslateMessage(1)
114 pascal DispatchMessage(ptr) DispatchMessage(1)
118 pascal RegisterWindowMessage(ptr) RegisterWindowMessage(1)
119 pascal GetMessagePos() GetMessagePos()
120 pascal GetMessageTime() GetMessageTime()
124 pascal UpdateWindow(word) UpdateWindow(1)
125 pascal InvalidateRect(word ptr word) InvalidateRect(1 2 3)
126 pascal InvalidateRgn(word word word) InvalidateRgn(1 2 3)
127 pascal ValidateRect(word ptr) ValidateRect(1 2)
128 pascal ValidateRgn(word word) ValidateRgn(1 2)
129 pascal GetClassWord(word s_word) GetClassWord(1 2)
130 pascal SetClassWord(word s_word word) SetClassWord(1 2 3)
131 pascal GetClassLong(word s_word) GetClassLong(1 2)
132 pascal SetClassLong(word s_word long) SetClassLong(1 2 3)
150 pascal LoadMenu(word ptr) LoadMenu(1 2)
151 pascal CreateMenu() CreateMenu()
154 pascal CheckMenu(word word word) CheckMenu(1 2 3)
157 pascal GetMenu(word) GetMenu(1)
158 pascal SetMenu(word word) SetMenu(1 2)
173 pascal LoadCursor(word ptr) LoadCursor(1 2)
174 pascal LoadIcon(word ptr) LoadIcon(1 2)
175 pascal LoadBitmap(word ptr) LoadBitmap(1 2)
176 pascal LoadString(word word ptr s_word) LoadString(1 2 3 4)
179 pascal GetSystemMetrics(word) GetSystemMetrics(1)
182 pascal KillSystemTimer(word word) KillSystemTimer(1 2)
190 pascal GetUpdateRect(word ptr word) GetUpdateRect(1 2 3)
237 pascal GetUpdateRgn(word word word) GetUpdateRgn(1 2 3)
244 pascal EqualRect(ptr ptr) EqualRect(1 2)
266 pascal SetMessageQueue(word) SetMessageQueue(1)
288 pascal GetMessageExtraInfo() GetMessageExtraInfo()
324 pascal FillWindow(word word word word) FillWindow(1 2 3 4)
325 pascal PaintRect(word word word word ptr) PaintRect(1 2 3 4 5)
334 pascal GetQueueStatus(word) GetQueueStatus(1)
335 pascal GetInputState() GetInputState()
373 pascal SubtractRect(ptr ptr ptr) SubtractRect(1 2 3)
403 pascal UnregisterClass(ptr word) UnregisterClass(1 2)
411 pascal AppendMenu(word word word ptr) AppendMenu(1 2 3 4)

View File

@ -0,0 +1,7 @@
#define check_bitmap_width 10
#define check_bitmap_height 10
#define check_bitmap_x_hot 0
#define check_bitmap_y_hot 0
static char check_bitmap_bits[] = {
0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x03, 0x80, 0x01, 0xc0, 0x00,
0x63, 0x00, 0x36, 0x00, 0x1c, 0x00, 0x08, 0x00};

View File

@ -0,0 +1,7 @@
#define nocheck_bitmap_width 10
#define nocheck_bitmap_height 10
#define nocheck_bitmap_x_hot 0
#define nocheck_bitmap_y_hot 0
static char nocheck_bitmap_bits[] = {
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};

View File

@ -11,6 +11,7 @@
#define CLASS_MAGIC 0x4b4e /* 'NK' */ #define CLASS_MAGIC 0x4b4e /* 'NK' */
/* !! Don't change this structure (see GetClassLong()) */
typedef struct tagCLASS typedef struct tagCLASS
{ {
HCLASS hNext; /* Next class */ HCLASS hNext; /* Next class */
@ -23,9 +24,6 @@ typedef struct tagCLASS
} CLASS; } CLASS;
/* The caller must GlobalUnlock the pointer returned
* by these functions (except when NULL).
*/
HCLASS CLASS_FindClassByName( char * name, CLASS **ptr ); HCLASS CLASS_FindClassByName( char * name, CLASS **ptr );
CLASS * CLASS_FindClassPtr( HCLASS hclass ); CLASS * CLASS_FindClassPtr( HCLASS hclass );

24
include/dce.h Normal file
View File

@ -0,0 +1,24 @@
/*
* USER DCE definitions
*
* Copyright 1993 Alexandre Julliard
*/
#ifndef DCE_H
#define DCE_H
#include "windows.h"
typedef struct tagDCE
{
HANDLE hNext;
HWND hwndCurrent;
HDC hdc;
BYTE flags;
BOOL inUse;
WORD xOrigin;
WORD yOrigin;
} DCE;
#endif /* DCE_H */

287
include/gdi.h Normal file
View File

@ -0,0 +1,287 @@
/*
* GDI definitions
*
* Copyright 1993 Alexandre Julliard
*/
#ifndef GDI_H
#define GDI_H
#include <X11/Intrinsic.h>
#include "windows.h"
#include "segmem.h"
#include "heap.h"
/* GDI objects magic numbers */
#define PEN_MAGIC 0x4f47
#define BRUSH_MAGIC 0x4f48
#define FONT_MAGIC 0x4f49
#define PALETTE_MAGIC 0x4f4a
#define BITMAP_MAGIC 0x4f4b
#define REGION_MAGIC 0x4f4c
#define DC_MAGIC 0x4f4d
#define DISABLED_DC_MAGIC 0x4f4e
#define META_DC_MAGIC 0x4f4f
#define METAFILE_MAGIC 0x4f50
#define METAFILE_DC_MAGIC 0x4f51
typedef struct tagREGION
{
WORD type;
RECT box;
Pixmap pixmap;
} REGION;
typedef struct tagGDIOBJHDR
{
HANDLE hNext;
WORD wMagic;
DWORD dwCount;
WORD wMetaList;
} GDIOBJHDR;
typedef struct tagBRUSHOBJ
{
GDIOBJHDR header;
LOGBRUSH logbrush __attribute__ ((packed));
} BRUSHOBJ;
typedef struct tagPENOBJ
{
GDIOBJHDR header;
LOGPEN logpen __attribute__ ((packed));
} PENOBJ;
typedef struct tagPALETTEOBJ
{
GDIOBJHDR header;
LOGPALETTE logpalette __attribute__ ((packed));
} PALETTEOBJ;
typedef struct tagFONTOBJ
{
GDIOBJHDR header;
LOGFONT logfont __attribute__ ((packed));
} FONTOBJ;
typedef struct tagBITMAPOBJ
{
GDIOBJHDR header;
HANDLE hBitmap;
BOOL bSelected;
HDC hdc;
SIZE size;
} BITMAPOBJ;
typedef struct tagRGNOBJ
{
GDIOBJHDR header;
REGION region;
} RGNOBJ;
typedef struct
{
WORD version; /* 0: driver version */
WORD technology; /* 2: device technology */
WORD horzSize; /* 4: width of display in mm */
WORD vertSize; /* 6: height of display in mm */
WORD horzRes; /* 8: width of display in pixels */
WORD vertRes; /* 10: width of display in pixels */
WORD bitsPixel; /* 12: bits per pixel */
WORD planes; /* 14: color planes */
WORD numBrushes; /* 16: device-specific brushes */
WORD numPens; /* 18: device-specific pens */
WORD numMarkers; /* 20: device-specific markers */
WORD numFonts; /* 22: device-specific fonts */
WORD numColors; /* 24: size of color table */
WORD pdeviceSize; /* 26: size of PDEVICE structure */
WORD curveCaps; /* 28: curve capabilities */
WORD lineCaps; /* 30: line capabilities */
WORD polygonalCaps; /* 32: polygon capabilities */
WORD textCaps; /* 34: text capabilities */
WORD clipCaps; /* 36: clipping capabilities */
WORD rasterCaps; /* 38: raster capabilities */
WORD aspectX; /* 40: relative width of device pixel */
WORD aspectY; /* 42: relative height of device pixel */
WORD aspectXY; /* 44: relative diagonal width of device pixel */
WORD pad1[21]; /* 46-86: reserved */
WORD logPixelsX; /* 88: pixels / logical X inch */
WORD logPixelsY; /* 90: pixels / logical Y inch */
WORD pad2[6]; /* 92-102: reserved */
WORD sizePalette; /* 104: entries in system palette */
WORD numReserved; /* 106: reserved entries */
WORD colorRes; /* 108: color resolution */
} DeviceCaps;
/* Device independent DC information */
typedef struct
{
int flags;
DeviceCaps *devCaps;
HANDLE hMetaFile;
HRGN hClipRgn; /* Clip region */
HRGN hVisRgn; /* Visible region */
HRGN hGCClipRgn; /* GC clip region (ClipRgn AND VisRgn) */
HPEN hPen;
HBRUSH hBrush;
HFONT hFont;
HBITMAP hBitmap;
HANDLE hDevice;
HPALETTE hPalette;
WORD ROPmode;
WORD polyFillMode;
WORD stretchBltMode;
WORD relAbsMode;
WORD backgroundMode;
COLORREF backgroundColor;
COLORREF textColor;
int backgroundPixel;
int textPixel;
short brushOrgX;
short brushOrgY;
WORD textAlign; /* Text alignment from SetTextAlign() */
short charExtra; /* Spacing from SetTextCharacterExtra() */
short breakTotalExtra; /* Total extra space for justification */
short breakCount; /* Break char. count */
short breakExtra; /* breakTotalExtra / breakCount */
short breakRem; /* breakTotalExtra % breakCount */
BYTE planes;
BYTE bitsPerPixel;
WORD MapMode;
short DCOrgX; /* DC origin */
short DCOrgY;
short CursPosX; /* Current position */
short CursPosY;
short WndOrgX;
short WndOrgY;
short WndExtX;
short WndExtY;
short VportOrgX;
short VportOrgY;
short VportExtX;
short VportExtY;
} WIN_DC_INFO;
/* X physical pen */
typedef struct
{
int style;
int pixel;
int width;
} X_PHYSPEN;
/* X physical brush */
typedef struct
{
int style;
int fillStyle;
int pixel;
Pixmap pixmap;
} X_PHYSBRUSH;
/* X physical font */
typedef struct
{
XFontStruct * fstruct;
TEXTMETRIC metrics;
} X_PHYSFONT;
/* X-specific DC information */
typedef struct
{
GC gc; /* X Window GC */
Drawable drawable;
Widget widget;
X_PHYSFONT font;
X_PHYSPEN pen;
X_PHYSBRUSH brush;
} X_DC_INFO;
typedef struct tagDC
{
GDIOBJHDR header;
WORD saveLevel;
WIN_DC_INFO w;
union
{
X_DC_INFO x;
/* other devices (e.g. printer) */
} u;
} DC;
/* DC flags */
#define DC_MEMORY 1 /* It is a memory DC */
#define DC_SAVED 2 /* It is a saved DC */
/* Last 32 bytes are reserved for stock object handles */
#define GDI_HEAP_SIZE 0xffe0
/* First handle possible for stock objects (must be >= GDI_HEAP_SIZE) */
#define FIRST_STOCK_HANDLE GDI_HEAP_SIZE
/* Stock objects handles */
#define STOCK_WHITE_BRUSH (FIRST_STOCK_HANDLE + WHITE_BRUSH)
#define STOCK_LTGRAY_BRUSH (FIRST_STOCK_HANDLE + LTGRAY_BRUSH)
#define STOCK_GRAY_BRUSH (FIRST_STOCK_HANDLE + GRAY_BRUSH)
#define STOCK_DKGRAY_BRUSH (FIRST_STOCK_HANDLE + DKGRAY_BRUSH)
#define STOCK_BLACK_BRUSH (FIRST_STOCK_HANDLE + BLACK_BRUSH)
#define STOCK_NULL_BRUSH (FIRST_STOCK_HANDLE + NULL_BRUSH)
#define STOCK_HOLLOW_BRUSH (FIRST_STOCK_HANDLE + HOLLOW_BRUSH)
#define STOCK_WHITE_PEN (FIRST_STOCK_HANDLE + WHITE_PEN)
#define STOCK_BLACK_PEN (FIRST_STOCK_HANDLE + BLACK_PEN)
#define STOCK_NULL_PEN (FIRST_STOCK_HANDLE + NULL_PEN)
#define STOCK_OEM_FIXED_FONT (FIRST_STOCK_HANDLE + OEM_FIXED_FONT)
#define STOCK_ANSI_FIXED_FONT (FIRST_STOCK_HANDLE + ANSI_FIXED_FONT)
#define STOCK_ANSI_VAR_FONT (FIRST_STOCK_HANDLE + ANSI_VAR_FONT)
#define STOCK_SYSTEM_FONT (FIRST_STOCK_HANDLE + SYSTEM_FONT)
#define STOCK_DEVICE_DEFAULT_FONT (FIRST_STOCK_HANDLE + DEVICE_DEFAULT_FONT)
#define STOCK_DEFAULT_PALETTE (FIRST_STOCK_HANDLE + DEFAULT_PALETTE)
#define STOCK_SYSTEM_FIXED_FONT (FIRST_STOCK_HANDLE + SYSTEM_FIXED_FONT)
#define NB_STOCK_OBJECTS (SYSTEM_FIXED_FONT + 1)
#define FIRST_STOCK_FONT STOCK_OEM_FIXED_FONT
#define LAST_STOCK_FONT STOCK_SYSTEM_FIXED_FONT
/* Device <-> logical coords conversion */
#define XDPTOLP(dc,x) \
(((x)-(dc)->w.VportOrgX) * (dc)->w.WndExtX / (dc)->w.VportExtX+(dc)->w.WndOrgX)
#define YDPTOLP(dc,y) \
(((y)-(dc)->w.VportOrgY) * (dc)->w.WndExtY / (dc)->w.VportExtY+(dc)->w.WndOrgY)
#define XLPTODP(dc,x) \
(((x)-(dc)->w.WndOrgX) * (dc)->w.VportExtX / (dc)->w.WndExtX+(dc)->w.VportOrgX)
#define YLPTODP(dc,y) \
(((y)-(dc)->w.WndOrgY) * (dc)->w.VportExtY / (dc)->w.WndExtY+(dc)->w.VportOrgY)
/* GDI local heap */
extern MDESC *GDI_Heap;
#define GDI_HEAP_ALLOC(f,size) ((int)HEAP_Alloc(&GDI_Heap,f,size) & 0xffff)
#define GDI_HEAP_ADDR(handle) ((void *)(handle | ((int)GDI_Heap & 0xffff0000)))
#define GDI_HEAP_FREE(handle) (HEAP_Free(&GDI_Heap,GDI_HEAP_ADDR(handle)))
extern HANDLE GDI_AllocObject( WORD, WORD );
extern BOOL GDI_FreeObject( HANDLE );
extern GDIOBJHDR * GDI_GetObjPtr( HANDLE, WORD );
extern Display * XT_display;
extern Screen * XT_screen;
#endif /* GDI_H */

View File

@ -9,13 +9,18 @@
typedef struct heap_mem_desc_s typedef struct heap_mem_desc_s
{ {
struct heap_mem_desc_s *prev, *next; struct heap_mem_desc_s *prev, *next;
int length; unsigned short length;
unsigned char lock;
unsigned char flags;
} MDESC; } MDESC;
extern void HEAP_Init(MDESC **free_list, void *start, int length); extern void HEAP_Init(MDESC **free_list, void *start, int length);
extern void *HEAP_Alloc(MDESC **free_list, int flags, int bytes); extern void *HEAP_Alloc(MDESC **free_list, int flags, int bytes);
extern void HEAP_Free(MDESC **free_list, void *block); extern int HEAP_Free(MDESC **free_list, void *block);
extern void *HEAP_ReAlloc(MDESC **free_list, void *old_block, extern void *HEAP_ReAlloc(MDESC **free_list, void *old_block,
int new_size, unsigned int flags); int new_size, unsigned int flags);
extern void *GlobalQuickAlloc(int size);
extern unsigned int GlobalHandleFromPointer(void *block);
#endif /* HEAP_H */ #endif /* HEAP_H */

67
include/menu.h Normal file
View File

@ -0,0 +1,67 @@
/* $Id$
*
* Menu definitions
*/
#ifndef MENU_H
#define MENU_H
#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Core.h>
#include <X11/Xaw/Form.h>
#include <X11/Xaw/Command.h>
#include <X11/Xaw/Box.h>
#include "windows.h"
typedef struct tagMENUITEM
{
struct tagMENUITEM *next;
struct tagMENUITEM *prev;
struct tagMENUITEM *child;
struct tagMENUITEM *parent;
WORD item_flags;
WORD item_id;
char *item_text;
Widget w;
Widget menu_w;
char menu_name[10];
} MENUITEM;
typedef struct tagMENUBAR
{
struct tagMENUBAR *next;
HANDLE menuDescription; /* Memory containing menu desc. */
HWND ownerWnd; /* Owner window */
int nItems; /* Number of items on menu */
Widget parentWidget; /* Parent of menu widget */
Widget menuBarWidget; /* Widget to contain menu options */
MENUITEM *firstItem;
} MENUBAR, *LPMENUBAR;
typedef struct
{
WORD version; /* Should be zero */
WORD reserved; /* Must be zero */
} MENU_HEADER;
typedef struct
{
WORD item_flags; /* See windows.h */
char item_text[1]; /* Text for menu item */
} MENU_POPUPITEM;
typedef struct
{
WORD item_flags; /* See windows.h */
WORD item_id; /* Control Id for menu item */
char item_text[1]; /* Text for menu item */
} MENU_NORMALITEM;
extern LPMENUBAR MENU_CreateMenuBar(Widget parent, HANDLE instance,
HWND wnd, char *menu_name, int width);
extern LPMENUBAR MENU_UseMenu(Widget parent, HANDLE instance,
HWND wnd, HMENU hmenu, int width);
#endif /* MENU_H */

View File

@ -133,7 +133,9 @@ struct relocation_entry_s
#define NE_RELTYPE_ORDINAL 1 #define NE_RELTYPE_ORDINAL 1
#define NE_RELTYPE_NAME 2 #define NE_RELTYPE_NAME 2
#define NE_RELTYPE_OSFIXUP 3 #define NE_RELTYPE_OSFIXUP 3
/* Used by Windows 3.0 programs, like when getting selector to be
given to makeprocinst */
#define NE_RELTYPE_INT1 4
/* /*
* DOS PSP * DOS PSP
*/ */
@ -151,6 +153,7 @@ struct dos_psp_s
unsigned short pspReserved3[23]; unsigned short pspReserved3[23];
unsigned char pspFCB_1[16]; unsigned char pspFCB_1[16];
unsigned char pspFCB_2[16]; unsigned char pspFCB_2[16];
unsigned char pspReserved4[4];
unsigned char pspCommandTailCount; unsigned char pspCommandTailCount;
unsigned char pspCommandTail[128]; unsigned char pspCommandTail[128];
}; };

22
include/regfunc.h Normal file
View File

@ -0,0 +1,22 @@
/* $Id$
*/
#ifndef REGFUNC_H
#define REGFUNC_H
extern unsigned short *Stack16Frame;
#define _AX Stack16Frame[21]
#define _BX Stack16Frame[18]
#define _CX Stack16Frame[20]
#define _DX Stack16Frame[19]
#define _SP Stack16Frame[17]
#define _BP Stack16Frame[16]
#define _SI Stack16Frame[15]
#define _DI Stack16Frame[14]
#define _DS Stack16Frame[13]
#define _ES Stack16Frame[12]
extern void ReturnFromRegisterFunc(void);
#endif /* REGFUNC_H */

21
include/user.h Normal file
View File

@ -0,0 +1,21 @@
/*
* USER definitions
*
* Copyright 1993 Alexandre Julliard
*/
#ifndef USER_H
#define USER_H
#include "segmem.h"
#include "heap.h"
/* USER local heap */
extern MDESC *USER_Heap;
#define USER_HEAP_ALLOC(f,size) ((int)HEAP_Alloc(&USER_Heap,f,size) & 0xffff)
#define USER_HEAP_ADDR(handle) ((void *)(handle|((int)USER_Heap & 0xffff0000)))
#define USER_HEAP_FREE(handle) (HEAP_Free(&USER_Heap,USER_HEAP_ADDR(handle)))
#endif /* USER_H */

View File

@ -12,7 +12,7 @@
#include <X11/Core.h> #include <X11/Core.h>
#include "windows.h" #include "windows.h"
#include "menu.h"
#define WND_MAGIC 0x444e4957 /* 'WIND' */ #define WND_MAGIC 0x444e4957 /* 'WIND' */
@ -35,11 +35,17 @@ typedef struct tagWND
HANDLE hDCE; /* Window DC Entry (if CS_OWNDC) */ HANDLE hDCE; /* Window DC Entry (if CS_OWNDC) */
HMENU hmenuSystem; /* System menu */ HMENU hmenuSystem; /* System menu */
WORD wIDmenu; /* ID or hmenu (from CreateWindow) */ WORD wIDmenu; /* ID or hmenu (from CreateWindow) */
WORD flags; /* Misc. flags */
Widget shellWidget; /* For top-level windows */ Widget shellWidget; /* For top-level windows */
Widget winWidget; /* For all windows */ Widget winWidget; /* For all windows */
Widget compositeWidget;/* For top-level windows */
LPMENUBAR menuBarPtr; /* Menu bar */
WORD wExtra[1]; /* Window extra bytes */ WORD wExtra[1]; /* Window extra bytes */
} WND; } WND;
/* WND flags values */
#define WIN_ERASE_UPDATERGN 1 /* Update region needs erasing */
/* The caller must GlobalUnlock the pointer returned /* The caller must GlobalUnlock the pointer returned
* by this function (except when NULL). * by this function (except when NULL).

File diff suppressed because it is too large Load Diff

BIN
ldt.tar

Binary file not shown.

Binary file not shown.

18
loader/Makefile Normal file
View File

@ -0,0 +1,18 @@
CFLAGS=$(COPTS) $(DEBUGOPTS) -I$(INCLUDE_DIR)
OBJS=dump.o ldt.o ldtlib.o resource.o selector.o signal.o wine.o
default: loader.o
loader.o: $(OBJS)
$(LD) -r -o loader.o $(OBJS)
clean:
rm -f *.o *~ *.s dll_* *.a
depend:
$(CC) $(CFLAGS) -M *.c > .depend
ifeq (.depend,$(wildcard .depend))
include .depend
endif

View File

View File

@ -8,12 +8,12 @@ static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include <linux/head.h> #include <linux/head.h>
#include <linux/ldt.h> #include <linux/ldt.h>
_syscall2(int, modify_ldt, int, func, void *, ptr) _syscall3(int, modify_ldt, int, func, void *, ptr, unsigned long, bytecount)
int int
get_ldt(void *buffer) get_ldt(void *buffer)
{ {
return modify_ldt(0, buffer); return modify_ldt(0, buffer, 32 * sizeof(struct modify_ldt_ldt_s));
} }
int int
@ -31,5 +31,5 @@ set_ldt_entry(int entry, unsigned long base, unsigned int limit,
ldt_info.read_exec_only = read_only_flag; ldt_info.read_exec_only = read_only_flag;
ldt_info.limit_in_pages = limit_in_pages_flag; ldt_info.limit_in_pages = limit_in_pages_flag;
return modify_ldt(1, &ldt_info); return modify_ldt(1, &ldt_info, sizeof(ldt_info));
} }

View File

@ -6,160 +6,77 @@ static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include "prototypes.h" #include "prototypes.h"
#include "neexe.h" #include "neexe.h"
#include "windows.h" #include "windows.h"
#include "gdi.h"
#define MIN(a,b) ((a) < (b) ? (a) : (b)) #define MIN(a,b) ((a) < (b) ? (a) : (b))
typedef struct resource_data_s
{
int resource_type;
void *resource_data;
} RSCD;
int ResourceSizes[16] =
{
0, 0, sizeof(BITMAP), 0,
0, 0, 0, 0,
0, 0, 0, 0,
0, 0, 0, 0,
};
RSCD *Resources;
int ResourceArraySize;
/********************************************************************** /**********************************************************************
* ConvertCoreBitmap * ConvertCoreBitmap
*/ */
void * HBITMAP
ConvertCoreBitmap(BITMAPCOREHEADER *image, int image_size) ConvertCoreBitmap( HDC hdc, BITMAPCOREHEADER * image )
{ {
BITMAP *new_image; BITMAPINFO * bmpInfo;
char *old_p, *new_p; HBITMAP hbitmap;
int old_line_length, new_line_length; char * bits;
unsigned int handle; int i, size, n_colors;
int i;
int n_colors;
n_colors = 1 << image->bcBitCount; n_colors = 1 << image->bcBitCount;
handle = GlobalAlloc(GMEM_MOVEABLE,
image_size + sizeof(*new_image) + n_colors);
new_image = GlobalLock(handle);
#ifdef DEBUG_RESOURCE
printf("ConvertCoreBitmap: handle = %04x, new image = %08x\n",
handle, new_image);
#endif
if (new_image == NULL)
return NULL;
new_image->bmType = 0;
new_image->bmWidth = image->bcWidth;
new_image->bmHeight = image->bcHeight;
new_image->bmPlanes = image->bcPlanes;
new_image->bmBitsPixel = image->bcBitCount;
if (image->bcBitCount < 24) if (image->bcBitCount < 24)
{ {
RGBTRIPLE *old_color = (RGBTRIPLE *) (image + 1); size = sizeof(BITMAPINFOHEADER) + n_colors * sizeof(RGBQUAD);
RGBQUAD *new_color = (RGBQUAD *) (new_image + 1); bits = (char *) (image + 1) + (n_colors * sizeof(RGBTRIPLE));
for (i = 0; i < n_colors; i++)
{
memcpy(new_color, old_color, sizeof(*old_color));
new_color++;
old_color++;
}
old_p = (char *) old_color;
new_p = (char *) new_color;
old_line_length = image->bcWidth / (8 / image->bcBitCount);
} }
else else
{ {
old_p = (char *) (image + 1); size = sizeof(BITMAPINFOHEADER);
new_p = (char *) (new_image + 1); bits = (char *) (image + 1);
old_line_length = image->bcWidth * 3;
} }
bmpInfo = (BITMAPINFO *) malloc( size );
new_line_length = (old_line_length + 1) & ~1;
old_line_length = (old_line_length + 3) & ~3;
new_image->bmBits = (unsigned long) new_p; bmpInfo->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
new_image->bmWidthBytes = new_line_length; bmpInfo->bmiHeader.biWidth = image->bcWidth;
bmpInfo->bmiHeader.biHeight = image->bcHeight;
bmpInfo->bmiHeader.biPlanes = image->bcPlanes;
bmpInfo->bmiHeader.biBitCount = image->bcBitCount;
bmpInfo->bmiHeader.biCompression = 0;
bmpInfo->bmiHeader.biSizeImage = 0;
bmpInfo->bmiHeader.biXPelsPerMeter = 0;
bmpInfo->bmiHeader.biYPelsPerMeter = 0;
bmpInfo->bmiHeader.biClrUsed = 0;
bmpInfo->bmiHeader.biClrImportant = 0;
for (i = 0; i < image->bcHeight; i++) if (image->bcBitCount < 24)
{ {
memcpy(new_p, old_p, new_line_length); RGBTRIPLE * oldMap = (RGBTRIPLE *)(image + 1);
new_p += new_line_length; RGBQUAD * newMap = bmpInfo->bmiColors;
old_p += old_line_length; for (i = 0; i < n_colors; i++, oldMap++, newMap++)
{
newMap->rgbRed = oldMap->rgbtRed;
newMap->rgbGreen = oldMap->rgbtGreen;
newMap->rgbBlue = oldMap->rgbtBlue;
newMap->rgbReserved = 0;
}
} }
return new_image; hbitmap = CreateDIBitmap( hdc, &bmpInfo->bmiHeader, CBM_INIT,
bits, bmpInfo, DIB_RGB_COLORS );
free( bmpInfo );
return hbitmap;
} }
/********************************************************************** /**********************************************************************
* ConvertInfoBitmap * ConvertInfoBitmap
*/ */
void * HBITMAP
ConvertInfoBitmap(BITMAPINFOHEADER *image, int image_size) ConvertInfoBitmap( HDC hdc, BITMAPINFO * image )
{ {
#ifdef DEBUG_RESOURCE char * bits = ((char *)image) + DIB_BitmapInfoSize(image, DIB_RGB_COLORS);
printf("ConvertInfoBitmap: \n"); return CreateDIBitmap( hdc, &image->bmiHeader, CBM_INIT,
#endif bits, image, DIB_RGB_COLORS );
}
return NULL;
}
/**********************************************************************
* AddResource
*/
int
AddResource(int type, void *data)
{
RSCD *r;
int i;
int j;
/*
* Find free resource id.
*/
r = Resources;
for (i = 0; i < ResourceArraySize; i++, r++)
if (r->resource_type == 0)
break;
/*
* Do we need to add more resource slots?
*/
if (i == ResourceArraySize)
{
if (ResourceArraySize > 0)
r = realloc(Resources, (ResourceArraySize + 32) * sizeof(RSCD));
else
r = malloc(32 * sizeof(RSCD));
if (r == NULL)
return 0;
for (j = ResourceArraySize; j < ResourceArraySize + 32; j++)
r[j].resource_type = 0;
ResourceArraySize += 32;
Resources = r;
r = &Resources[i];
}
/*
* Add new resource to list.
*/
r->resource_type = type;
r->resource_data = data;
#ifdef DEBUG_RESOURCE
printf("AddResource: return handle %d\n", i + 1);
#endif
/*
* Return a unique handle.
*/
return i + 1;
}
/********************************************************************** /**********************************************************************
* FindResourceByNumber * FindResourceByNumber
*/ */
@ -227,12 +144,88 @@ FindResourceByNumber(struct resource_nameinfo_s *result_p,
return -1; return -1;
} }
/********************************************************************** /**********************************************************************
* RSC_LoadString * FindResourceByName
*/ */
int int
RSC_LoadString(int instance, int resource_id, char *buffer, int buflen) FindResourceByName(struct resource_nameinfo_s *result_p,
int type_id, char *resource_name)
{
struct resource_typeinfo_s typeinfo;
struct resource_nameinfo_s nameinfo;
unsigned short size_shift;
off_t old_pos, new_pos;
unsigned char nbytes;
char name[256];
int i;
/*
* Move to beginning of resource table.
*/
lseek(CurrentNEFile, (CurrentMZHeader->ne_offset +
CurrentNEHeader->resource_tab_offset), SEEK_SET);
/*
* Read block size.
*/
if (read(CurrentNEFile, &size_shift, sizeof(size_shift)) !=
sizeof(size_shift))
{
return -1;
}
/*
* Find resource.
*/
typeinfo.type_id = 0xffff;
while (typeinfo.type_id != 0)
{
if (read(CurrentNEFile, &typeinfo, sizeof(typeinfo)) !=
sizeof(typeinfo))
{
return -1;
}
if (typeinfo.type_id == type_id || type_id == -1)
{
for (i = 0; i < typeinfo.count; i++)
{
if (read(CurrentNEFile, &nameinfo, sizeof(nameinfo)) !=
sizeof(nameinfo))
{
return -1;
}
if (nameinfo.id & 0x8000)
continue;
old_pos = lseek(CurrentNEFile, 0, SEEK_CUR);
new_pos = (CurrentMZHeader->ne_offset +
CurrentNEHeader->resource_tab_offset +
nameinfo.id);
lseek(CurrentNEFile, new_pos, SEEK_SET);
read(CurrentNEFile, &nbytes, 1);
read(CurrentNEFile, name, nbytes);
lseek(CurrentNEFile, old_pos, SEEK_SET);
name[nbytes] = '\0';
if (strcasecmp(name, resource_name) == 0)
{
memcpy(result_p, &nameinfo, sizeof(nameinfo));
return size_shift;
}
}
}
}
return -1;
}
/**********************************************************************
* LoadString
*/
int
LoadString(HANDLE instance, WORD resource_id, LPSTR buffer, int buflen)
{ {
struct resource_nameinfo_s nameinfo; struct resource_nameinfo_s nameinfo;
unsigned short target_id; unsigned short target_id;
@ -274,17 +267,34 @@ RSC_LoadString(int instance, int resource_id, char *buffer, int buflen)
#endif #endif
return i; return i;
} }
/**********************************************************************
* LoadIcon
*/
HICON
LoadIcon(HANDLE instance, LPSTR icon_name)
{
return 0;
}
/**********************************************************************
* LoadCursor
*/
HCURSOR
LoadCursor(HANDLE instance, LPSTR cursor_name)
{
return 0;
}
/********************************************************************** /**********************************************************************
* RSC_LoadResource * RSC_LoadResource
*/ */
int HANDLE
RSC_LoadResource(int instance, char *rsc_name, int type) RSC_LoadResource(int instance, char *rsc_name, int type, int *image_size_ret)
{ {
struct resource_nameinfo_s nameinfo; struct resource_nameinfo_s nameinfo;
HANDLE hmem;
void *image; void *image;
void *rsc_image;
long *lp;
int image_size; int image_size;
int size_shift; int size_shift;
@ -308,7 +318,7 @@ RSC_LoadResource(int instance, char *rsc_name, int type)
*/ */
else else
{ {
size_shift = -1; size_shift = FindResourceByName(&nameinfo, type, rsc_name);
} }
if (size_shift == -1) if (size_shift == -1)
return 0; return 0;
@ -319,92 +329,65 @@ RSC_LoadResource(int instance, char *rsc_name, int type)
lseek(CurrentNEFile, ((int) nameinfo.offset << size_shift), SEEK_SET); lseek(CurrentNEFile, ((int) nameinfo.offset << size_shift), SEEK_SET);
image_size = nameinfo.length << size_shift; image_size = nameinfo.length << size_shift;
image = malloc(image_size); if (image_size_ret != NULL)
*image_size_ret = image_size;
hmem = GlobalAlloc(GMEM_MOVEABLE, image_size);
image = GlobalLock(hmem);
if (image == NULL || read(CurrentNEFile, image, image_size) != image_size) if (image == NULL || read(CurrentNEFile, image, image_size) != image_size)
{ {
free(image); GlobalFree(hmem);
return 0; return 0;
} }
/* GlobalUnlock(hmem);
* Convert bitmap to internal format. return hmem;
*/
lp = (long *) image;
if (*lp == sizeof(BITMAPCOREHEADER))
rsc_image = ConvertCoreBitmap(image, image_size);
else if (*lp == sizeof(BITMAPINFOHEADER))
rsc_image = ConvertInfoBitmap(image, image_size);
free(image);
#ifdef DEBUG_RESOURCE
printf("LoadResource: rsc_image = %08x\n", rsc_image);
#endif
/*
* Add to resource list.
*/
if (rsc_image)
return AddResource(type, rsc_image);
else
return 0;
} }
/********************************************************************** /**********************************************************************
* RSC_LoadIcon * RSC_LoadMenu
*/ */
int HANDLE
RSC_LoadIcon(int instance, char *icon_name) RSC_LoadMenu(HANDLE instance, LPSTR menu_name)
{ {
#ifdef DEBUG_RESOURCE return RSC_LoadResource(instance, menu_name, NE_RSCTYPE_MENU, NULL);
printf("LoadIcon: instance = %04x, name = %08x\n",
instance, icon_name);
#endif
return RSC_LoadResource( instance, icon_name, NE_RSCTYPE_ICON);
} }
/********************************************************************** /**********************************************************************
* RSC_LoadBitmap * LoadBitmap
*/ */
int HBITMAP
RSC_LoadBitmap(int instance, char *bmp_name) LoadBitmap(HANDLE instance, LPSTR bmp_name)
{ {
HBITMAP hbitmap;
HANDLE rsc_mem;
HDC hdc;
long *lp;
int image_size;
#ifdef DEBUG_RESOURCE #ifdef DEBUG_RESOURCE
printf("LoadBitmap: instance = %04x, name = %08x\n", printf("LoadBitmap: instance = %04x, name = %08x\n",
instance, bmp_name); instance, bmp_name);
#endif #endif
return RSC_LoadResource( instance, bmp_name, NE_RSCTYPE_BITMAP);
}
/**********************************************************************
* RSC_LoadCursor
*/
int
RSC_LoadCursor(int instance, char *cursor_name)
{
#ifdef DEBUG_RESOURCE
printf("LoadCursor: instance = %04x, name = %08x\n",
instance, cursor_name);
#endif
return RSC_LoadResource( instance, cursor_name, NE_RSCTYPE_CURSOR);
}
/**********************************************************************
* RSC_GetObject
*/
int
RSC_GetObject(int handle, int nbytes, void *buffer)
{
if (handle > 0 && handle <= ResourceArraySize)
{
RSCD *r = &Resources[handle - 1];
if (r->resource_type > 0)
{
int n = MIN(nbytes, ResourceSizes[r->resource_type & 0xf]);
memcpy(buffer, r->resource_data, n);
return n;
}
}
return 0; if (!(hdc = GetDC( 0 ))) return 0;
rsc_mem = RSC_LoadResource(instance, bmp_name, NE_RSCTYPE_BITMAP,
&image_size);
lp = (long *) GlobalLock(rsc_mem);
if (lp == NULL)
{
GlobalFree(rsc_mem);
return 0;
}
if (*lp == sizeof(BITMAPCOREHEADER))
hbitmap = ConvertCoreBitmap( hdc, (BITMAPCOREHEADER *) lp );
else if (*lp == sizeof(BITMAPINFOHEADER))
hbitmap = ConvertInfoBitmap( hdc, (BITMAPINFO *) lp );
else hbitmap = 0;
GlobalFree(rsc_mem);
ReleaseDC( 0, hdc );
return hbitmap;
} }

View File

@ -27,10 +27,13 @@ unsigned short PSPSelector;
unsigned char ran_out = 0; unsigned char ran_out = 0;
unsigned short SelectorOwners[MAX_SELECTORS]; unsigned short SelectorOwners[MAX_SELECTORS];
static int next_unused_selector = 0; static int next_unused_selector = 8;
extern void KERNEL_Ordinal_102(); extern void KERNEL_Ordinal_102();
extern void UNIXLIB_Ordinal_0(); extern void UNIXLIB_Ordinal_0();
extern char **Argv;
extern int Argc;
/********************************************************************** /**********************************************************************
* GetNextSegment * GetNextSegment
*/ */
@ -142,7 +145,12 @@ unsigned int GetEntryDLLOrdinal(char * dll_name, int ordinal, int * sel,
j = GetEntryPointFromOrdinal(wpnt, ordinal); j = GetEntryPointFromOrdinal(wpnt, ordinal);
*addr = j & 0xffff; *addr = j & 0xffff;
j = j >> 16; j = j >> 16;
#if 0
/* This seems like it would never work */
*sel = wpnt->selector_table[j].selector; *sel = wpnt->selector_table[j].selector;
#else
*sel = j; /* Is there any reason this will ever fail?? */
#endif
return 0; return 0;
}; };
return 1; return 1;
@ -322,6 +330,8 @@ CreatePSP(FILE *zfile)
unsigned short *usp; unsigned short *usp;
int sel_idx; int sel_idx;
struct segment_descriptor_s * s; struct segment_descriptor_s * s;
char *p1, *p2;
int i;
s = (struct segment_descriptor_s *) s = (struct segment_descriptor_s *)
malloc(sizeof(struct segment_descriptor_s)); malloc(sizeof(struct segment_descriptor_s));
@ -355,9 +365,22 @@ CreatePSP(FILE *zfile)
psp->pspCritErrorVector[0] = (unsigned short) UNIXLIB_Ordinal_0; psp->pspCritErrorVector[0] = (unsigned short) UNIXLIB_Ordinal_0;
psp->pspCritErrorVector[1] = 0x0023; psp->pspCritErrorVector[1] = 0x0023;
psp->pspEnvironment = EnvironmentSelector->selector; psp->pspEnvironment = EnvironmentSelector->selector;
psp->pspCommandTailCount = 1;
strcpy(psp->pspCommandTail, "\r"); p1 = psp->pspCommandTail;
for (i = 1; i < Argc; i++)
{
if ((int) ((int) p1 - (int) psp->pspCommandTail) +
strlen(Argv[i]) > 124)
break;
for (p2 = Argv[i]; *p2 != '\0'; )
*p1++ = *p2++;
*p1++ = ' ';
}
*p1++ = '\r';
*p1 = '\0';
psp->pspCommandTailCount = strlen(psp->pspCommandTail);
/* /*
* Create entry in LDT for this segment. * Create entry in LDT for this segment.
@ -387,7 +410,7 @@ CreateSelectors(struct w_files * wpnt)
int i; int i;
int status; int status;
FILE * zfile; FILE * zfile;
int old_length; int old_length, file_image_length;
/* /*
* Allocate memory for the table to keep track of all selectors. * Allocate memory for the table to keep track of all selectors.
@ -433,7 +456,9 @@ CreateSelectors(struct w_files * wpnt)
/* /*
* Image in file, let's just point to the image in memory. * Image in file, let's just point to the image in memory.
*/ */
s->length = seg_table[i].seg_data_length; s->length = seg_table[i].min_alloc;
file_image_length = seg_table[i].seg_data_length;
if (file_image_length == 0) file_image_length = 0x10000;
} }
if (s->length == 0) if (s->length == 0)
@ -484,13 +509,13 @@ CreateSelectors(struct w_files * wpnt)
*/ */
status = lseek(fd, seg_table[i].seg_data_offset * status = lseek(fd, seg_table[i].seg_data_offset *
(1 << ne_header->align_shift_count), SEEK_SET); (1 << ne_header->align_shift_count), SEEK_SET);
if(read(fd, s->base_addr, old_length) != old_length) if(read(fd, s->base_addr, file_image_length) != file_image_length)
myerror("Unable to read segment from file"); myerror("Unable to read segment from file");
} }
/* /*
* Create entry in LDT for this segment. * Create entry in LDT for this segment.
*/ */
if (set_ldt_entry(i, (unsigned long) s->base_addr, if (set_ldt_entry(s->selector >> 3, (unsigned long) s->base_addr,
(s->length - 1) & 0xffff, 0, (s->length - 1) & 0xffff, 0,
contents, read_only, 0) < 0) contents, read_only, 0) < 0)
{ {

216
loader/signal.c Normal file
View File

@ -0,0 +1,216 @@
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <syscall.h>
#include <signal.h>
#include <errno.h>
#include <linux/sched.h>
#include <asm/system.h>
extern void ___sig_restore();
extern void ___masksig_restore();
/* Similar to the sigaction function in libc, except it leaves alone the
restorer field */
static int
wine_sigaction(int sig,struct sigaction * new, struct sigaction * old)
{
__asm__("int $0x80":"=a" (sig)
:"0" (SYS_sigaction),"b" (sig),"c" (new),"d" (old));
if (sig>=0)
return 0;
errno = -sig;
return -1;
}
char * cstack[4096];
struct sigaction segv_act;
struct sigcontext_struct {
unsigned short gs, __gsh;
unsigned short fs, __fsh;
unsigned short es, __esh;
unsigned short ds, __dsh;
unsigned long edi;
unsigned long esi;
unsigned long ebp;
unsigned long esp;
unsigned long ebx;
unsigned long edx;
unsigned long ecx;
unsigned long eax;
unsigned long trapno;
unsigned long err;
unsigned long eip;
unsigned short cs, __csh;
unsigned long eflags;
unsigned long esp_at_signal;
unsigned short ss, __ssh;
unsigned long i387;
unsigned long oldmask;
unsigned long cr2;
};
static void
GetTimeDate(int time_flag, struct sigcontext_struct * context)
{
struct tm *now;
time_t ltime;
ltime = time(NULL);
now = localtime(&ltime);
if (time_flag)
{
context->ecx = (now->tm_hour << 8) | now->tm_min;
context->edx = now->tm_sec << 8;
}
else
{
context->ecx = now->tm_year + 1900;
context->edx = ((now->tm_mon + 1) << 8) | now->tm_mday;
context->eax &= 0xff00;
context->eax |= now->tm_wday;
}
}
/* We handle all int21 calls here. There is some duplicate code from
misc/dos.c that I am unsure how to deal with, since the locations
that we store the registers are all different */
static int
do_int21(struct sigcontext_struct * context){
fprintf(stderr,"Doing int21 %x ", (context->eax >> 8) & 0xff);
switch((context->eax >> 8) & 0xff){
case 0x30:
context->eax = 0x0303; /* Hey folks, this is DOS V3.3! */
context->ebx = 0;
context->ecx = 0;
break;
/* Ignore any attempt to set a segment vector */
case 0x25:
return 1;
case 0x35: /* Return a NULL segment selector - this will bomb
if anyone ever tries to use it */
context->es = 0;
context->ebx = 0;
break;
case 0x2a:
GetTimeDate(0, context);
/* Function does not return */
case 0x2c:
GetTimeDate(1, context);
/* Function does not return */
case 0x4c:
exit(context->eax & 0xff);
default:
fprintf(stderr,"Unable to handle int 0x21 %x\n", context->eax);
return 1;
};
return 1;
}
static int
do_int1A(struct sigcontext_struct * context){
time_t ltime;
int ticks;
switch((context->eax >> 8) & 0xff){
case 0:
ltime = time(NULL);
ticks = (int) (ltime * HZ);
context->ecx = ticks >> 16;
context->edx = ticks & 0x0000FFFF;
context->eax = 0; /* No midnight rollover */
break;
default:
fprintf(stderr,"Unable to handle int 0x1A %x\n", context->eax);
return 1;
};
return 1;
}
static void win_segfault(int signal, struct sigcontext_struct context){
unsigned char * instr;
unsigned char intno;
unsigned int * dump;
int i;
/* First take care of a few preliminaries */
if(signal != SIGSEGV) exit(1);
if((context.cs & 7) != 7){
fprintf(stderr,
"Segmentation fault in Wine program (%x:%x)."
" Please debug\n",
context.cs, context.eip);
goto oops;
};
/* Now take a look at the actual instruction where the program
bombed */
instr = (char *) ((context.cs << 16) | (context.eip & 0xffff));
if(*instr != 0xcd) {
fprintf(stderr,
"Unexpected Windows program segfault"
" - opcode = %x\n", *instr);
#if 0
return;
#else
goto oops;
#endif
};
instr++;
intno = *instr;
switch(intno){
case 0x21:
if(!do_int21(&context)) goto oops;
break;
case 0x1A:
if(!do_int1A(&context)) goto oops;
break;
default:
fprintf(stderr,"Unexpected Windows interrupt %x\n", intno);
goto oops;
};
/* OK, done handling the interrupt */
context.eip += 2; /* Bypass the int instruction */
return;
oops:
fprintf(stderr,"In win_segfault %x:%x\n", context.cs, context.eip);
fprintf(stderr,"Stack: %x:%x\n", context.ss, context.esp_at_signal);
dump = (int*) &context;
for(i=0; i<22; i++)
{
fprintf(stderr," %8.8x", *dump++);
if ((i % 8) == 7)
fprintf(stderr,"\n");
}
fprintf(stderr,"\n");
exit(1);
}
int
init_wine_signals(){
segv_act.sa_handler = (__sighandler_t) win_segfault;
/* Point to the top of the stack, minus 4 just in case, and make
it aligned */
segv_act.sa_restorer =
(void (*)()) (((unsigned int)(cstack + sizeof(cstack) - 4)) & ~3);
wine_sigaction(SIGSEGV, &segv_act, NULL);
}

View File

@ -18,6 +18,7 @@ static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include "prototypes.h" #include "prototypes.h"
#include "dlls.h" #include "dlls.h"
#include "wine.h" #include "wine.h"
#include "windows.h"
extern int CallToInit16(unsigned long csip, unsigned long sssp, extern int CallToInit16(unsigned long csip, unsigned long sssp,
unsigned short ds); unsigned short ds);
@ -52,13 +53,10 @@ DebugPrintString(char *str)
void void
myerror(const char *s) myerror(const char *s)
{ {
char buffer[200];
sprintf(buffer, "%s", Argv[0]);
if (s == NULL) if (s == NULL)
perror(buffer); perror("wine");
else else
fprintf(stderr, "%s: %s\n", buffer, s); fprintf(stderr, "wine: %s\n", s);
exit(1); exit(1);
} }
@ -229,8 +227,8 @@ _WinMain(int argc, char **argv)
int i; int i;
int rv; int rv;
Argc = argc; Argc = argc - 1;
Argv = argv; Argv = argv + 1;
if (argc < 2) if (argc < 2)
{ {
@ -272,6 +270,8 @@ _WinMain(int argc, char **argv)
ss_reg = wine_files->selector_table[wine_files->ne_header->ss-1].selector; ss_reg = wine_files->selector_table[wine_files->ne_header->ss-1].selector;
sp_reg = wine_files->ne_header->sp; sp_reg = wine_files->ne_header->sp;
init_wine_signals();
rv = CallToInit16(cs_reg << 16 | ip_reg, ss_reg << 16 | sp_reg, ds_reg); rv = CallToInit16(cs_reg << 16 | ip_reg, ss_reg << 16 | sp_reg, ds_reg);
printf ("rv = %x\n", rv); printf ("rv = %x\n", rv);
} }
@ -452,6 +452,7 @@ FixupSegment(struct w_files * wpnt, int segment_num)
break; break;
case NE_RELTYPE_INTERNAL: case NE_RELTYPE_INTERNAL:
case NE_RELTYPE_INT1:
if (rep->target1 == 0x00ff) if (rep->target1 == 0x00ff)
{ {
address = GetEntryPointFromOrdinal(wpnt, rep->target2); address = GetEntryPointFromOrdinal(wpnt, rep->target2);
@ -549,3 +550,16 @@ FixupSegment(struct w_files * wpnt, int segment_num)
free(rep1); free(rep1);
return 0; return 0;
} }
/**********************************************************************
* GetProcAddress
*/
FARPROC GetProcAddress(HINSTANCE hinstance, char *proc_name)
{
if ((int) proc_name & 0xffff0000)
printf("GetProcAddress: %#04x, '%s'\n", hinstance, proc_name);
else
printf("GetProcAddress: %#04x, %d\n", hinstance, (int) proc_name);
return NULL;
}

18
memory/Makefile Normal file
View File

@ -0,0 +1,18 @@
CFLAGS=$(COPTS) $(DEBUGOPTS) -I$(INCLUDE_DIR)
OBJS=global.o heap.o
default: memory.o
memory.o: $(OBJS)
$(LD) -r -o memory.o $(OBJS)
clean:
rm -f *.o *~ *.s dll_* *.a
depend:
$(CC) $(CFLAGS) -M *.c > .depend
ifeq (.depend,$(wildcard .depend))
include .depend
endif

View File

@ -220,6 +220,7 @@ GlobalAlloc(unsigned int flags, unsigned long size)
g->addr = m; g->addr = m;
g->length = size; g->length = size;
g->next = g_prev->next; g->next = g_prev->next;
if (g->next) g->next->prev = g;
g->lock_count = 0; g->lock_count = 0;
g_prev->next = g; g_prev->next = g;
@ -274,7 +275,7 @@ GlobalFree(unsigned int block)
*/ */
if (g->sequence == 0) if (g->sequence == 0)
{ {
HEAP_Free((MDESC **) (block & 0xffff0000), (void *) block); HEAP_Free((MDESC **) ((int) g->addr & 0xffff0000), (void *) g->addr);
g->prev->next = g->next; g->prev->next = g->next;
@ -677,3 +678,46 @@ GlobalReAlloc(unsigned int block, unsigned int new_size, unsigned int flags)
*/ */
return 0; return 0;
} }
/**********************************************************************
* GlobalQuickAlloc
*/
void *
GlobalQuickAlloc(int size)
{
unsigned int hmem;
hmem = GlobalAlloc(GLOBAL_FLAGS_MOVEABLE, size);
if (hmem == 0)
return NULL;
else
return GlobalLock(hmem);
}
/**********************************************************************
* GlobalHandleFromPointer
*/
unsigned int
GlobalHandleFromPointer(void *block)
{
GDESC *g;
if (block == NULL)
return 0;
/*
* Find GDESC for this block.
*/
for (g = GlobalList; g != NULL; g = g->next)
if (g->handle > 0 && g->addr == block)
break;
if (g == NULL)
return 0;
else
return g->handle;
}

View File

@ -61,6 +61,8 @@ HEAP_Alloc(MDESC **free_list, int flags, int bytes)
m->prev = m; m->prev = m;
m->next = m; m->next = m;
m->lock = 0;
m->flags = 0;
if (flags & GLOBAL_FLAGS_ZEROINIT) if (flags & GLOBAL_FLAGS_ZEROINIT)
memset(m + 1, 0, bytes); memset(m + 1, 0, bytes);
#ifdef DEBUG_HEAP #ifdef DEBUG_HEAP
@ -82,6 +84,8 @@ HEAP_Alloc(MDESC **free_list, int flags, int bytes)
m->prev = m; m->prev = m;
m->next = m; m->next = m;
m->lock = 0;
m->flags = 0;
if (flags & GLOBAL_FLAGS_ZEROINIT) if (flags & GLOBAL_FLAGS_ZEROINIT)
memset(m + 1, 0, bytes); memset(m + 1, 0, bytes);
#ifdef DEBUG_HEAP #ifdef DEBUG_HEAP
@ -103,14 +107,76 @@ void *
HEAP_ReAlloc(MDESC **free_list, void *old_block, HEAP_ReAlloc(MDESC **free_list, void *old_block,
int new_size, unsigned int flags) int new_size, unsigned int flags)
{ {
return 0; MDESC *m_free;
MDESC *m;
/*
* Check validity of block
*/
m = (MDESC *) old_block - 1;
if (m->prev != m || m->next != m ||
((int) m & 0xffff0000) != ((int) *free_list & 0xffff0000))
{
#ifdef DEBUG_HEAP
printf("Attempt to resize bad pointer, m = %08x, *free_list = %08x\n",
m, free_list);
#endif
return NULL;
}
/*
* Check for grow block
*/
if (new_size > m->length)
{
m_free = m + 1 + m->length / sizeof(MDESC);
if (m_free->next != m_free ||
m_free->prev != m_free ||
m_free->length + sizeof(MDESC) < new_size)
{
void *new_p = HEAP_Alloc(free_list, flags, new_size);
if (new_p ==NULL)
return NULL;
memcpy(new_p, old_block, m->length);
HEAP_Free(free_list, old_block);
return new_p;
}
if (m_free->prev == NULL)
*free_list = m_free->next;
else
m_free->prev->next = m_free->next;
if (m_free->next != NULL)
m_free->next->prev = m_free->prev;
m->length += sizeof(MDESC) + m_free->length;
if (flags & GLOBAL_FLAGS_ZEROINIT)
memset(m_free, '\0', sizeof(MDESC) + m_free->length);
}
/*
* Check for shrink block.
*/
if (new_size < m->length - 4 * sizeof(MDESC))
{
m_free = m + new_size / sizeof(MDESC) + 2;
m_free->next = m_free;
m_free->prev = m_free;
m_free->length = m->length - (int) m_free - (int) m;
m->length = (int) m_free - (int) (m + 1);
HEAP_Free(free_list, m_free + 1);
}
return old_block;
} }
/********************************************************************** /**********************************************************************
* HEAP_Free * HEAP_Free
*/ */
void int
HEAP_Free(MDESC **free_list, void *block) HEAP_Free(MDESC **free_list, void *block)
{ {
MDESC *m_free; MDESC *m_free;
@ -129,7 +195,7 @@ HEAP_Free(MDESC **free_list, void *block)
"m_free = %08x, *free_list = %08x\n", "m_free = %08x, *free_list = %08x\n",
m_free, free_list); m_free, free_list);
#endif #endif
return; return -1;
} }
/* /*
@ -146,7 +212,7 @@ HEAP_Free(MDESC **free_list, void *block)
"m_free = %08x, m_prev = %08x (length %x)\n", "m_free = %08x, m_prev = %08x (length %x)\n",
m_free, m_prev, m_prev->length); m_free, m_prev, m_prev->length);
#endif #endif
return; return -1;
} }
if ((m != NULL && (int) m_free + m_free->length > (int) m) || if ((m != NULL && (int) m_free + m_free->length > (int) m) ||
@ -157,7 +223,7 @@ HEAP_Free(MDESC **free_list, void *block)
"m_free = %08x (length %x), m = %08x\n", "m_free = %08x (length %x), m = %08x\n",
m_free, m_free->length, m); m_free, m_free->length, m);
#endif #endif
return; return -1;
} }
/* /*
@ -203,6 +269,8 @@ HEAP_Free(MDESC **free_list, void *block)
{ {
m_free->next = NULL; m_free->next = NULL;
} }
return 0;
} }
/********************************************************************** /**********************************************************************
@ -215,10 +283,10 @@ HEAP_LocalInit(void *start, int length)
} }
/********************************************************************** /**********************************************************************
* HEAP_LocalAlloc * LocalAlloc
*/ */
void * void *
HEAP_LocalAlloc(int flags, int bytes) LocalAlloc(int flags, int bytes)
{ {
void *m; void *m;
@ -235,10 +303,10 @@ HEAP_LocalAlloc(int flags, int bytes)
} }
/********************************************************************** /**********************************************************************
* HEAP_LocalCompact * LocalCompact
*/ */
int int
HEAP_LocalCompact(int min_free) LocalCompact(int min_free)
{ {
MDESC *m; MDESC *m;
int max_block; int max_block;
@ -250,3 +318,113 @@ HEAP_LocalCompact(int min_free)
return max_block; return max_block;
} }
/**********************************************************************
* LocalFlags
*/
unsigned int
LocalFlags(unsigned int handle)
{
MDESC *m;
m = (MDESC *) (((int) LOCAL_FreeList & 0xffff0000) |
(handle & 0xffff)) - 1;
if (m->next != m || m->prev != m)
return 0;
return m->lock;
}
/**********************************************************************
* LocalFree
*/
unsigned int
LocalFree(unsigned int handle)
{
unsigned int addr;
addr = ((int) LOCAL_FreeList & 0xffff0000) | (handle & 0xffff);
if (HEAP_Free(&LOCAL_FreeList, (void *) addr) < 0)
return handle;
else
return 0;
}
/**********************************************************************
* LocalInit
*/
unsigned int
LocalInit(unsigned int segment, unsigned int start, unsigned int end)
{
HEAP_Init(&LOCAL_FreeList,
(void *) ((segment << 16) | start), end - start + 1);
return segment;
}
/**********************************************************************
* LocalLock
*/
void *
LocalLock(unsigned int handle)
{
MDESC *m;
m = (MDESC *) (((int) LOCAL_FreeList & 0xffff0000) |
(handle & 0xffff)) - 1;
if (m->next != m || m->prev != m)
return 0;
m->lock++;
return (void *) (m + 1);
}
/**********************************************************************
* LocalReAlloc
*/
void *
LocalReAlloc(unsigned int handle, int flags, int bytes)
{
void *m;
m = HEAP_ReAlloc(&LOCAL_FreeList, (void *)
(((int) LOCAL_FreeList & 0xffff0000) | (handle & 0xffff)),
bytes, flags);
return m;
}
/**********************************************************************
* LocalSize
*/
unsigned int
LocalSize(unsigned int handle)
{
MDESC *m;
m = (MDESC *) (((int) LOCAL_FreeList & 0xffff0000) |
(handle & 0xffff)) - 1;
if (m->next != m || m->prev != m)
return 0;
return m->length;
}
/**********************************************************************
* LocalUnlock
*/
unsigned int
LocalUnlock(unsigned int handle)
{
MDESC *m;
m = (MDESC *) (((int) LOCAL_FreeList & 0xffff0000) |
(handle & 0xffff)) - 1;
if (m->next != m || m->prev != m)
return 1;
if (m->lock > 0)
m->lock--;
return 0;
}

18
misc/Makefile Normal file
View File

@ -0,0 +1,18 @@
CFLAGS=$(COPTS) $(DEBUGOPTS) -I$(INCLUDE_DIR)
OBJS=dos.o kernel.o user.o xt.o rect.o
default: misc.o
misc.o: $(OBJS)
$(LD) -r -o misc.o $(OBJS)
clean:
rm -f *.o *~ *.s dll_* *.a
depend:
$(CC) $(CFLAGS) -M *.c > .depend
ifeq (.depend,$(wildcard .depend))
include .depend
endif

76
misc/dos.c Normal file
View File

@ -0,0 +1,76 @@
static char RCSId[] = "$Id$";
static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include "prototypes.h"
#include "regfunc.h"
static void
GetTimeDate(int time_flag)
{
struct tm *now;
time_t ltime;
ltime = time(NULL);
now = localtime(&ltime);
if (time_flag)
{
_CX = (now->tm_hour << 8) | now->tm_min;
_DX = now->tm_sec << 8;
}
else
{
_CX = now->tm_year + 1900;
_DX = ((now->tm_mon + 1) << 8) | now->tm_mday;
_AX &= 0xff00;
_AX |= now->tm_wday;
}
#ifdef DEBUG_DOS
printf("GetTimeDate: AX = %04x, CX = %04x, DX = %04x\n", _AX, _CX, _DX);
#endif
ReturnFromRegisterFunc();
/* Function does not return */
}
/**********************************************************************
* KERNEL_DOS3Call
*/
int
KERNEL_DOS3Call()
{
switch ((_AX >> 8) & 0xff)
{
case 0x30:
_AX = 0x0303;
ReturnFromRegisterFunc();
/* Function does not return */
case 0x25:
case 0x35:
return 0;
case 0x2a:
GetTimeDate(0);
/* Function does not return */
case 0x2c:
GetTimeDate(1);
/* Function does not return */
case 0x4c:
exit(_AX & 0xff);
default:
fprintf(stderr, "DOS: AX %04x, BX %04x, CX %04x, DX %04x\n",
_AX, _BX, _CX, _DX);
fprintf(stderr, " SP %04x, BP %04x, SI %04x, DI %04x\n",
_SP, _BP, _SI, _DI);
fprintf(stderr, " DS %04x, ES %04x\n",
_DS, _ES);
}
return 0;
}

View File

@ -4,8 +4,9 @@ static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include "prototypes.h" #include "prototypes.h"
#include "regfunc.h"
extern unsigned short *Stack16Frame; extern unsigned short WIN_StackSize;
/********************************************************************** /**********************************************************************
* KERNEL_LockSegment * KERNEL_LockSegment
@ -39,6 +40,20 @@ KERNEL_UnlockSegment(int segment)
return segment; return segment;
} }
/**********************************************************************
* KERNEL_InitTask
*/
KERNEL_InitTask()
{
_BX = 0x81;
_AX = 1;
_CX = WIN_StackSize;
_DX = 1;
_SI = 0;
ReturnFromRegisterFunc();
/* Function does not return */
}
/********************************************************************** /**********************************************************************
* KERNEL_WaitEvent * KERNEL_WaitEvent
*/ */
@ -65,34 +80,3 @@ KERNEL_GetModuleFileName(int module, char *filename, int bytes)
return strlen(filename); return strlen(filename);
} }
/**********************************************************************
* KERNEL_DOS3Call
*/
int
KERNEL_DOS3Call(int ax, int cx, int dx, int bx, int sp, int bp,
int si, int di, int ds, int es)
{
switch ((ax >> 8) & 0xff)
{
case 0x30:
return 0x0303;
case 0x25:
case 0x35:
return 0;
case 0x4c:
exit(ax & 0xff);
default:
fprintf(stderr, "DOS: AX %04x, BX %04x, CX %04x, DX %04x\n",
ax, bx, cx, dx);
fprintf(stderr, " SP %04x, BP %04x, SI %04x, DI %04x\n",
sp, bp, si, di);
fprintf(stderr, " DS %04x, ES %04x\n",
ds, es);
}
return 0;
}

167
misc/rect.c Normal file
View File

@ -0,0 +1,167 @@
/*
* Rectangle-related functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "windows.h"
#define MIN(a,b) ((a) < (b) ? (a) : (b))
#define MAX(a,b) ((a) > (b) ? (a) : (b))
/***********************************************************************
* SetRect (USER.72)
*/
void SetRect( LPRECT rect, short left, short top, short right, short bottom )
{
rect->left = left;
rect->right = right;
rect->top = top;
rect->bottom = bottom;
}
/***********************************************************************
* SetRectEmpty (USER.73)
*/
void SetRectEmpty( LPRECT rect )
{
rect->left = rect->right = rect->top = rect->bottom = 0;
}
/***********************************************************************
* CopyRect (USER.74)
*/
void CopyRect( LPRECT dest, LPRECT src )
{
*dest = *src;
}
/***********************************************************************
* IsRectEmpty (USER.75)
*/
BOOL IsRectEmpty( LPRECT rect )
{
return ((rect->left == rect->right) || (rect->top == rect->bottom));
}
/***********************************************************************
* PtInRect (USER.76)
*/
BOOL PtInRect( LPRECT rect, POINT pt )
{
return ((pt.x >= rect->left) && (pt.x < rect->right) &&
(pt.y >= rect->top) && (pt.y < rect->bottom));
}
/***********************************************************************
* OffsetRect (USER.77)
*/
void OffsetRect( LPRECT rect, short x, short y )
{
rect->left += x;
rect->right += x;
rect->top += y;
rect->bottom += y;
}
/***********************************************************************
* InflateRect (USER.78)
*/
void InflateRect( LPRECT rect, short x, short y )
{
rect->right += x;
rect->bottom += y;
}
/***********************************************************************
* IntersectRect (USER.79)
*/
BOOL IntersectRect( LPRECT dest, LPRECT src1, LPRECT src2 )
{
if ((src1->left >= src2->right) || (src2->left >= src1->right) ||
(src1->top >= src2->bottom) || (src2->top >= src1->bottom))
{
SetRectEmpty( dest );
return FALSE;
}
dest->left = MAX( src1->left, src2->left );
dest->right = MIN( src1->right, src2->right );
dest->top = MAX( src1->top, src2->top );
dest->bottom = MIN( src1->bottom, src2->bottom );
return TRUE;
}
/***********************************************************************
* UnionRect (USER.80)
*/
BOOL UnionRect( LPRECT dest, LPRECT src1, LPRECT src2 )
{
if (IsRectEmpty(src1))
{
if (IsRectEmpty(src2))
{
SetRectEmpty( dest );
return FALSE;
}
else *dest = *src2;
}
else
{
if (IsRectEmpty(src2)) *dest = *src1;
else
{
dest->left = MIN( src1->left, src2->left );
dest->right = MAX( src1->right, src2->right );
dest->top = MIN( src1->top, src2->top );
dest->bottom = MAX( src1->bottom, src2->bottom );
}
}
return TRUE;
}
/***********************************************************************
* EqualRect (USER.244)
*/
BOOL EqualRect( LPRECT rect1, LPRECT rect2 )
{
return ((rect1->left == rect2->left) && (rect1->right == rect2->right) &&
(rect1->top == rect2->top) && (rect1->bottom == rect2->bottom));
}
/***********************************************************************
* SubtractRect (USER.373)
*/
BOOL SubtractRect( LPRECT dest, LPRECT src1, LPRECT src2 )
{
RECT tmp;
*dest = *src1;
if (IntersectRect( &tmp, src1, src2 ))
{
if (EqualRect( &tmp, dest )) SetRectEmpty( src1 );
else if ((tmp.top == dest->top) && (tmp.bottom == dest->bottom))
{
if (tmp.left == dest->left) dest->right = tmp.right;
else if (tmp.right == dest->right) dest->left = tmp.left;
}
else if ((tmp.left == dest->left) && (tmp.right == dest->right))
{
if (tmp.top == dest->top) dest->bottom = tmp.bottom;
else if (tmp.bottom == dest->bottom) dest->top = tmp.top;
}
}
return TRUE;
}

56
misc/user.c Normal file
View File

@ -0,0 +1,56 @@
static char RCSId[] = "$Id: user.c,v 1.2 1993/07/04 04:04:21 root Exp root $";
static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include <stdio.h>
#include <stdlib.h>
#include "prototypes.h"
#include "windows.h"
#include "user.h"
#define DEFAULT_MSG_QUEUE_SIZE 8
#define USER_HEAP_SIZE 0x10000
MDESC *USER_Heap = NULL;
/***********************************************************************
* USER_HeapInit
*/
static BOOL USER_HeapInit()
{
struct segment_descriptor_s * s;
s = GetNextSegment( 0, 0x10000 );
if (s == NULL) return FALSE;
HEAP_Init( &USER_Heap, s->base_addr, USER_HEAP_SIZE );
free(s);
return TRUE;
}
/**********************************************************************
* USER_InitApp
*
* Load necessary resources?
*/
int
USER_InitApp(int hInstance)
{
/* GDI initialisation */
if (!GDI_Init()) return 0;
/* Create USER heap */
if (!USER_HeapInit()) return 0;
/* Create the DCEs */
DCE_Init();
/* Initialize built-in window classes */
WIDGETS_Init();
/* Create task message queue */
if (!SetMessageQueue( DEFAULT_MSG_QUEUE_SIZE )) return 0;
return 1;
}

174
misc/xt.c Normal file
View File

@ -0,0 +1,174 @@
/*
* X toolkit functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <sys/param.h>
#include <sys/times.h>
#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Core.h>
#include <X11/Shell.h>
#include "message.h"
#include "callback.h"
#include "win.h"
#include "class.h"
#include "gdi.h"
Display * XT_display;
Screen * XT_screen;
XtAppContext XT_app_context;
static Widget topLevelWidget;
/***********************************************************************
* main
*/
void main(int argc, char **argv)
{
topLevelWidget = XtVaAppInitialize(&XT_app_context,
"XWine", /* Application class */
NULL, 0, /* Option list */
&argc, argv, /* Command line args */
NULL, /* Fallback resources */
NULL );
XT_display = XtDisplay( topLevelWidget );
XT_screen = XtScreen( topLevelWidget );
_WinMain( argc, argv );
}
/***********************************************************************
* DefWindowProc (USER.107)
*/
LONG DefWindowProc( HWND hwnd, WORD msg, WORD wParam, LONG lParam )
{
WND * wndPtr;
CLASS * classPtr;
#ifdef DEBUG_MESSAGE
printf( "DefWindowProc: %d %d %d %08x\n", hwnd, msg, wParam, lParam );
#endif
switch(msg)
{
case WM_PAINT:
{
PAINTSTRUCT paintstruct;
BeginPaint( hwnd, &paintstruct );
EndPaint( hwnd, &paintstruct );
return 0;
}
case WM_CREATE:
return 0;
case WM_CLOSE:
DestroyWindow( hwnd );
return 0;
case WM_ERASEBKGND:
case WM_ICONERASEBKGND:
{
if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return 1;
if (!(classPtr = CLASS_FindClassPtr( wndPtr->hClass ))) return 1;
if (!classPtr->wc.hbrBackground) return 1;
FillWindow( wndPtr->hwndParent, hwnd, (HDC)wParam,
classPtr->wc.hbrBackground );
GlobalUnlock( hwnd );
return 0;
}
}
return 0;
}
/********************************************************************
*
* Miscellaneous partially implemented functions.
*
*/
int MessageBox( HWND hwnd, LPSTR str, LPSTR title, WORD type )
{
printf( "MessageBox: '%s'\n", str );
}
void MessageBeep( WORD i )
{
printf( "MessageBeep: %d\n", i );
}
WORD RegisterWindowMessage( LPSTR str )
{
printf( "RegisterWindowMessage: '%s'\n", str );
return 0xc000;
}
/***********************************************************************
* GetTickCount (USER.13)
*/
DWORD GetTickCount()
{
struct tms dummy;
return times(&dummy) / (1000 / HZ);
}
int GetSystemMetrics( short index )
{
printf( "GetSystemMetrics: %d\n", index );
switch(index)
{
case SM_CXSCREEN:
return DisplayWidth( XT_display, DefaultScreen( XT_display ));
case SM_CYSCREEN:
return DisplayHeight( XT_display, DefaultScreen( XT_display ));
default:
return 0;
}
}
void AdjustWindowRect( LPRECT rect, DWORD style, BOOL menu )
{
printf( "AdjustWindowRect: (%d,%d)-(%d,%d) %d %d\n", rect->left, rect->top,
rect->right, rect->bottom, style, menu );
}
WORD GetPrivateProfileInt( LPSTR section, LPSTR entry,
short defval, LPSTR filename )
{
printf( "GetPrivateProfileInt: %s %s %d %s\n", section, entry, defval, filename );
return defval;
}
short GetPrivateProfileString( LPSTR section, LPSTR entry, LPSTR defval,
LPSTR buffer, short count, LPSTR filename )
{
printf( "GetPrivateProfileString: %s %s %s %d %s\n", section, entry, defval, count, filename );
strncpy( buffer, defval, count );
buffer[count-1] = 0;
return strlen(buffer);
}
BOOL IsIconic( HWND hwnd )
{
printf( "IsIconic: returning FALSE\n" );
return FALSE;
}
HMENU CreateMenu() { }
BOOL AppendMenu( HMENU hmenu, WORD flags, WORD id, LPSTR text ) { }

19
objects/Makefile Normal file
View File

@ -0,0 +1,19 @@
CFLAGS=$(COPTS) $(DEBUGOPTS) -I$(INCLUDE_DIR)
OBJS=bitmap.o brush.o font.o gdiobj.o palette.o pen.o dib.o region.o \
text.o dcvalues.o clipping.o bitblt.o linedda.o
default: objects.o
objects.o: $(OBJS)
$(LD) -r -o objects.o $(OBJS)
clean:
rm -f *.o *~ *.s dll_* *.a
depend:
$(CC) $(CFLAGS) -M *.c > .depend
ifeq (.depend,$(wildcard .depend))
include .depend
endif

111
objects/bitblt.c Normal file
View File

@ -0,0 +1,111 @@
/*
* GDI bit-blit operations
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdio.h>
#include <stdlib.h>
#include <X11/Xlib.h>
#include "gdi.h"
extern const int DC_XROPfunction[];
#define MIN(a,b) ((a) < (b) ? (a) : (b))
#define MAX(a,b) ((a) > (b) ? (a) : (b))
/***********************************************************************
* PatBlt (GDI.29)
*/
BOOL PatBlt( HDC hdc, short left, short top,
short width, short height, DWORD rop)
{
int x1, x2, y1, y2;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return FALSE;
#ifdef DEBUG_GDI
printf( "PatBlt: %d %d,%d %dx%d %06x\n",
hdc, left, top, width, height, rop );
#endif
rop >>= 16;
if (!DC_SetupGCForBrush( dc )) rop &= 0x0f;
else rop = (rop & 0x03) | ((rop >> 4) & 0x0c);
XSetFunction( XT_display, dc->u.x.gc, DC_XROPfunction[rop] );
x1 = XLPTODP( dc, left );
x2 = XLPTODP( dc, left + width );
y1 = YLPTODP( dc, top );
y2 = YLPTODP( dc, top + height );
XFillRectangle( XT_display, dc->u.x.drawable, dc->u.x.gc,
MIN(x1,x2), MIN(y1,y2), abs(x2-x1), abs(y2-y1) );
return TRUE;
}
/***********************************************************************
* BitBlt (GDI.34)
*/
BOOL BitBlt( HDC hdcDest, short xDest, short yDest, short width, short height,
HDC hdcSrc, short xSrc, short ySrc, DWORD rop )
{
int xs1, xs2, ys1, ys2;
int xd1, xd2, yd1, yd2;
DC *dcDest, *dcSrc;
#ifdef DEBUG_GDI
printf( "BitBlt: %d %d,%d %dx%d %d %d,%d %08x\n",
hdcDest, xDest, yDest, width, height, hdcSrc, xSrc, ySrc, rop );
#endif
if ((rop & 0xcc0000) == ((rop & 0x330000) << 2))
return PatBlt( hdcDest, xDest, yDest, width, height, rop );
rop >>= 16;
if ((rop & 0x0f) != (rop >> 4))
{
printf( "BitBlt: Unimplemented ROP %02x\n", rop );
return FALSE;
}
dcDest = (DC *) GDI_GetObjPtr( hdcDest, DC_MAGIC );
if (!dcDest) return FALSE;
dcSrc = (DC *) GDI_GetObjPtr( hdcSrc, DC_MAGIC );
if (!dcSrc) return FALSE;
xs1 = XLPTODP( dcSrc, xSrc );
xs2 = XLPTODP( dcSrc, xSrc + width );
ys1 = YLPTODP( dcSrc, ySrc );
ys2 = YLPTODP( dcSrc, ySrc + height );
xd1 = XLPTODP( dcDest, xDest );
xd2 = XLPTODP( dcDest, xDest + width );
yd1 = YLPTODP( dcDest, yDest );
yd2 = YLPTODP( dcDest, yDest + height );
if ((abs(xs2-xs1) != abs(xd2-xd1)) || (abs(ys2-ys1) != abs(yd2-yd1)))
return FALSE; /* Should call StretchBlt here */
DC_SetupGCForText( dcDest );
XSetFunction( XT_display, dcDest->u.x.gc, DC_XROPfunction[rop & 0x0f] );
if (dcSrc->w.bitsPerPixel == dcDest->w.bitsPerPixel)
{
XCopyArea( XT_display, dcSrc->u.x.drawable,
dcDest->u.x.drawable, dcDest->u.x.gc,
MIN(xs1,xs2), MIN(ys1,ys2), abs(xs2-xs1), abs(ys2-ys1),
MIN(xd1,xd2), MIN(yd1,yd2) );
}
else
{
if (dcSrc->w.bitsPerPixel != 1) return FALSE;
XCopyPlane( XT_display, dcSrc->u.x.drawable,
dcDest->u.x.drawable, dcDest->u.x.gc,
MIN(xs1,xs2), MIN(ys1,ys2), abs(xs2-xs1), abs(ys2-ys1),
MIN(xd1,xd2), MIN(yd1,yd2), 1 );
}
return TRUE;
}

423
objects/bitmap.c Normal file
View File

@ -0,0 +1,423 @@
/*
* GDI bitmap objects
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "gdi.h"
/* A GDI bitmap object contains a handle to a packed BITMAP,
* which is stored on the global heap.
* A packed BITMAP is a BITMAP structure followed by the bitmap bits.
*/
/* Handle of the bitmap selected by default in a memory DC */
HBITMAP BITMAP_hbitmapMemDC;
/* List of supported depths */
static int depthCount;
static int * depthList;
/* List of GC used for bitmap to pixmap operations (one for each depth) */
static GC * bitmapGC;
/***********************************************************************
* BITMAP_Init
*/
BOOL BITMAP_Init()
{
int i;
Pixmap tmpPixmap;
depthList = XListDepths( XT_display, DefaultScreen(XT_display),
&depthCount );
if (!depthList || !depthCount) return FALSE;
if (!(bitmapGC = (GC *) malloc( depthCount * sizeof(GC) ))) return FALSE;
/* Create the necessary GCs */
for (i = 0; i < depthCount; i++)
{
tmpPixmap = XCreatePixmap( XT_display, DefaultRootWindow(XT_display),
1, 1, depthList[i] );
if (tmpPixmap)
{
bitmapGC[i] = XCreateGC( XT_display, tmpPixmap, 0, NULL );
XFreePixmap( XT_display, tmpPixmap );
}
else bitmapGC[i] = 0;
}
BITMAP_hbitmapMemDC = CreateBitmap( 1, 1, 1, 1, NULL );
return (BITMAP_hbitmapMemDC != 0);
}
/***********************************************************************
* BITMAP_FindGCForDepth
*
* Return a GC appropriate for operations with the given depth.
*/
GC BITMAP_FindGCForDepth( int depth )
{
int i;
for (i = 0; i < depthCount; i++)
if (depthList[i] == depth) return bitmapGC[i];
return 0;
}
/***********************************************************************
* BITMAP_BmpToImage
*
* Create an XImage pointing to the bitmap data.
*/
XImage * BITMAP_BmpToImage( BITMAP * bmp, void * bmpData )
{
XImage * image;
image = XCreateImage( XT_display, DefaultVisualOfScreen(XT_screen),
bmp->bmBitsPixel, ZPixmap, 0, bmpData,
bmp->bmWidth, bmp->bmHeight, 16, bmp->bmWidthBytes );
if (!image) return 0;
image->byte_order = MSBFirst;
image->bitmap_bit_order = MSBFirst;
image->bitmap_unit = 16;
_XInitImageFuncPtrs(image);
return image;
}
/***********************************************************************
* BITMAP_CopyToPixmap
*
* Copy the content of the bitmap to the pixmap. Both must have the same depth.
*/
BOOL BITMAP_CopyToPixmap( BITMAP * bmp, Pixmap pixmap,
int x, int y, int width, int height )
{
GC gc;
XImage * image;
gc = BITMAP_FindGCForDepth( bmp->bmBitsPixel );
if (!gc) return FALSE;
image = BITMAP_BmpToImage( bmp, ((char *)bmp) + sizeof(BITMAP) );
if (!image) return FALSE;
#ifdef DEBUG_GDI
printf( "BITMAP_CopyToPixmap: %dx%d %d colors -> %d,%d %dx%d\n",
bmp->bmWidth, bmp->bmHeight, 1 << bmp->bmBitsPixel, x, y, width, height );
#endif
XPutImage(XT_display, pixmap, gc, image, 0, 0, x, y, width, height);
image->data = NULL;
XDestroyImage( image );
return TRUE;
}
/***********************************************************************
* BITMAP_CopyFromPixmap
*
* Copy the content of the pixmap to the bitmap. Both must have
* the same dimensions and depth.
*/
BOOL BITMAP_CopyFromPixmap( BITMAP * bmp, Pixmap pixmap )
{
XImage *image = BITMAP_BmpToImage( bmp, ((char *)bmp) + sizeof(BITMAP) );
if (!image) return FALSE;
#ifdef DEBUG_GDI
printf( "BITMAP_CopyFromPixmap: %dx%d %d colors\n",
bmp->bmWidth, bmp->bmHeight, 1 << bmp->bmBitsPixel );
#endif
XGetSubImage( XT_display, pixmap, 0, 0, bmp->bmWidth, bmp->bmHeight,
AllPlanes, ZPixmap, image, 0, 0 );
image->data = NULL;
XDestroyImage( image );
return TRUE;
}
/***********************************************************************
* CreateBitmap (GDI.48)
*/
HBITMAP CreateBitmap( short width, short height,
BYTE planes, BYTE bpp, LPSTR bits )
{
BITMAP bitmap = { 0, width, height, 0, planes, bpp, bits };
#ifdef DEBUG_GDI
printf( "CreateBitmap: %dx%d, %d colors\n",
width, height, 1 << (planes*bpp) );
#endif
if (!width || !height) return 0;
if ((planes != 1) && (bpp != 1)) return 0;
bitmap.bmWidthBytes = (width * bpp + 15) / 16 * 2;
return CreateBitmapIndirect( &bitmap );
}
/***********************************************************************
* CreateCompatibleBitmap (GDI.51)
*/
HBITMAP CreateCompatibleBitmap( HDC hdc, short width, short height )
{
HBITMAP hbitmap;
DC * dc;
#ifdef DEBUG_GDI
printf( "CreateCompatibleBitmap: %d %dx%d\n", hdc, width, height );
#endif
dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
hbitmap = CreateBitmap( width, height, dc->w.planes, dc->w.bitsPerPixel, NULL);
return hbitmap;
}
/***********************************************************************
* CreateBitmapIndirect (GDI.49)
*/
HBITMAP CreateBitmapIndirect( BITMAP * bmp )
{
BITMAPOBJ * bmpObjPtr;
char * bmpPtr;
HBITMAP hbitmap;
int size = bmp->bmPlanes * bmp->bmHeight * bmp->bmWidthBytes;
/* Create the BITMAPOBJ */
hbitmap = GDI_AllocObject( sizeof(BITMAPOBJ), BITMAP_MAGIC );
if (!hbitmap) return 0;
bmpObjPtr = (BITMAPOBJ *) GDI_HEAP_ADDR( hbitmap );
/* Create the bitmap in global heap */
bmpObjPtr->hBitmap = GlobalAlloc( GMEM_MOVEABLE, sizeof(BITMAP) + size );
if (!bmpObjPtr->hBitmap)
{
GDI_FreeObject( hbitmap );
return 0;
}
bmpPtr = (char *) GlobalLock( bmpObjPtr->hBitmap );
memcpy( bmpPtr, bmp, sizeof(BITMAP) );
((BITMAP *)bmpPtr)->bmBits = NULL;
if (bmp->bmBits) memcpy( bmpPtr + sizeof(BITMAP), bmp->bmBits, size );
GlobalUnlock( bmpObjPtr->hBitmap );
bmpObjPtr->bSelected = FALSE;
bmpObjPtr->hdc = 0;
bmpObjPtr->size.cx = 0;
bmpObjPtr->size.cy = 0;
return hbitmap;
}
/***********************************************************************
* BITMAP_GetSetBitmapBits
*/
LONG BITMAP_GetSetBitmapBits( HBITMAP hbitmap, LONG count,
LPSTR buffer, int set )
{
BITMAPOBJ * bmpObjPtr;
BITMAP * bmp;
DC * dc = NULL;
int maxSize;
if (!count) return 0;
bmpObjPtr = (BITMAPOBJ *) GDI_GetObjPtr( hbitmap, BITMAP_MAGIC );
if (!bmpObjPtr) return 0;
if (!(bmp = (BITMAP *) GlobalLock( bmpObjPtr->hBitmap ))) return 0;
if (bmpObjPtr->bSelected)
dc = (DC *) GDI_GetObjPtr( bmpObjPtr->hdc, DC_MAGIC );
maxSize = bmp->bmPlanes * bmp->bmHeight * bmp->bmWidthBytes;
if (count > maxSize) count = maxSize;
if (set)
{
memcpy( bmp+1, buffer, count );
if (dc) BITMAP_CopyToPixmap( bmp, dc->u.x.drawable,
0, 0, bmp->bmWidth, bmp->bmHeight );
}
else
{
if (dc) BITMAP_CopyFromPixmap( bmp, dc->u.x.drawable );
memcpy( buffer, bmp+1, count );
}
GlobalUnlock( bmpObjPtr->hBitmap );
return hbitmap;
}
/***********************************************************************
* GetBitmapBits (GDI.74)
*/
LONG GetBitmapBits( HBITMAP hbitmap, LONG count, LPSTR buffer )
{
return BITMAP_GetSetBitmapBits( hbitmap, count, buffer, 0 );
}
/***********************************************************************
* SetBitmapBits (GDI.106)
*/
LONG SetBitmapBits( HBITMAP hbitmap, LONG count, LPSTR buffer )
{
return BITMAP_GetSetBitmapBits( hbitmap, count, buffer, 1 );
}
/***********************************************************************
* BMP_DeleteObject
*/
BOOL BMP_DeleteObject( HBITMAP hbitmap, BITMAPOBJ * bitmap )
{
/* Free bitmap on global heap */
GlobalFree( bitmap->hBitmap );
return GDI_FreeObject( hbitmap );
}
/***********************************************************************
* BMP_GetObject
*/
int BMP_GetObject( BITMAPOBJ * bitmap, int count, LPSTR buffer )
{
char * bmpPtr = (char *) GlobalLock( bitmap->hBitmap );
if (count > sizeof(BITMAP)) count = sizeof(BITMAP);
memcpy( buffer, bmpPtr, count );
GlobalUnlock( bitmap->hBitmap );
return count;
}
/***********************************************************************
* BITMAP_UnselectBitmap
*
* Unselect the bitmap from the DC. Used by SelectObject and DeleteDC.
*/
BOOL BITMAP_UnselectBitmap( DC * dc )
{
BITMAPOBJ * bmp;
BITMAP * bmpPtr;
if (!dc->w.hBitmap) return TRUE;
bmp = (BITMAPOBJ *) GDI_GetObjPtr( dc->w.hBitmap, BITMAP_MAGIC );
if (!bmp) return FALSE;
if (!(bmpPtr = (BITMAP *) GlobalLock( bmp->hBitmap ))) return FALSE;
BITMAP_CopyFromPixmap( bmpPtr, dc->u.x.drawable );
XFreePixmap( XT_display, dc->u.x.drawable );
bmp->bSelected = FALSE;
bmp->hdc = 0;
GlobalUnlock( bmp->hBitmap );
return TRUE;
}
/***********************************************************************
* BITMAP_SelectObject
*/
HBITMAP BITMAP_SelectObject( HDC hdc, DC * dc, HBITMAP hbitmap,
BITMAPOBJ * bitmap )
{
BITMAP * bmp;
HBITMAP prevHandle = dc->w.hBitmap;
if (!(dc->w.flags & DC_MEMORY)) return 0;
if (bitmap->bSelected && hbitmap != BITMAP_hbitmapMemDC) return 0;
if (!(bmp = (BITMAP *) GlobalLock( bitmap->hBitmap ))) return 0;
/* Make sure the bitmap has the right format */
if ((bmp->bmPlanes != 1) || !BITMAP_FindGCForDepth( bmp->bmBitsPixel ))
{
GlobalUnlock( bitmap->hBitmap );
return 0;
}
/* Unselect the previous bitmap */
if (!BITMAP_UnselectBitmap( dc ))
{
GlobalUnlock( bitmap->hBitmap );
return 0;
}
/* Create the pixmap */
dc->u.x.drawable = XCreatePixmap( XT_display,
DefaultRootWindow( XT_display ),
bmp->bmWidth, bmp->bmHeight,
bmp->bmBitsPixel );
BITMAP_CopyToPixmap( bmp, dc->u.x.drawable,
0, 0, bmp->bmWidth, bmp->bmHeight );
/* Change GC depth if needed */
if (dc->w.bitsPerPixel != bmp->bmBitsPixel)
{
XFreeGC( XT_display, dc->u.x.gc );
dc->u.x.gc = XCreateGC( XT_display, dc->u.x.drawable, 0, NULL );
dc->w.bitsPerPixel = bmp->bmBitsPixel;
DC_SetDeviceInfo( hdc, dc );
}
GlobalUnlock( bitmap->hBitmap );
dc->w.hBitmap = hbitmap;
bitmap->bSelected = TRUE;
bitmap->hdc = hdc;
return prevHandle;
}
/***********************************************************************
* GetBitmapDimensionEx (GDI.468)
*/
BOOL GetBitmapDimensionEx( HBITMAP hbitmap, LPSIZE size )
{
BITMAPOBJ * bmp = (BITMAPOBJ *) GDI_GetObjPtr( hbitmap, BITMAP_MAGIC );
if (!bmp) return FALSE;
*size = bmp->size;
return TRUE;
}
/***********************************************************************
* GetBitmapDimension (GDI.162)
*/
DWORD GetBitmapDimension( HBITMAP hbitmap )
{
SIZE size;
if (!GetBitmapDimensionEx( hbitmap, &size )) return 0;
return size.cx | (size.cy << 16);
}
/***********************************************************************
* SetBitmapDimensionEx (GDI.478)
*/
BOOL SetBitmapDimensionEx( HBITMAP hbitmap, short x, short y, LPSIZE prevSize )
{
BITMAPOBJ * bmp = (BITMAPOBJ *) GDI_GetObjPtr( hbitmap, BITMAP_MAGIC );
if (!bmp) return FALSE;
if (prevSize) *prevSize = bmp->size;
bmp->size.cx = x;
bmp->size.cy = y;
return TRUE;
}
/***********************************************************************
* SetBitmapDimension (GDI.163)
*/
DWORD SetBitmapDimension( HBITMAP hbitmap, short x, short y )
{
SIZE size;
if (!SetBitmapDimensionEx( hbitmap, x, y, &size )) return 0;
return size.cx | (size.cy << 16);
}

270
objects/brush.c Normal file
View File

@ -0,0 +1,270 @@
/*
* GDI brush objects
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "gdi.h"
extern Display * XT_display;
extern Screen * XT_screen;
#define NB_HATCH_STYLES 6
static char HatchBrushes[NB_HATCH_STYLES][8] =
{
{ 0x00, 0x00, 0x00, 0xff, 0x00, 0x00, 0x00, 0x00 }, /* HS_HORIZONTAL */
{ 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08 }, /* HS_VERTICAL */
{ 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80 }, /* HS_FDIAGONAL */
{ 0x80, 0x40, 0x20, 0x10, 0x08, 0x04, 0x02, 0x01 }, /* HS_BDIAGONAL */
{ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0x08 }, /* HS_CROSS */
{ 0x81, 0x42, 0x24, 0x18, 0x18, 0x24, 0x42, 0x81 } /* HS_DIAGCROSS */
};
extern XImage * BITMAP_BmpToImage( BITMAP *, void * );
/***********************************************************************
* CreateBrushIndirect (GDI.50)
*/
HBRUSH CreateBrushIndirect( LOGBRUSH * brush )
{
BRUSHOBJ * brushPtr;
HBRUSH hbrush = GDI_AllocObject( sizeof(BRUSHOBJ), BRUSH_MAGIC );
if (!hbrush) return 0;
brushPtr = (BRUSHOBJ *) GDI_HEAP_ADDR( hbrush );
memcpy( &brushPtr->logbrush, brush, sizeof(LOGBRUSH) );
return hbrush;
}
/***********************************************************************
* CreateHatchBrush (GDI.58)
*/
HBRUSH CreateHatchBrush( short style, COLORREF color )
{
LOGBRUSH logbrush = { BS_HATCHED, color, style };
#ifdef DEBUG_GDI
printf( "CreateHatchBrush: %d %06x\n", style, color );
#endif
if ((style < 0) || (style >= NB_HATCH_STYLES)) return 0;
return CreateBrushIndirect( &logbrush );
}
/***********************************************************************
* CreatePatternBrush (GDI.60)
*/
HBRUSH CreatePatternBrush( HBITMAP hbitmap )
{
LOGBRUSH logbrush = { BS_PATTERN, 0, 0 };
BITMAPOBJ * bmpObj;
BITMAP * bmp;
#ifdef DEBUG_GDI
printf( "CreatePatternBrush: %d\n", hbitmap );
#endif
/* Make a copy of the bitmap */
if (!(bmpObj = (BITMAPOBJ *) GDI_GetObjPtr( hbitmap, BITMAP_MAGIC )))
return 0;
if (!(bmp = (BITMAP *) GlobalLock( bmpObj->hBitmap ))) return 0;
logbrush.lbHatch = CreateBitmap( bmp->bmWidth, bmp->bmHeight,
bmp->bmPlanes, bmp->bmBitsPixel,
((char *)bmp) + sizeof(BITMAP) );
GlobalUnlock( bmpObj->hBitmap );
if (!logbrush.lbHatch) return 0;
return CreateBrushIndirect( &logbrush );
}
/***********************************************************************
* CreateDIBPatternBrush (GDI.445)
*/
HBRUSH CreateDIBPatternBrush( HANDLE hbitmap, WORD coloruse )
{
LOGBRUSH logbrush = { BS_DIBPATTERN, coloruse, 0 };
BITMAPINFO *info, *newInfo;
int size;
#ifdef DEBUG_GDI
printf( "CreateDIBPatternBrush: %d\n", hbitmap );
#endif
/* Make a copy of the bitmap */
if (!(info = (BITMAPINFO *) GlobalLock( hbitmap ))) return 0;
size = info->bmiHeader.biSizeImage;
if (!size)
size = (info->bmiHeader.biWidth * info->bmiHeader.biBitCount + 31) / 32
* 8 * info->bmiHeader.biHeight;
size += DIB_BitmapInfoSize( info, coloruse );
if (!(logbrush.lbHatch = GlobalAlloc( GMEM_MOVEABLE, size )))
{
GlobalUnlock( hbitmap );
return 0;
}
newInfo = (BITMAPINFO *) GlobalLock( logbrush.lbHatch );
memcpy( newInfo, info, size );
GlobalUnlock( logbrush.lbHatch );
GlobalUnlock( hbitmap );
return CreateBrushIndirect( &logbrush );
}
/***********************************************************************
* CreateSolidBrush (GDI.66)
*/
HBRUSH CreateSolidBrush( COLORREF color )
{
LOGBRUSH logbrush = { BS_SOLID, color, 0 };
#ifdef DEBUG_GDI
printf( "CreateSolidBrush: %06x\n", color );
#endif
return CreateBrushIndirect( &logbrush );
}
/***********************************************************************
* SetBrushOrg (GDI.148)
*/
DWORD SetBrushOrg( HDC hdc, short x, short y )
{
DWORD retval;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return FALSE;
retval = dc->w.brushOrgX | (dc->w.brushOrgY << 16);
dc->w.brushOrgX = x;
dc->w.brushOrgY = y;
return retval;
}
/***********************************************************************
* BRUSH_DeleteObject
*/
BOOL BRUSH_DeleteObject( HBRUSH hbrush, BRUSHOBJ * brush )
{
switch(brush->logbrush.lbStyle)
{
case BS_PATTERN:
DeleteObject( brush->logbrush.lbHatch );
break;
case BS_DIBPATTERN:
GlobalFree( brush->logbrush.lbHatch );
break;
}
return GDI_FreeObject( hbrush );
}
/***********************************************************************
* BRUSH_GetObject
*/
int BRUSH_GetObject( BRUSHOBJ * brush, int count, LPSTR buffer )
{
if (count > sizeof(LOGBRUSH)) count = sizeof(LOGBRUSH);
memcpy( buffer, &brush->logbrush, count );
return count;
}
/***********************************************************************
* BRUSH_SelectPatternBrush
*/
BOOL BRUSH_SelectPatternBrush( DC * dc, HBITMAP hbitmap )
{
BITMAPOBJ * bmpObjPtr;
BITMAP * bmp;
bmpObjPtr = (BITMAPOBJ *) GDI_GetObjPtr( hbitmap, BITMAP_MAGIC );
if (!bmpObjPtr) return FALSE;
if (!(bmp = (BITMAP *) GlobalLock( bmpObjPtr->hBitmap ))) return FALSE;
dc->u.x.brush.pixmap = XCreatePixmap( XT_display,
DefaultRootWindow(XT_display),
8, 8, bmp->bmBitsPixel );
BITMAP_CopyToPixmap( bmp, dc->u.x.brush.pixmap, 0, 0, 8, 8 );
if (bmp->bmBitsPixel > 1)
{
dc->u.x.brush.fillStyle = FillTiled;
XSetTile( XT_display, dc->u.x.gc, dc->u.x.brush.pixmap );
dc->u.x.brush.pixel = 0; /* Ignored */
}
else
{
dc->u.x.brush.fillStyle = FillOpaqueStippled;
XSetStipple( XT_display, dc->u.x.gc, dc->u.x.brush.pixmap );
dc->u.x.brush.pixel = -1; /* Special case (see DC_SetupGCForBrush) */
}
return TRUE;
}
/***********************************************************************
* BRUSH_SelectObject
*/
HBRUSH BRUSH_SelectObject( HDC hdc, DC * dc, HBRUSH hbrush, BRUSHOBJ * brush )
{
HBITMAP hBitmap;
BITMAPINFO * bmpInfo;
HBRUSH prevHandle = dc->w.hBrush;
dc->w.hBrush = hbrush;
if (dc->u.x.brush.pixmap)
{
XFreePixmap( XT_display, dc->u.x.brush.pixmap );
dc->u.x.brush.pixmap = 0;
}
dc->u.x.brush.style = brush->logbrush.lbStyle;
switch(brush->logbrush.lbStyle)
{
case BS_SOLID:
case BS_NULL:
dc->u.x.brush.pixel = GetNearestPaletteIndex( dc->w.hPalette,
brush->logbrush.lbColor );
dc->u.x.brush.fillStyle = FillSolid;
break;
case BS_HATCHED:
dc->u.x.brush.pixel = GetNearestPaletteIndex( dc->w.hPalette,
brush->logbrush.lbColor );
dc->u.x.brush.pixmap = XCreateBitmapFromData(XT_display,
DefaultRootWindow(XT_display),
HatchBrushes[brush->logbrush.lbHatch],
8, 8 );
XSetStipple( XT_display, dc->u.x.gc, dc->u.x.brush.pixmap );
dc->u.x.brush.fillStyle = FillStippled;
break;
case BS_PATTERN:
BRUSH_SelectPatternBrush( dc, brush->logbrush.lbHatch );
break;
case BS_DIBPATTERN:
if ((bmpInfo = (BITMAPINFO *) GlobalLock( brush->logbrush.lbHatch )))
{
int size = DIB_BitmapInfoSize( bmpInfo, brush->logbrush.lbColor );
hBitmap = CreateDIBitmap( hdc, &bmpInfo->bmiHeader, CBM_INIT,
((char *)bmpInfo) + size, bmpInfo,
(WORD) brush->logbrush.lbColor );
BRUSH_SelectPatternBrush( dc, hBitmap );
DeleteObject( hBitmap );
GlobalUnlock( brush->logbrush.lbHatch );
}
break;
}
return prevHandle;
}

354
objects/clipping.c Normal file
View File

@ -0,0 +1,354 @@
/*
* DC clipping functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdio.h>
#include "gdi.h"
/***********************************************************************
* CLIPPING_UpdateGCRegion
*
* Update the GC clip region when the ClipRgn of VisRgn have changed.
*/
static void CLIPPING_UpdateGCRegion( DC * dc )
{
if (!dc->w.hGCClipRgn) dc->w.hGCClipRgn = CreateRectRgn(0,0,0,0);
if (!dc->w.hVisRgn)
{
if (!dc->w.hClipRgn)
{
DeleteObject( dc->w.hGCClipRgn );
dc->w.hGCClipRgn = 0;
}
else
CombineRgn( dc->w.hGCClipRgn, dc->w.hClipRgn, 0, RGN_COPY );
}
else
{
if (!dc->w.hClipRgn)
CombineRgn( dc->w.hGCClipRgn, dc->w.hVisRgn, 0, RGN_COPY );
else
CombineRgn( dc->w.hGCClipRgn, dc->w.hClipRgn, dc->w.hVisRgn, RGN_AND );
}
if (dc->w.hGCClipRgn)
{
RGNOBJ *obj = (RGNOBJ *) GDI_GetObjPtr( dc->w.hGCClipRgn, REGION_MAGIC );
XSetClipMask( XT_display, dc->u.x.gc, obj->region.pixmap );
XSetClipOrigin( XT_display, dc->u.x.gc,
obj->region.box.left, obj->region.box.top );
}
else
{
XSetClipMask( XT_display, dc->u.x.gc, None );
XSetClipOrigin( XT_display, dc->u.x.gc, 0, 0 );
}
}
/***********************************************************************
* CLIPPING_SelectRgn
*
* Helper function for SelectClipRgn() and SelectVisRgn().
*/
static int CLIPPING_SelectRgn( DC * dc, HRGN * hrgnPrev, HRGN hrgn )
{
int retval;
if (hrgn)
{
if (!*hrgnPrev) *hrgnPrev = CreateRectRgn(0,0,0,0);
retval = CombineRgn( *hrgnPrev, hrgn, 0, RGN_COPY );
}
else
{
if (*hrgnPrev) DeleteObject( *hrgnPrev );
*hrgnPrev = 0;
retval = SIMPLEREGION; /* Clip region == client area */
}
CLIPPING_UpdateGCRegion( dc );
return retval;
}
/***********************************************************************
* SelectClipRgn (GDI.44)
*/
int SelectClipRgn( HDC hdc, HRGN hrgn )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "SelectClipRgn: %d %d\n", hdc, hrgn );
#endif
return CLIPPING_SelectRgn( dc, &dc->w.hClipRgn, hrgn );
}
/***********************************************************************
* SelectVisRgn (GDI.105)
*/
int SelectVisRgn( HDC hdc, HRGN hrgn )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "SelectVisRgn: %d %d\n", hdc, hrgn );
#endif
return CLIPPING_SelectRgn( dc, &dc->w.hVisRgn, hrgn );
}
/***********************************************************************
* OffsetClipRgn (GDI.32)
*/
int OffsetClipRgn( HDC hdc, short x, short y )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "OffsetClipRgn: %d %d,%d\n", hdc, x, y );
#endif
if (dc->w.hClipRgn)
{
int retval = OffsetRgn( dc->w.hClipRgn, x, y );
CLIPPING_UpdateGCRegion( dc );
return retval;
}
else return SIMPLEREGION; /* Clip region == client area */
}
/***********************************************************************
* OffsetVisRgn (GDI.102)
*/
int OffsetVisRgn( HDC hdc, short x, short y )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "OffsetVisRgn: %d %d,%d\n", hdc, x, y );
#endif
if (dc->w.hVisRgn)
{
int retval = OffsetRgn( dc->w.hVisRgn, x, y );
CLIPPING_UpdateGCRegion( dc );
return retval;
}
else return SIMPLEREGION; /* Clip region == client area */
}
/***********************************************************************
* CLIPPING_IntersectRect
*
* Helper function for {Intersect,Exclude}{Clip,Vis}Rect
*/
int CLIPPING_IntersectRect( DC * dc, HRGN * hrgn, short left, short top,
short right, short bottom, int exclude )
{
HRGN tempRgn, newRgn;
RGNOBJ *newObj, *prevObj;
int retval;
if (!*hrgn) return NULLREGION;
if (!(newRgn = CreateRectRgn( 0, 0, 0, 0))) return ERROR;
if (!(tempRgn = CreateRectRgn( left, top, right, bottom )))
{
DeleteObject( newRgn );
return ERROR;
}
retval = CombineRgn( newRgn, *hrgn, tempRgn, exclude ? RGN_DIFF : RGN_AND);
newObj = (RGNOBJ *) GDI_GetObjPtr( newRgn, REGION_MAGIC );
prevObj = (RGNOBJ *) GDI_GetObjPtr( *hrgn, REGION_MAGIC );
if (newObj && prevObj) newObj->header.hNext = prevObj->header.hNext;
DeleteObject( tempRgn );
DeleteObject( *hrgn );
*hrgn = newRgn;
CLIPPING_UpdateGCRegion( dc );
return retval;
}
/***********************************************************************
* ExcludeClipRect (GDI.21)
*/
int ExcludeClipRect( HDC hdc, short left, short top,
short right, short bottom )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "ExcludeClipRect: %d %dx%d,%dx%d\n",
hdc, left, top, right, bottom );
#endif
return CLIPPING_IntersectRect( dc, &dc->w.hClipRgn, left, top,
right, bottom, 1 );
}
/***********************************************************************
* IntersectClipRect (GDI.22)
*/
int IntersectClipRect( HDC hdc, short left, short top,
short right, short bottom )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "IntersectClipRect: %d %dx%d,%dx%d\n",
hdc, left, top, right, bottom );
#endif
return CLIPPING_IntersectRect( dc, &dc->w.hClipRgn, left, top,
right, bottom, 0 );
}
/***********************************************************************
* ExcludeVisRect (GDI.73)
*/
int ExcludeVisRect( HDC hdc, short left, short top,
short right, short bottom )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "ExcludeVisRect: %d %dx%d,%dx%d\n",
hdc, left, top, right, bottom );
#endif
return CLIPPING_IntersectRect( dc, &dc->w.hVisRgn, left, top,
right, bottom, 1 );
}
/***********************************************************************
* IntersectVisRect (GDI.98)
*/
int IntersectVisRect( HDC hdc, short left, short top,
short right, short bottom )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "IntersectVisRect: %d %dx%d,%dx%d\n",
hdc, left, top, right, bottom );
#endif
return CLIPPING_IntersectRect( dc, &dc->w.hVisRgn, left, top,
right, bottom, 0 );
}
/***********************************************************************
* PtVisible (GDI.103)
*/
BOOL PtVisible( HDC hdc, short x, short y )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "PtVisible: %d %d,%d\n", hdc, x, y );
#endif
if (!dc->w.hClipRgn) return FALSE;
return PtInRegion( dc->w.hClipRgn, x, y );
}
/***********************************************************************
* RectVisible (GDI.104)
*/
BOOL RectVisible( HDC hdc, LPRECT rect )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "RectVisible: %d %p\n", hdc, rect );
#endif
if (!dc->w.hClipRgn) return FALSE;
return RectInRegion( dc->w.hClipRgn, rect );
}
/***********************************************************************
* GetClipBox (GDI.77)
*/
int GetClipBox( HDC hdc, LPRECT rect )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "GetClipBox: %d %p\n", hdc, rect );
#endif
if (dc->w.hGCClipRgn) return GetRgnBox( dc->w.hGCClipRgn, rect );
else
{
Window root;
int width, height, x, y, border, depth;
XGetGeometry( XT_display, dc->u.x.drawable, &root, &x, &y,
&width, &height, &border, &depth );
rect->top = rect->left = 0;
rect->right = width & 0xffff;
rect->bottom = height & 0xffff;
return SIMPLEREGION;
}
}
/***********************************************************************
* SaveVisRgn (GDI.129)
*/
HRGN SaveVisRgn( HDC hdc )
{
HRGN copy;
RGNOBJ *obj, *copyObj;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
#ifdef DEBUG_CLIPPING
printf( "SaveVisRgn: %d\n", hdc );
#endif
if (!dc->w.hVisRgn) return 0;
if (!(obj = (RGNOBJ *) GDI_GetObjPtr( dc->w.hVisRgn, REGION_MAGIC )))
return 0;
if (!(copy = CreateRectRgn( 0, 0, 0, 0 ))) return 0;
CombineRgn( copy, dc->w.hVisRgn, 0, RGN_COPY );
if (!(copyObj = (RGNOBJ *) GDI_GetObjPtr( copy, REGION_MAGIC )))
return 0;
copyObj->header.hNext = obj->header.hNext;
obj->header.hNext = copy;
return copy;
}
/***********************************************************************
* RestoreVisRgn (GDI.130)
*/
int RestoreVisRgn( HDC hdc )
{
HRGN saved;
RGNOBJ *obj, *savedObj;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return ERROR;
#ifdef DEBUG_CLIPPING
printf( "RestoreVisRgn: %d\n", hdc );
#endif
if (!dc->w.hVisRgn) return ERROR;
if (!(obj = (RGNOBJ *) GDI_GetObjPtr( dc->w.hVisRgn, REGION_MAGIC )))
return ERROR;
if (!(saved = obj->header.hNext)) return ERROR;
if (!(savedObj = (RGNOBJ *) GDI_GetObjPtr( saved, REGION_MAGIC )))
return ERROR;
DeleteObject( dc->w.hVisRgn );
dc->w.hVisRgn = saved;
CLIPPING_UpdateGCRegion( dc );
return savedObj->region.type;
}

142
objects/dcvalues.c Normal file
View File

@ -0,0 +1,142 @@
/*
* DC device-independent Get/SetXXX functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "gdi.h"
/* Default DC values */
const WIN_DC_INFO DCVAL_defaultValues =
{
0, /* flags */
NULL, /* devCaps */
0, /* hMetaFile */
0, /* hClipRgn */
0, /* hVisRgn */
0, /* hGCClipRgn */
STOCK_BLACK_PEN, /* hPen */
STOCK_WHITE_BRUSH, /* hBrush */
STOCK_SYSTEM_FONT, /* hFont */
0, /* hBitmap */
0, /* hDevice */
STOCK_DEFAULT_PALETTE, /* hPalette */
R2_COPYPEN, /* ROPmode */
ALTERNATE, /* polyFillMode */
BLACKONWHITE, /* stretchBltMode */
ABSOLUTE, /* relAbsMode */
OPAQUE, /* backgroundMode */
RGB( 255, 255, 255 ), /* backgroundColor */
RGB( 0, 0, 0 ), /* textColor */
0, /* backgroundPixel */
0, /* textPixel */
0, /* brushOrgX */
0, /* brushOrgY */
TA_LEFT | TA_TOP | TA_NOUPDATECP, /* textAlign */
0, /* charExtra */
0, /* breakTotalExtra */
0, /* breakCount */
0, /* breakExtra */
0, /* breakRem */
1, /* planes */
1, /* bitsPerPixel */
MM_TEXT, /* MapMode */
0, /* DCOrgX */
0, /* DCOrgY */
0, /* CursPosX */
0, /* CursPosY */
0, /* WndOrgX */
0, /* WndOrgY */
1, /* WndExtX */
1, /* WndExtY */
0, /* VportOrgX */
0, /* VportOrgY */
1, /* VportExtX */
1 /* VportExtY */
};
#define DC_GET_VAL( func_type, func_name, dc_field ) \
func_type func_name( HDC hdc ) \
{ \
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ); \
if (!dc) return 0; \
return dc->w.dc_field; \
}
#define DC_GET_X_Y( func_type, func_name, ret_x, ret_y ) \
func_type func_name( HDC hdc ) \
{ \
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ); \
if (!dc) return 0; \
return dc->w.ret_x | (dc->w.ret_y << 16); \
}
#define DC_GET_VAL_EX( func_name, ret_x, ret_y ) \
BOOL func_name( HDC hdc, LPPOINT pt ) \
{ \
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ); \
if (!dc) return FALSE; \
pt->x = dc->w.ret_x; \
pt->y = dc->w.ret_y; \
return TRUE; \
}
#define DC_SET_VAL( func_type, func_name, dc_field ) \
func_type func_name( HDC hdc, func_type val ) \
{ \
func_type prevVal; \
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ); \
if (!dc) return 0; \
prevVal = dc->w.dc_field; \
dc->w.dc_field = val; \
return prevVal; \
}
#define DC_SET_MODE( func_name, dc_field, min_val, max_val ) \
WORD func_name( HDC hdc, WORD mode ) \
{ \
WORD prevMode; \
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ); \
if (!dc) return 0; \
if ((mode < min_val) || (mode > max_val)) return 0; \
prevMode = dc->w.dc_field; \
dc->w.dc_field = mode; \
return prevMode; \
}
DC_SET_MODE( SetBkMode, backgroundMode, TRANSPARENT, OPAQUE ) /* GDI.2 */
DC_SET_MODE( SetROP2, ROPmode, R2_BLACK, R2_WHITE ) /* GDI.4 */
DC_SET_MODE( SetRelAbs, relAbsMode, ABSOLUTE, RELATIVE ) /* GDI.5 */
DC_SET_MODE( SetPolyFillMode, polyFillMode, ALTERNATE, WINDING ) /* GDI.6 */
DC_SET_MODE( SetStretchBltMode, stretchBltMode,
BLACKONWHITE, COLORONCOLOR ) /* GDI.7 */
DC_GET_VAL( COLORREF, GetBkColor, backgroundColor ) /* GDI.75 */
DC_GET_VAL( WORD, GetBkMode, backgroundMode ) /* GDI.76 */
DC_GET_X_Y( DWORD, GetCurrentPosition, CursPosX, CursPosY ) /* GDI.78 */
DC_GET_X_Y( DWORD, GetDCOrg, DCOrgX, DCOrgY ) /* GDI.79 */
DC_GET_VAL( WORD, GetMapMode, MapMode ) /* GDI.81 */
DC_GET_VAL( WORD, GetPolyFillMode, polyFillMode ) /* GDI.84 */
DC_GET_VAL( WORD, GetROP2, ROPmode ) /* GDI.85 */
DC_GET_VAL( WORD, GetRelAbs, relAbsMode ) /* GDI.86 */
DC_GET_VAL( WORD, GetStretchBltMode, stretchBltMode ) /* GDI.88 */
DC_GET_VAL( COLORREF, GetTextColor, textColor ) /* GDI.90 */
DC_GET_X_Y( DWORD, GetViewportExt, VportExtX, VportExtY ) /* GDI.94 */
DC_GET_X_Y( DWORD, GetViewportOrg, VportOrgX, VportOrgY ) /* GDI.95 */
DC_GET_X_Y( DWORD, GetWindowExt, WndExtX, WndExtY ) /* GDI.96 */
DC_GET_X_Y( DWORD, GetWindowOrg, WndOrgX, WndOrgY ) /* GDI.97 */
DC_GET_VAL( HRGN, InquireVisRgn, hVisRgn ) /* GDI.131 */
DC_GET_X_Y( DWORD, GetBrushOrg, brushOrgX, brushOrgY ) /* GDI.149 */
DC_GET_VAL( HRGN, GetClipRgn, hClipRgn ) /* GDI.173 */
DC_GET_VAL( WORD, GetTextAlign, textAlign ) /* GDI.345 */
DC_SET_VAL( WORD, SetTextAlign, textAlign ) /* GDI.346 */
DC_GET_VAL( HFONT, GetCurLogFont, hFont ) /* GDI.411 */
DC_GET_VAL_EX( GetBrushOrgEx, brushOrgX, brushOrgY ) /* GDI.469 */
DC_GET_VAL_EX( GetCurrentPositionEx, CursPosX, CursPosY ) /* GDI.470 */
DC_GET_VAL_EX( GetViewportExtEx, VportExtX, VportExtY ) /* GDI.472 */
DC_GET_VAL_EX( GetViewportOrgEx, VportOrgX, VportOrgY ) /* GDI.473 */
DC_GET_VAL_EX( GetWindowExtEx, WndExtX, WndExtY ) /* GDI.474 */
DC_GET_VAL_EX( GetWindowOrgEx, WndOrgX, WndOrgY ) /* GDI.475 */

203
objects/dib.c Normal file
View File

@ -0,0 +1,203 @@
/*
* GDI device independent bitmaps
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdlib.h>
#include "gdi.h"
extern XImage * BITMAP_BmpToImage( BITMAP *, void * );
/***********************************************************************
* DIB_BitmapInfoSize
*
* Return the size of the bitmap info structure.
*/
int DIB_BitmapInfoSize( BITMAPINFO * info, WORD coloruse )
{
int size = info->bmiHeader.biClrUsed;
if (!size && (info->bmiHeader.biBitCount != 24))
size = 1 << info->bmiHeader.biBitCount;
if (coloruse == DIB_RGB_COLORS)
size = info->bmiHeader.biSize + size * sizeof(RGBQUAD);
else
size = info->bmiHeader.biSize + size * sizeof(WORD);
return size;
}
/***********************************************************************
* DIB_DIBmpToImage
*
* Create an XImage pointing to the bitmap data.
*/
XImage * DIB_DIBmpToImage( BITMAPINFOHEADER * bmp, void * bmpData )
{
XImage * image;
int bytesPerLine = (bmp->biWidth * bmp->biBitCount + 31) / 32 * 4;
image = XCreateImage( XT_display, DefaultVisualOfScreen( XT_screen ),
bmp->biBitCount, ZPixmap, 0, bmpData,
bmp->biWidth, bmp->biHeight, 32, bytesPerLine );
if (!image) return 0;
image->byte_order = MSBFirst;
image->bitmap_bit_order = MSBFirst;
image->bitmap_unit = 16;
_XInitImageFuncPtrs(image);
return image;
}
/***********************************************************************
* SetDIBits (GDI.440)
*/
int SetDIBits( HDC hdc, HBITMAP hbitmap, WORD startscan, WORD lines,
LPSTR bits, BITMAPINFO * info, WORD coloruse )
{
DC * dc;
BITMAPOBJ * bmpObj;
BITMAP * bmp;
WORD * colorMapping;
RGBQUAD * rgbPtr;
XImage * bmpImage, * dibImage;
int i, x, y, pixel, colors;
if (!lines) return 0;
if (!(dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ))) return 0;
if (!(bmpObj = (BITMAPOBJ *)GDI_GetObjPtr( hbitmap, BITMAP_MAGIC )))
return 0;
if (!(bmp = (BITMAP *) GlobalLock( bmpObj->hBitmap ))) return 0;
/* Build the color mapping table */
if (info->bmiHeader.biBitCount == 24) colorMapping = NULL;
else if (coloruse == DIB_RGB_COLORS)
{
colors = info->bmiHeader.biClrUsed;
if (!colors) colors = 1 << info->bmiHeader.biBitCount;
if (!(colorMapping = (WORD *)malloc( colors * sizeof(WORD) )))
{
GlobalUnlock( bmpObj->hBitmap );
return 0;
}
for (i = 0, rgbPtr = info->bmiColors; i < colors; i++, rgbPtr++)
colorMapping[i] = GetNearestPaletteIndex( dc->w.hPalette,
RGB(rgbPtr->rgbRed,
rgbPtr->rgbGreen,
rgbPtr->rgbBlue) );
}
else colorMapping = (WORD *)info->bmiColors;
/* Transfer the pixels (very slow...) */
bmpImage = BITMAP_BmpToImage( bmp, ((char *)bmp) + sizeof(BITMAP) );
dibImage = DIB_DIBmpToImage( &info->bmiHeader, bits );
for (y = 0; y < lines; y++)
{
for (x = 0; x < info->bmiHeader.biWidth; x++)
{
pixel = XGetPixel( dibImage, x, y );
if (colorMapping) pixel = colorMapping[pixel];
else pixel = GetNearestPaletteIndex(dc->w.hPalette,(COLORREF)pixel);
XPutPixel( bmpImage, x, bmp->bmHeight - startscan - y - 1, pixel );
}
}
bmpImage->data = NULL;
dibImage->data = NULL;
XDestroyImage( bmpImage );
XDestroyImage( dibImage );
if (colorMapping && (coloruse == DIB_RGB_COLORS)) free(colorMapping);
GlobalUnlock( bmpObj->hBitmap );
return lines;
}
/***********************************************************************
* GetDIBits (GDI.441)
*/
int GetDIBits( HDC hdc, HBITMAP hbitmap, WORD startscan, WORD lines,
LPSTR bits, BITMAPINFO * info, WORD coloruse )
{
DC * dc;
BITMAPOBJ * bmpObj;
BITMAP * bmp;
PALETTEENTRY * palEntry;
PALETTEOBJ * palette;
XImage * bmpImage, * dibImage;
int i, x, y;
if (!lines) return 0;
if (!(dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ))) return 0;
if (!(bmpObj = (BITMAPOBJ *)GDI_GetObjPtr( hbitmap, BITMAP_MAGIC )))
return 0;
if (!(palette = (PALETTEOBJ*)GDI_GetObjPtr( dc->w.hPalette, PALETTE_MAGIC )))
return 0;
if (!(bmp = (BITMAP *) GlobalLock( bmpObj->hBitmap ))) return 0;
/* Transfer color info */
palEntry = palette->logpalette.palPalEntry;
for (i = 0; i < info->bmiHeader.biClrUsed; i++, palEntry++)
{
if (coloruse == DIB_RGB_COLORS)
{
info->bmiColors[i].rgbRed = palEntry->peRed;
info->bmiColors[i].rgbGreen = palEntry->peGreen;
info->bmiColors[i].rgbBlue = palEntry->peBlue;
info->bmiColors[i].rgbReserved = 0;
}
else ((WORD *)info->bmiColors)[i] = (WORD)i;
}
/* Transfer the pixels (very slow...) */
if (bits)
{
bmpImage = BITMAP_BmpToImage( bmp, ((char *)bmp) + sizeof(BITMAP) );
dibImage = DIB_DIBmpToImage( &info->bmiHeader, bits );
for (y = 0; y < lines; y++)
{
for (x = 0; x < info->bmiHeader.biWidth; x++)
{
XPutPixel( dibImage, x, y,
XGetPixel(bmpImage, x, bmp->bmHeight-startscan-y-1) );
}
}
bmpImage->data = NULL;
dibImage->data = NULL;
XDestroyImage( bmpImage );
XDestroyImage( dibImage );
}
GlobalUnlock( bmpObj->hBitmap );
return lines;
}
/***********************************************************************
* CreateDIBitmap (GDI.442)
*/
HBITMAP CreateDIBitmap( HDC hdc, BITMAPINFOHEADER * header, DWORD init,
LPSTR bits, BITMAPINFO * data, WORD coloruse )
{
HBITMAP handle;
handle = CreateCompatibleBitmap( hdc, header->biWidth, header->biHeight );
if (!handle) return 0;
if (init == CBM_INIT) SetDIBits( hdc, handle, 0, header->biHeight,
bits, data, coloruse );
return handle;
}

332
objects/font.c Normal file
View File

@ -0,0 +1,332 @@
/*
* GDI font objects
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdio.h>
#include <stdlib.h>
#include <X11/Xatom.h>
#include "gdi.h"
extern Display * XT_display;
extern Screen * XT_screen;
/***********************************************************************
* FONT_MatchFont
*
* Find a X font matching the logical font.
*/
XFontStruct * FONT_MatchFont( DC * dc, LOGFONT * font )
{
char pattern[100];
char *family, *weight, *charset;
char **names;
char slant, spacing;
int width, height, count;
XFontStruct * fontStruct;
weight = (font->lfWeight > 550) ? "bold" : "medium";
slant = font->lfItalic ? 'i' : 'r';
height = font->lfHeight * 10;
width = font->lfWidth * 10;
spacing = (font->lfPitchAndFamily & FIXED_PITCH) ? 'm' :
(font->lfPitchAndFamily & VARIABLE_PITCH) ? 'p' : '*';
charset = (font->lfCharSet == ANSI_CHARSET) ? "iso8859-1" : "*";
family = font->lfFaceName;
if (!*family) switch(font->lfPitchAndFamily & 0xf0)
{
case FF_ROMAN: family = "times"; break;
case FF_SWISS: family = "helvetica"; break;
case FF_MODERN: family = "courier"; break;
case FF_SCRIPT: family = "*"; break;
case FF_DECORATIVE: family = "*"; break;
default: family = "*"; break;
}
sprintf( pattern, "-*-%s-%s-%c-normal--*-%d-*-*-%c-%d-%s",
family, weight, slant, height, spacing, width, charset );
#ifdef DEBUG_FONT
printf( "FONT_MatchFont: '%s'\n", pattern );
#endif
names = XListFonts( XT_display, pattern, 1, &count );
if (!count)
{
#ifdef DEBUG_FONT
printf( " No matching font found\n" );
#endif
return NULL;
}
#ifdef DEBUG_FONT
printf( " Found '%s'\n", *names );
#endif
fontStruct = XLoadQueryFont( XT_display, *names );
XFreeFontNames( names );
return fontStruct;
}
/***********************************************************************
* FONT_GetMetrics
*/
void FONT_GetMetrics( LOGFONT * logfont, XFontStruct * xfont,
TEXTMETRIC * metrics )
{
int average, i;
unsigned long prop;
metrics->tmAscent = xfont->ascent;
metrics->tmDescent = xfont->descent;
metrics->tmHeight = xfont->ascent + xfont->descent;
metrics->tmInternalLeading = 0;
if (XGetFontProperty( xfont, XA_X_HEIGHT, &prop ))
metrics->tmInternalLeading = xfont->ascent - (short)prop;
metrics->tmExternalLeading = 0;
metrics->tmMaxCharWidth = xfont->max_bounds.width;
metrics->tmWeight = logfont->lfWeight;
metrics->tmItalic = logfont->lfItalic;
metrics->tmUnderlined = logfont->lfUnderline;
metrics->tmStruckOut = logfont->lfStrikeOut;
metrics->tmFirstChar = xfont->min_char_or_byte2;
metrics->tmLastChar = xfont->max_char_or_byte2;
metrics->tmDefaultChar = xfont->default_char;
metrics->tmBreakChar = ' ';
metrics->tmPitchAndFamily = logfont->lfPitchAndFamily;
metrics->tmCharSet = logfont->lfCharSet;
metrics->tmOverhang = 0;
metrics->tmDigitizedAspectX = 1;
metrics->tmDigitizedAspectY = 1;
if (xfont->per_char) average = metrics->tmMaxCharWidth;
else
{
XCharStruct * charPtr = xfont->per_char;
average = 0;
for (i = metrics->tmFirstChar; i <= metrics->tmLastChar; i++)
{
average += charPtr->width;
charPtr++;
}
average /= metrics->tmLastChar - metrics->tmFirstChar + 1;
}
metrics->tmAveCharWidth = average;
}
/***********************************************************************
* CreateFontIndirect (GDI.57)
*/
HFONT CreateFontIndirect( LOGFONT * font )
{
FONTOBJ * fontPtr;
HFONT hfont = GDI_AllocObject( sizeof(FONTOBJ), FONT_MAGIC );
if (!hfont) return 0;
fontPtr = (FONTOBJ *) GDI_HEAP_ADDR( hfont );
memcpy( &fontPtr->logfont, font, sizeof(LOGFONT) );
return hfont;
}
/***********************************************************************
* CreateFont (GDI.56)
*/
HFONT CreateFont( int height, int width, int esc, int orient, int weight,
BYTE italic, BYTE underline, BYTE strikeout, BYTE charset,
BYTE outpres, BYTE clippres, BYTE quality, BYTE pitch,
LPSTR name )
{
LOGFONT logfont = { height, width, esc, orient, weight, italic, underline,
strikeout, charset, outpres, clippres, quality, pitch, };
strncpy( logfont.lfFaceName, name, LF_FACESIZE );
return CreateFontIndirect( &logfont );
}
/***********************************************************************
* FONT_GetObject
*/
int FONT_GetObject( FONTOBJ * font, int count, LPSTR buffer )
{
if (count > sizeof(LOGFONT)) count = sizeof(LOGFONT);
memcpy( buffer, &font->logfont, count );
return count;
}
/***********************************************************************
* FONT_SelectObject
*/
HFONT FONT_SelectObject( DC * dc, HFONT hfont, FONTOBJ * font )
{
static X_PHYSFONT stockFonts[LAST_STOCK_FONT-FIRST_STOCK_FONT+1];
X_PHYSFONT * stockPtr;
HFONT prevHandle = dc->w.hFont;
XFontStruct * fontStruct;
/* Load font if necessary */
if ((hfont >= FIRST_STOCK_FONT) && (hfont <= LAST_STOCK_FONT))
stockPtr = &stockFonts[hfont - FIRST_STOCK_FONT];
else stockPtr = NULL;
if (!stockPtr || !stockPtr->fstruct)
{
fontStruct = FONT_MatchFont( dc, &font->logfont );
}
else
{
fontStruct = stockPtr->fstruct;
#ifdef DEBUG_FONT
printf( "FONT_SelectObject: Loaded font from cache %x %p\n",
hfont, fontStruct );
#endif
}
if (!fontStruct) return 0;
/* Free previous font */
if ((prevHandle < FIRST_STOCK_FONT) || (prevHandle > LAST_STOCK_FONT))
{
if (dc->u.x.font.fstruct)
XFreeFont( XT_display, dc->u.x.font.fstruct );
}
/* Store font */
dc->w.hFont = hfont;
if (stockPtr)
{
if (!stockPtr->fstruct)
{
stockPtr->fstruct = fontStruct;
FONT_GetMetrics( &font->logfont, fontStruct, &stockPtr->metrics );
}
memcpy( &dc->u.x.font, stockPtr, sizeof(*stockPtr) );
}
else
{
dc->u.x.font.fstruct = fontStruct;
FONT_GetMetrics( &font->logfont, fontStruct, &dc->u.x.font.metrics );
}
return prevHandle;
}
/***********************************************************************
* GetTextCharacterExtra (GDI.89)
*/
short GetTextCharacterExtra( HDC hdc )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
return abs( (dc->w.charExtra * dc->w.WndExtX + dc->w.VportExtX / 2)
/ dc->w.VportExtX );
}
/***********************************************************************
* SetTextCharacterExtra (GDI.8)
*/
short SetTextCharacterExtra( HDC hdc, short extra )
{
short prev;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
extra = (extra * dc->w.VportExtX + dc->w.WndExtX / 2) / dc->w.WndExtX;
prev = dc->w.charExtra;
dc->w.charExtra = abs(extra);
return (prev * dc->w.WndExtX + dc->w.VportExtX / 2) / dc->w.VportExtX;
}
/***********************************************************************
* SetTextJustification (GDI.10)
*/
short SetTextJustification( HDC hdc, short extra, short breaks )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
extra = abs((extra * dc->w.VportExtX + dc->w.WndExtX / 2) / dc->w.WndExtX);
if (!extra) breaks = 0;
dc->w.breakTotalExtra = extra;
dc->w.breakCount = breaks;
if (breaks)
{
dc->w.breakExtra = extra / breaks;
dc->w.breakRem = extra - (dc->w.breakCount * dc->w.breakExtra);
}
else
{
dc->w.breakExtra = 0;
dc->w.breakRem = 0;
}
return 1;
}
/***********************************************************************
* GetTextExtent (GDI.91)
*/
DWORD GetTextExtent( HDC hdc, LPSTR str, short count )
{
SIZE size;
if (!GetTextExtentPoint( hdc, str, count, &size )) return 0;
return size.cx | (size.cy << 16);
}
/***********************************************************************
* GetTextExtentPoint (GDI.471)
*/
BOOL GetTextExtentPoint( HDC hdc, LPSTR str, short count, LPSIZE size )
{
int dir, ascent, descent;
XCharStruct info;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return FALSE;
XTextExtents( dc->u.x.font.fstruct, str, count, &dir,
&ascent, &descent, &info );
size->cx = abs((info.width + dc->w.breakRem + count * dc->w.charExtra)
* dc->w.WndExtX / dc->w.VportExtX);
size->cy = abs((dc->u.x.font.fstruct->ascent+dc->u.x.font.fstruct->descent)
* dc->w.WndExtY / dc->w.VportExtY);
#ifdef DEBUG_FONT
printf( "GetTextExtentPoint(%d '%s' %d %p): returning %d,%d\n",
hdc, str, count, size, size->cx, size->cy );
#endif
return TRUE;
}
/***********************************************************************
* GetTextMetrics (GDI.93)
*/
BOOL GetTextMetrics( HDC hdc, LPTEXTMETRIC metrics )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return FALSE;
memcpy( metrics, &dc->u.x.font.metrics, sizeof(*metrics) );
metrics->tmAscent = abs( metrics->tmAscent
* dc->w.WndExtY / dc->w.VportExtY );
metrics->tmDescent = abs( metrics->tmDescent
* dc->w.WndExtY / dc->w.VportExtY );
metrics->tmHeight = metrics->tmAscent + metrics->tmDescent;
metrics->tmInternalLeading = abs( metrics->tmInternalLeading
* dc->w.WndExtY / dc->w.VportExtY );
metrics->tmExternalLeading = abs( metrics->tmExternalLeading
* dc->w.WndExtY / dc->w.VportExtY );
metrics->tmMaxCharWidth = abs( metrics->tmMaxCharWidth
* dc->w.WndExtX / dc->w.VportExtX );
metrics->tmAveCharWidth = abs( metrics->tmAveCharWidth
* dc->w.WndExtX / dc->w.VportExtX );
return TRUE;
}

380
objects/gdiobj.c Normal file
View File

@ -0,0 +1,380 @@
/*
* GDI functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "gdi.h"
extern Display * XT_display;
extern Screen * XT_screen;
MDESC *GDI_Heap = NULL;
/***********************************************************************
* GDI stock objects
*/
static BRUSHOBJ WhiteBrush =
{
{ 0, BRUSH_MAGIC, 1, 0 }, /* header */
{ BS_SOLID, RGB(255,255,255), 0 } /* logbrush */
};
static BRUSHOBJ LtGrayBrush =
{
{ 0, BRUSH_MAGIC, 1, 0 }, /* header */
{ BS_SOLID, RGB(192,192,192), 0 } /* logbrush */
};
static BRUSHOBJ GrayBrush =
{
{ 0, BRUSH_MAGIC, 1, 0 }, /* header */
{ BS_SOLID, RGB(128,128,128), 0 } /* logbrush */
};
static BRUSHOBJ DkGrayBrush =
{
{ 0, BRUSH_MAGIC, 1, 0 }, /* header */
{ BS_SOLID, RGB(64,64,64), 0 } /* logbrush */
};
static BRUSHOBJ BlackBrush =
{
{ 0, BRUSH_MAGIC, 1, 0 }, /* header */
{ BS_SOLID, RGB(0,0,0), 0 } /* logbrush */
};
static BRUSHOBJ NullBrush =
{
{ 0, BRUSH_MAGIC, 1, 0 }, /* header */
{ BS_NULL, 0, 0 } /* logbrush */
};
static PENOBJ WhitePen =
{
{ 0, PEN_MAGIC, 1, 0 }, /* header */
{ PS_SOLID, { 1, 0 }, RGB(255,255,255) } /* logpen */
};
static PENOBJ BlackPen =
{
{ 0, PEN_MAGIC, 1, 0 }, /* header */
{ PS_SOLID, { 1, 0 }, RGB(0,0,0) } /* logpen */
};
static PENOBJ NullPen =
{
{ 0, PEN_MAGIC, 1, 0 }, /* header */
{ PS_NULL, { 1, 0 }, 0 } /* logpen */
};
static FONTOBJ OEMFixedFont =
{
{ 0, FONT_MAGIC, 1, 0 }, /* header */
{ 12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, OEM_CHARSET,
0, 0, DEFAULT_QUALITY, FIXED_PITCH | FF_MODERN, "" }
};
static FONTOBJ AnsiFixedFont =
{
{ 0, FONT_MAGIC, 1, 0 }, /* header */
{ 12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
0, 0, DEFAULT_QUALITY, FIXED_PITCH | FF_MODERN, "" }
};
static FONTOBJ AnsiVarFont =
{
{ 0, FONT_MAGIC, 1, 0 }, /* header */
{ 12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
0, 0, DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, "" }
};
static FONTOBJ SystemFont =
{
{ 0, FONT_MAGIC, 1, 0 }, /* header */
{ 12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
0, 0, DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, "" }
};
static FONTOBJ DeviceDefaultFont =
{
{ 0, FONT_MAGIC, 1, 0 }, /* header */
{ 12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
0, 0, DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, "" }
};
static FONTOBJ SystemFixedFont =
{
{ 0, FONT_MAGIC, 1, 0 }, /* header */
{ 12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
0, 0, DEFAULT_QUALITY, FIXED_PITCH | FF_MODERN, "" }
};
static GDIOBJHDR * StockObjects[NB_STOCK_OBJECTS] =
{
(GDIOBJHDR *) &WhiteBrush,
(GDIOBJHDR *) &LtGrayBrush,
(GDIOBJHDR *) &GrayBrush,
(GDIOBJHDR *) &DkGrayBrush,
(GDIOBJHDR *) &BlackBrush,
(GDIOBJHDR *) &NullBrush,
(GDIOBJHDR *) &WhitePen,
(GDIOBJHDR *) &BlackPen,
(GDIOBJHDR *) &NullPen,
NULL,
(GDIOBJHDR *) &OEMFixedFont,
(GDIOBJHDR *) &AnsiFixedFont,
(GDIOBJHDR *) &AnsiVarFont,
(GDIOBJHDR *) &SystemFont,
(GDIOBJHDR *) &DeviceDefaultFont,
NULL, /* DEFAULT_PALETTE created by PALETTE_Init */
(GDIOBJHDR *) &SystemFixedFont
};
extern GDIOBJHDR * PALETTE_systemPalette;
/***********************************************************************
* GDI_Init
*
* GDI initialisation.
*/
BOOL GDI_Init()
{
struct segment_descriptor_s * s;
/* Create GDI heap */
s = GetNextSegment( 0, 0x10000 );
if (s == NULL) return FALSE;
HEAP_Init( &GDI_Heap, s->base_addr, GDI_HEAP_SIZE );
free(s);
/* Create default palette */
PALETTE_Init();
StockObjects[DEFAULT_PALETTE] = PALETTE_systemPalette;
/* Create default bitmap */
if (!BITMAP_Init()) return FALSE;
/* Initialise regions */
if (!REGION_Init()) return FALSE;
return TRUE;
}
/***********************************************************************
* GDI_FindPrevObject
*
* Return the GDI object whose hNext field points to obj.
*/
HANDLE GDI_FindPrevObject( HANDLE first, HANDLE obj )
{
HANDLE handle;
for (handle = first; handle && (handle != obj); )
{
GDIOBJHDR * header = (GDIOBJHDR *) GDI_HEAP_ADDR( handle );
handle = header->hNext;
}
return handle;
}
/***********************************************************************
* GDI_AllocObject
*/
HANDLE GDI_AllocObject( WORD size, WORD magic )
{
static DWORD count = 0;
GDIOBJHDR * obj;
HANDLE handle = GDI_HEAP_ALLOC( GMEM_MOVEABLE, size );
if (!handle) return 0;
obj = (GDIOBJHDR *) GDI_HEAP_ADDR( handle );
obj->hNext = 0;
obj->wMagic = magic;
obj->dwCount = ++count;
return handle;
}
/***********************************************************************
* GDI_FreeObject
*/
BOOL GDI_FreeObject( HANDLE handle )
{
GDIOBJHDR * object;
HANDLE prev;
/* Can't free stock objects */
if (handle >= FIRST_STOCK_HANDLE) return FALSE;
object = (GDIOBJHDR *) GDI_HEAP_ADDR( handle );
if (!object) return FALSE;
/* Free object */
GDI_HEAP_FREE( handle );
return TRUE;
}
/***********************************************************************
* GDI_GetObjPtr
*
* Return a pointer to the GDI object associated to the handle.
* Return NULL if the object has the wrong magic number.
*/
GDIOBJHDR * GDI_GetObjPtr( HANDLE handle, WORD magic )
{
GDIOBJHDR * ptr = NULL;
if (handle >= FIRST_STOCK_HANDLE)
{
if (handle < FIRST_STOCK_HANDLE + NB_STOCK_OBJECTS)
ptr = StockObjects[handle - FIRST_STOCK_HANDLE];
}
else ptr = (GDIOBJHDR *) GDI_HEAP_ADDR( handle );
if (!ptr) return NULL;
if (ptr->wMagic != magic) return NULL;
return ptr;
}
/***********************************************************************
* DeleteObject (GDI.69)
*/
BOOL DeleteObject( HANDLE obj )
{
/* Check if object is valid */
GDIOBJHDR * header = (GDIOBJHDR *) GDI_HEAP_ADDR( obj );
if (!header) return FALSE;
#ifdef DEBUG_GDI
printf( "DeleteObject: %d\n", obj );
#endif
/* Delete object */
switch(header->wMagic)
{
case PEN_MAGIC: return GDI_FreeObject( obj );
case BRUSH_MAGIC: return BRUSH_DeleteObject( obj, header );
case FONT_MAGIC: return GDI_FreeObject( obj );
case PALETTE_MAGIC: return GDI_FreeObject( obj );
case BITMAP_MAGIC: return BMP_DeleteObject( obj, header );
case REGION_MAGIC: return REGION_DeleteObject( obj, header );
}
return FALSE;
}
/***********************************************************************
* GetStockObject (GDI.87)
*/
HANDLE GetStockObject( int obj )
{
if ((obj < 0) || (obj >= NB_STOCK_OBJECTS)) return 0;
if (!StockObjects[obj]) return 0;
#ifdef DEBUG_GDI
printf( "GetStockObject: returning %04x\n", FIRST_STOCK_HANDLE + obj );
#endif
return FIRST_STOCK_HANDLE + obj;
}
/***********************************************************************
* GetObject (GDI.82)
*/
int GetObject( HANDLE handle, int count, LPSTR buffer )
{
GDIOBJHDR * ptr = NULL;
#ifdef DEBUG_GDI
printf( "GetObject: %04x %d %08x\n", handle, count, buffer );
#endif
if (!count) return 0;
if (handle >= FIRST_STOCK_HANDLE)
{
if (handle < FIRST_STOCK_HANDLE + NB_STOCK_OBJECTS)
ptr = StockObjects[handle - FIRST_STOCK_HANDLE];
}
else ptr = (GDIOBJHDR *) GDI_HEAP_ADDR( handle );
if (!ptr) return 0;
switch(ptr->wMagic)
{
case PEN_MAGIC:
return PEN_GetObject( (PENOBJ *)ptr, count, buffer );
case BRUSH_MAGIC:
return BRUSH_GetObject( (BRUSHOBJ *)ptr, count, buffer );
case BITMAP_MAGIC:
return BMP_GetObject( (BITMAPOBJ *)ptr, count, buffer );
case FONT_MAGIC:
return FONT_GetObject( (FONTOBJ *)ptr, count, buffer );
case PALETTE_MAGIC:
return PALETTE_GetObject( (PALETTEOBJ *)ptr, count, buffer );
}
return 0;
}
/***********************************************************************
* SelectObject (GDI.45)
*/
HANDLE SelectObject( HDC hdc, HANDLE handle )
{
GDIOBJHDR * ptr = NULL;
DC * dc;
#ifdef DEBUG_GDI
printf( "SelectObject: %d %04x\n", hdc, handle );
#endif
if (handle >= FIRST_STOCK_HANDLE)
{
if (handle < FIRST_STOCK_HANDLE + NB_STOCK_OBJECTS)
ptr = StockObjects[handle - FIRST_STOCK_HANDLE];
}
else ptr = (GDIOBJHDR *) GDI_HEAP_ADDR( handle );
if (!ptr) return 0;
dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
switch(ptr->wMagic)
{
case PEN_MAGIC:
return PEN_SelectObject( dc, handle, (PENOBJ *)ptr );
case BRUSH_MAGIC:
return BRUSH_SelectObject( hdc, dc, handle, (BRUSHOBJ *)ptr );
case BITMAP_MAGIC:
return BITMAP_SelectObject( hdc, dc, handle, (BITMAPOBJ *)ptr );
case FONT_MAGIC:
return FONT_SelectObject( dc, handle, (FONTOBJ *)ptr );
case REGION_MAGIC:
return SelectClipRgn( hdc, handle );
}
return 0;
}
/***********************************************************************
* UnrealizeObject (GDI.150)
*/
BOOL UnrealizeObject( HANDLE handle )
{
#ifdef DEBUG_GDI
printf( "UnrealizeObject: %04x\n", handle );
#endif
return TRUE;
}

19
objects/linedda.c Normal file
View File

@ -0,0 +1,19 @@
/*
* LineDDA
*
* Copyright 1993 Bob Amstadt
*/
static char Copyright[] = "Copyright Bob Amstadt, 1993";
#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include "win.h"
/**********************************************************************
* LineDDA (GDI.100)
*/
void LineDDA(short nXStart, short nYStart, short nXEnd, short nYEnd,
FARPROC callback, long lParam)
{
}

191
objects/palette.c Normal file
View File

@ -0,0 +1,191 @@
/*
* GDI palette objects
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdlib.h>
#include <values.h>
#include <X11/Xlib.h>
#include "gdi.h"
extern Display * XT_display;
extern Screen * XT_screen;
#define NB_RESERVED_COLORS 17
static char * ReservedColors[NB_RESERVED_COLORS] =
{
"black",
"gray25",
"gray50",
"gray75",
"white",
"red1",
"red4",
"green1",
"green4",
"blue1",
"blue4",
"cyan1",
"cyan4",
"magenta1",
"magenta4",
"yellow1",
"yellow4"
};
GDIOBJHDR * PALETTE_systemPalette;
static int SysColorPixels[NB_RESERVED_COLORS];
/***********************************************************************
* PALETTE_Init
*/
BOOL PALETTE_Init()
{
int i, size, pixel;
XColor serverColor, exactColor;
HPALETTE hpalette;
LOGPALETTE * palPtr;
size = DefaultVisual(XT_display,DefaultScreen(XT_display))->map_entries;
palPtr = malloc( sizeof(LOGPALETTE) + (size-1)*sizeof(PALETTEENTRY) );
if (!palPtr) return FALSE;
palPtr->palVersion = 0x300;
palPtr->palNumEntries = size;
memset( palPtr->palPalEntry, 0xff, size*sizeof(PALETTEENTRY) );
for (i = 0; i < NB_RESERVED_COLORS; i++)
{
if (XAllocNamedColor( XT_display,
DefaultColormapOfScreen( XT_screen ),
ReservedColors[i],
&serverColor, &exactColor ))
{
pixel = serverColor.pixel;
palPtr->palPalEntry[pixel].peRed = serverColor.red >> 8;
palPtr->palPalEntry[pixel].peGreen = serverColor.green >> 8;
palPtr->palPalEntry[pixel].peBlue = serverColor.blue >> 8;
palPtr->palPalEntry[pixel].peFlags = 0;
}
}
hpalette = CreatePalette( palPtr );
PALETTE_systemPalette = (GDIOBJHDR *) GDI_HEAP_ADDR( hpalette );
free( palPtr );
return TRUE;
}
/***********************************************************************
* CreatePalette (GDI.360)
*/
HPALETTE CreatePalette( LOGPALETTE * palette )
{
PALETTEOBJ * palettePtr;
HPALETTE hpalette;
int size;
size = sizeof(LOGPALETTE) + (palette->palNumEntries - 1) * sizeof(PALETTEENTRY);
hpalette = GDI_AllocObject( sizeof(GDIOBJHDR) + size, PALETTE_MAGIC );
if (!hpalette) return 0;
palettePtr = (PALETTEOBJ *) GDI_HEAP_ADDR( hpalette );
memcpy( &palettePtr->logpalette, palette, size );
return hpalette;
}
/***********************************************************************
* GetPaletteEntries (GDI.363)
*/
WORD GetPaletteEntries( HPALETTE hpalette, WORD start, WORD count,
LPPALETTEENTRY entries )
{
PALETTEOBJ * palPtr;
int numEntries;
palPtr = (PALETTEOBJ *) GDI_GetObjPtr( hpalette, PALETTE_MAGIC );
if (!palPtr) return 0;
numEntries = palPtr->logpalette.palNumEntries;
if (start >= numEntries) return 0;
if (start+count > numEntries) count = numEntries - start;
memcpy( entries, &palPtr->logpalette.palPalEntry[start],
count * sizeof(PALETTEENTRY) );
return count;
}
/***********************************************************************
* SetPaletteEntries (GDI.364)
*/
WORD SetPaletteEntries( HPALETTE hpalette, WORD start, WORD count,
LPPALETTEENTRY entries )
{
PALETTEOBJ * palPtr;
int numEntries;
palPtr = (PALETTEOBJ *) GDI_GetObjPtr( hpalette, PALETTE_MAGIC );
if (!palPtr) return 0;
numEntries = palPtr->logpalette.palNumEntries;
if (start >= numEntries) return 0;
if (start+count > numEntries) count = numEntries - start;
memcpy( &palPtr->logpalette.palPalEntry[start], entries,
count * sizeof(PALETTEENTRY) );
return count;
}
/***********************************************************************
* GetNearestPaletteIndex (GDI.370)
*/
WORD GetNearestPaletteIndex( HPALETTE hpalette, COLORREF color )
{
int i, minDist, dist;
WORD index = 0;
BYTE r, g, b;
PALETTEENTRY * entry;
PALETTEOBJ * palPtr;
palPtr = (PALETTEOBJ *) GDI_GetObjPtr( hpalette, PALETTE_MAGIC );
if (!palPtr) return 0;
r = GetRValue(color);
g = GetGValue(color);
b = GetBValue(color);
entry = palPtr->logpalette.palPalEntry;
for (i = 0, minDist = MAXINT; i < palPtr->logpalette.palNumEntries; i++)
{
if (entry->peFlags != 0xff)
{
dist = (r - entry->peRed) * (r - entry->peRed) +
(g - entry->peGreen) * (g - entry->peGreen) +
(b - entry->peBlue) * (b - entry->peBlue);
if (dist < minDist)
{
minDist = dist;
index = i;
}
}
entry++;
}
#ifdef DEBUG_GDI
printf( "GetNearestPaletteIndex(%x,%06x) : returning %d\n",
hpalette, color, index );
#endif
return index;
}
/***********************************************************************
* PALETTE_GetObject
*/
int PALETTE_GetObject( PALETTEOBJ * palette, int count, LPSTR buffer )
{
if (count > sizeof(WORD)) count = sizeof(WORD);
memcpy( buffer, &palette->logpalette.palNumEntries, count );
return count;
}

93
objects/pen.c Normal file
View File

@ -0,0 +1,93 @@
/*
* GDI pen objects
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "gdi.h"
extern Display * XT_display;
extern Screen * XT_screen;
/***********************************************************************
* CreatePen (GDI.61)
*/
HPEN CreatePen( short style, short width, COLORREF color )
{
LOGPEN logpen = { style, { width, 0 }, color };
#ifdef DEBUG_GDI
printf( "CreatePen: %d %d %06x\n", style, width, color );
#endif
return CreatePenIndirect( &logpen );
}
/***********************************************************************
* CreatePenIndirect (GDI.62)
*/
HPEN CreatePenIndirect( LOGPEN * pen )
{
PENOBJ * penPtr;
HPEN hpen;
if (pen->lopnStyle > PS_INSIDEFRAME) return 0;
hpen = GDI_AllocObject( sizeof(PENOBJ), PEN_MAGIC );
if (!hpen) return 0;
penPtr = (PENOBJ *) GDI_HEAP_ADDR( hpen );
memcpy( &penPtr->logpen, pen, sizeof(LOGPEN) );
return hpen;
}
/***********************************************************************
* PEN_GetObject
*/
int PEN_GetObject( PENOBJ * pen, int count, LPSTR buffer )
{
if (count > sizeof(LOGPEN)) count = sizeof(LOGPEN);
memcpy( buffer, &pen->logpen, count );
return count;
}
/***********************************************************************
* PEN_SelectObject
*/
HPEN PEN_SelectObject( DC * dc, HPEN hpen, PENOBJ * pen )
{
static char dash_dash[] = { 5, 3 }; /* ----- ----- ----- */
static char dash_dot[] = { 2, 2 }; /* -- -- -- -- -- -- */
static char dash_dashdot[] = { 4,3,2,3 }; /* ---- -- ---- -- */
static char dash_dashdotdot[] = { 4,2,2,2,2,2 }; /* ---- -- -- ---- */
HPEN prevHandle = dc->w.hPen;
dc->w.hPen = hpen;
dc->u.x.pen.style = pen->logpen.lopnStyle;
dc->u.x.pen.width = pen->logpen.lopnWidth.x * dc->w.VportExtX
/ dc->w.WndExtX;
if (dc->u.x.pen.width < 0) dc->u.x.pen.width = -dc->u.x.pen.width;
if (dc->u.x.pen.width == 1) dc->u.x.pen.width = 0; /* Faster */
dc->u.x.pen.pixel = GetNearestPaletteIndex( dc->w.hPalette,
pen->logpen.lopnColor );
switch(pen->logpen.lopnStyle)
{
case PS_DASH:
XSetDashes( XT_display, dc->u.x.gc, 0, dash_dash, 2 );
break;
case PS_DOT:
XSetDashes( XT_display, dc->u.x.gc, 0, dash_dot, 2 );
break;
case PS_DASHDOT:
XSetDashes( XT_display, dc->u.x.gc, 0, dash_dashdot, 4 );
break;
case PS_DASHDOTDOT:
XSetDashes( XT_display, dc->u.x.gc, 0, dash_dashdotdot, 6 );
break;
}
return prevHandle;
}

614
objects/region.c Normal file
View File

@ -0,0 +1,614 @@
/*
* GDI region objects
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdlib.h>
#include <stdio.h>
#include "gdi.h"
/* GC used for region operations */
static GC regionGC = 0;
/***********************************************************************
* REGION_Init
*/
BOOL REGION_Init()
{
Pixmap tmpPixmap;
/* CreateGC needs a drawable */
tmpPixmap = XCreatePixmap( XT_display, DefaultRootWindow(XT_display),
1, 1, 1 );
if (tmpPixmap)
{
regionGC = XCreateGC( XT_display, tmpPixmap, 0, NULL );
XFreePixmap( XT_display, tmpPixmap );
if (!regionGC) return FALSE;
XSetForeground( XT_display, regionGC, 1 );
return TRUE;
}
else return FALSE;
}
/***********************************************************************
* REGION_SetRect
*
* Set the bounding box of the region and create the pixmap.
* The hrgn must be valid.
*/
static BOOL REGION_SetRect( HRGN hrgn, LPRECT rect )
{
int width, height;
/* Fill region */
REGION * region = &((RGNOBJ *)GDI_HEAP_ADDR( hrgn ))->region;
width = rect->right - rect->left;
height = rect->bottom - rect->top;
if ((width <= 0) || (height <= 0))
{
region->type = NULLREGION;
region->box.left = 0;
region->box.right = 0;
region->box.top = 0;
region->box.bottom = 0;
region->pixmap = 0;
return TRUE;
}
region->type = SIMPLEREGION;
region->box = *rect;
/* Create pixmap */
region->pixmap = XCreatePixmap( XT_display, DefaultRootWindow(XT_display),
width, height, 1 );
if (!region->pixmap) return FALSE;
/* Fill pixmap */
XSetFunction( XT_display, regionGC, GXclear );
XFillRectangle( XT_display, region->pixmap, regionGC,
0, 0, width, height );
return TRUE;
}
/***********************************************************************
* REGION_DeleteObject
*/
BOOL REGION_DeleteObject( HRGN hrgn, RGNOBJ * obj )
{
if (obj->region.pixmap) XFreePixmap( XT_display, obj->region.pixmap );
return GDI_FreeObject( hrgn );
}
/***********************************************************************
* OffsetRgn (GDI.101)
*/
int OffsetRgn( HRGN hrgn, short x, short y )
{
RGNOBJ * obj = (RGNOBJ *) GDI_GetObjPtr( hrgn, REGION_MAGIC );
if (!obj) return ERROR;
#ifdef DEBUG_REGION
printf( "OffsetRgn: %d %d,%d\n", hrgn, x, y );
#endif
OffsetRect( &obj->region.box, x, y );
return obj->region.type;
}
/***********************************************************************
* GetRgnBox (GDI.134)
*/
int GetRgnBox( HRGN hrgn, LPRECT rect )
{
RGNOBJ * obj = (RGNOBJ *) GDI_GetObjPtr( hrgn, REGION_MAGIC );
if (!obj) return ERROR;
#ifdef DEBUG_REGION
printf( "GetRgnBox: %d\n", hrgn );
#endif
*rect = obj->region.box;
return obj->region.type;
}
/***********************************************************************
* CreateRectRgn (GDI.64)
*/
HRGN CreateRectRgn( short left, short top, short right, short bottom )
{
RECT rect = { left, top, right, bottom };
return CreateRectRgnIndirect( &rect );
}
/***********************************************************************
* CreateRectRgnIndirect (GDI.65)
*/
HRGN CreateRectRgnIndirect( LPRECT rect )
{
RGNOBJ * rgnObj;
HRGN hrgn;
#ifdef DEBUG_REGION
printf( "CreateRectRgnIndirect: %d,%d-%d,%d\n",
rect->left, rect->top, rect->right, rect->bottom );
#endif
/* Create region */
if (!(hrgn = GDI_AllocObject( sizeof(RGNOBJ), REGION_MAGIC ))) return 0;
if (!REGION_SetRect( hrgn, rect ))
{
GDI_FreeObject( hrgn );
return 0;
}
rgnObj = (RGNOBJ *) GDI_HEAP_ADDR( hrgn );
/* Fill pixmap */
if (rgnObj->region.type != NULLREGION)
{
int width = rgnObj->region.box.right - rgnObj->region.box.left;
int height = rgnObj->region.box.bottom - rgnObj->region.box.top;
XSetFunction( XT_display, regionGC, GXcopy );
XFillRectangle( XT_display, rgnObj->region.pixmap, regionGC,
0, 0, width, height );
}
return hrgn;
}
/***********************************************************************
* CreateRoundRectRgn (GDI.444)
*/
HRGN CreateRoundRectRgn( short left, short top, short right, short bottom,
short ellipse_width, short ellipse_height )
{
RECT rect = { left, top, right, bottom };
RGNOBJ * rgnObj;
HRGN hrgn;
#ifdef DEBUG_REGION
printf( "CreateRoundRectRgn: %d,%d-%d,%d %dx%d\n",
left, top, right, bottom, ellipse_width, ellipse_height );
#endif
/* Create region */
if (!(hrgn = GDI_AllocObject( sizeof(RGNOBJ), REGION_MAGIC ))) return 0;
if (!REGION_SetRect( hrgn, &rect ))
{
GDI_FreeObject( hrgn );
return 0;
}
rgnObj = (RGNOBJ *) GDI_HEAP_ADDR( hrgn );
/* Fill pixmap */
if (rgnObj->region.type != NULLREGION)
{
int width = rgnObj->region.box.right - rgnObj->region.box.left;
int height = rgnObj->region.box.bottom - rgnObj->region.box.top;
XSetFunction( XT_display, regionGC, GXcopy );
XFillRectangle( XT_display, rgnObj->region.pixmap, regionGC,
0, ellipse_height / 2,
width, height - ellipse_height );
XFillRectangle( XT_display, rgnObj->region.pixmap, regionGC,
ellipse_width / 2, 0,
width - ellipse_width, height );
XFillArc( XT_display, rgnObj->region.pixmap, regionGC,
0, 0,
ellipse_width, ellipse_height, 0, 360*64 );
XFillArc( XT_display, rgnObj->region.pixmap, regionGC,
width - ellipse_width, 0,
ellipse_width, ellipse_height, 0, 360*64 );
XFillArc( XT_display, rgnObj->region.pixmap, regionGC,
0, height - ellipse_height,
ellipse_width, ellipse_height, 0, 360*64 );
XFillArc( XT_display, rgnObj->region.pixmap, regionGC,
width - ellipse_width, height - ellipse_height,
ellipse_width, ellipse_height, 0, 360*64 );
}
return hrgn;
}
/***********************************************************************
* SetRectRgn (GDI.172)
*/
void SetRectRgn( HRGN hrgn, short left, short top, short right, short bottom )
{
RECT rect = { left, top, right, bottom };
RGNOBJ * rgnObj;
#ifdef DEBUG_REGION
printf( "SetRectRgn: %d %d,%d-%d,%d\n", hrgn, left, top, right, bottom );
#endif
/* Free previous pixmap */
if (!(rgnObj = (RGNOBJ *) GDI_GetObjPtr( hrgn, REGION_MAGIC ))) return;
if (rgnObj->region.pixmap)
XFreePixmap( XT_display, rgnObj->region.pixmap );
if (!REGION_SetRect( hrgn, &rect )) return;
/* Fill pixmap */
if (rgnObj->region.type != NULLREGION)
{
int width = rgnObj->region.box.right - rgnObj->region.box.left;
int height = rgnObj->region.box.bottom - rgnObj->region.box.top;
XSetFunction( XT_display, regionGC, GXcopy );
XFillRectangle( XT_display, rgnObj->region.pixmap, regionGC,
0, 0, width, height );
}
}
/***********************************************************************
* CreateEllipticRgn (GDI.54)
*/
HRGN CreateEllipticRgn( short left, short top, short right, short bottom )
{
RECT rect = { left, top, right, bottom };
return CreateEllipticRgnIndirect( &rect );
}
/***********************************************************************
* CreateEllipticRgnIndirect (GDI.55)
*/
HRGN CreateEllipticRgnIndirect( LPRECT rect )
{
RGNOBJ * rgnObj;
HRGN hrgn;
#ifdef DEBUG_REGION
printf( "CreateEllipticRgnIndirect: %d,%d-%d,%d\n",
rect->left, rect->top, rect->right, rect->bottom );
#endif
/* Create region */
if (!(hrgn = GDI_AllocObject( sizeof(RGNOBJ), REGION_MAGIC ))) return 0;
if (!REGION_SetRect( hrgn, rect ))
{
GDI_FreeObject( hrgn );
return 0;
}
rgnObj = (RGNOBJ *) GDI_HEAP_ADDR( hrgn );
/* Fill pixmap */
if (rgnObj->region.type != NULLREGION)
{
int width = rgnObj->region.box.right - rgnObj->region.box.left;
int height = rgnObj->region.box.bottom - rgnObj->region.box.top;
XSetFunction( XT_display, regionGC, GXcopy );
XFillArc( XT_display, rgnObj->region.pixmap, regionGC,
0, 0, width, height, 0, 360*64 );
}
return hrgn;
}
/***********************************************************************
* CreatePolygonRgn (GDI.63)
*/
HRGN CreatePolygonRgn( POINT * points, short count, short mode )
{
return CreatePolyPolygonRgn( points, &count, 1, mode );
}
/***********************************************************************
* CreatePolyPolygonRgn (GDI.451)
*/
HRGN CreatePolyPolygonRgn( POINT * points, short * count,
short nbpolygons, short mode )
{
RGNOBJ * rgnObj;
HRGN hrgn;
RECT box;
int i, j, totalPoints;
POINT * pt;
XPoint * xpoints;
if (!nbpolygons) return 0;
#ifdef DEBUG_REGION
printf( "CreatePolyPolygonRgn: %d polygons\n", nbpolygons );
#endif
/* Find bounding box */
box.top = box.left = 32767;
box.right = box.bottom = 0;
for (i = totalPoints = 0, pt = points; i < nbpolygons; i++)
{
totalPoints += count[i];
for (j = 0; j < count[i]; j++, pt++)
{
if (pt->x < box.left) box.left = pt->x;
if (pt->x > box.right) box.right = pt->x;
if (pt->y < box.top) box.top = pt->y;
if (pt->y > box.bottom) box.bottom = pt->y;
}
}
if (!totalPoints) return 0;
/* Build points array */
xpoints = (XPoint *) malloc( sizeof(XPoint) * totalPoints );
if (!xpoints) return 0;
for (i = 0, pt = points; i < totalPoints; i++, pt++)
{
xpoints[i].x = pt->x - box.left;
xpoints[i].y = pt->y - box.top;
}
/* Create region */
if (!(hrgn = GDI_AllocObject( sizeof(RGNOBJ), REGION_MAGIC )) ||
!REGION_SetRect( hrgn, &box ))
{
if (hrgn) GDI_FreeObject( hrgn );
free( xpoints );
return 0;
}
rgnObj = (RGNOBJ *) GDI_HEAP_ADDR( hrgn );
/* Fill pixmap */
if (rgnObj->region.type != NULLREGION)
{
XSetFunction( XT_display, regionGC, GXcopy );
if (mode == WINDING) XSetFillRule( XT_display, regionGC, WindingRule );
else XSetFillRule( XT_display, regionGC, EvenOddRule );
for (i = j = 0; i < nbpolygons; i++)
{
XFillPolygon( XT_display, rgnObj->region.pixmap, regionGC,
&xpoints[j], count[i], Complex, CoordModeOrigin );
j += count[i];
}
}
free( xpoints );
return hrgn;
}
/***********************************************************************
* PtInRegion (GDI.161)
*/
BOOL PtInRegion( HRGN hrgn, short x, short y )
{
XImage * image;
BOOL res;
RGNOBJ * obj;
POINT pt = { x, y };
if (!(obj = (RGNOBJ *) GDI_GetObjPtr( hrgn, REGION_MAGIC ))) return FALSE;
if (!PtInRect( &obj->region.box, pt )) return FALSE;
image = XGetImage( XT_display, obj->region.pixmap,
x - obj->region.box.left, y - obj->region.box.top,
1, 1, AllPlanes, ZPixmap );
if (!image) return FALSE;
res = (XGetPixel( image, 0, 0 ) != 0);
XDestroyImage( image );
return res;
}
/***********************************************************************
* RectInRegion (GDI.181)
*/
BOOL RectInRegion( HRGN hrgn, LPRECT rect )
{
XImage * image;
RGNOBJ * obj;
RECT intersect;
int x, y;
if (!(obj = (RGNOBJ *) GDI_GetObjPtr( hrgn, REGION_MAGIC ))) return FALSE;
if (!IntersectRect( &intersect, &obj->region.box, rect )) return FALSE;
image = XGetImage( XT_display, obj->region.pixmap,
intersect.left - obj->region.box.left,
intersect.top - obj->region.box.top,
intersect.right - intersect.left,
intersect.bottom - intersect.top,
AllPlanes, ZPixmap );
if (!image) return FALSE;
for (y = 0; y < image->height; y++)
for (x = 0; x < image->width; x++)
if (XGetPixel( image, x, y ) != 0)
{
XDestroyImage( image );
return TRUE;
}
XDestroyImage( image );
return FALSE;
}
/***********************************************************************
* EqualRgn (GDI.72)
*/
BOOL EqualRgn( HRGN rgn1, HRGN rgn2 )
{
RGNOBJ *obj1, *obj2;
XImage *image1, *image2;
int width, height, x, y;
/* Compare bounding boxes */
if (!(obj1 = (RGNOBJ *) GDI_GetObjPtr( rgn1, REGION_MAGIC ))) return FALSE;
if (!(obj2 = (RGNOBJ *) GDI_GetObjPtr( rgn2, REGION_MAGIC ))) return FALSE;
if (obj1->region.type == NULLREGION)
return (obj2->region.type == NULLREGION);
else if (obj2->region.type == NULLREGION) return FALSE;
if (!EqualRect( &obj1->region.box, &obj2->region.box )) return FALSE;
/* Get pixmap contents */
width = obj1->region.box.right - obj1->region.box.left;
height = obj1->region.box.bottom - obj1->region.box.top;
image1 = XGetImage( XT_display, obj1->region.pixmap,
0, 0, width, height, AllPlanes, ZPixmap );
if (!image1) return FALSE;
image2 = XGetImage( XT_display, obj2->region.pixmap,
0, 0, width, height, AllPlanes, ZPixmap );
if (!image2)
{
XDestroyImage( image1 );
return FALSE;
}
/* Compare pixmaps */
for (y = 0; y < height; y++)
for (x = 0; x < width; x++)
if (XGetPixel( image1, x, y ) != XGetPixel( image2, x, y))
{
XDestroyImage( image1 );
XDestroyImage( image2 );
return FALSE;
}
XDestroyImage( image1 );
XDestroyImage( image2 );
return TRUE;
}
/***********************************************************************
* REGION_CopyIntersection
*
* Copy to dest->pixmap the area of src->pixmap delimited by
* the intersection of dest and src regions, using the current GC function.
*/
void REGION_CopyIntersection( REGION * dest, REGION * src )
{
RECT inter;
if (!IntersectRect( &inter, &dest->box, &src->box )) return;
XCopyArea( XT_display, src->pixmap, dest->pixmap, regionGC,
inter.left - src->box.left, inter.top - src->box.top,
inter.right - inter.left, inter.bottom - inter.top,
inter.left - dest->box.left, inter.top - dest->box.top );
}
/***********************************************************************
* CombineRgn (GDI.451)
*/
int CombineRgn( HRGN hDest, HRGN hSrc1, HRGN hSrc2, short mode )
{
RGNOBJ *destObj, *src1Obj, *src2Obj;
REGION * region;
int width, height;
BOOL res;
#ifdef DEBUG_REGION
printf( "CombineRgn: %d %d %d %d\n", hDest, hSrc1, hSrc2, mode );
#endif
if (!(destObj = (RGNOBJ *) GDI_GetObjPtr( hDest, REGION_MAGIC )))
return ERROR;
if (!(src1Obj = (RGNOBJ *) GDI_GetObjPtr( hSrc1, REGION_MAGIC )))
return ERROR;
if (mode != RGN_COPY)
if (!(src2Obj = (RGNOBJ *) GDI_GetObjPtr( hSrc2, REGION_MAGIC )))
return ERROR;
region = &destObj->region;
switch(mode)
{
case RGN_AND:
res = IntersectRect( &region->box, &src1Obj->region.box,
&src2Obj->region.box );
break;
case RGN_OR:
case RGN_XOR:
res = UnionRect( &region->box, &src1Obj->region.box,
&src2Obj->region.box );
break;
case RGN_DIFF:
res = SubtractRect( &region->box, &src1Obj->region.box,
&src2Obj->region.box );
break;
case RGN_COPY:
region->box = src1Obj->region.box;
region->type = src1Obj->region.type;
res = (region->type != NULLREGION);
break;
default:
return ERROR;
}
if (region->pixmap) XFreePixmap( XT_display, region->pixmap );
if (!res)
{
region->type = NULLREGION;
region->pixmap = 0;
return NULLREGION;
}
width = region->box.right - region->box.left;
height = region->box.bottom - region->box.top;
region->pixmap = XCreatePixmap( XT_display, DefaultRootWindow(XT_display),
width, height, 1 );
switch(mode)
{
case RGN_AND:
XSetFunction( XT_display, regionGC, GXcopy );
REGION_CopyIntersection( region, &src1Obj->region );
XSetFunction( XT_display, regionGC, GXand );
REGION_CopyIntersection( region, &src2Obj->region );
return COMPLEXREGION;
case RGN_OR:
case RGN_XOR:
XSetFunction( XT_display, regionGC, GXclear );
XFillRectangle( XT_display, region->pixmap, regionGC,
0, 0, width, height );
XSetFunction( XT_display, regionGC, (mode == RGN_OR) ? GXor : GXxor);
REGION_CopyIntersection( region, &src1Obj->region );
REGION_CopyIntersection( region, &src2Obj->region );
return COMPLEXREGION;
case RGN_DIFF:
XSetFunction( XT_display, regionGC, GXclear );
XFillRectangle( XT_display, region->pixmap, regionGC,
0, 0, width, height );
XSetFunction( XT_display, regionGC, GXcopy );
REGION_CopyIntersection( region, &src1Obj->region );
XSetFunction( XT_display, regionGC, GXandInverted );
REGION_CopyIntersection( region, &src2Obj->region );
return COMPLEXREGION;
case RGN_COPY:
XSetFunction( XT_display, regionGC, GXcopy );
XCopyArea( XT_display, src1Obj->region.pixmap, region->pixmap,
regionGC, 0, 0, width, height, 0, 0 );
return region->type;
}
return ERROR;
}

168
objects/text.c Normal file
View File

@ -0,0 +1,168 @@
/*
* text functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Core.h>
#include <X11/Shell.h>
#include <X11/Xatom.h>
#include "message.h"
#include "callback.h"
#include "win.h"
#include "gdi.h"
/***********************************************************************
* DrawText (USER.85)
*/
int DrawText( HDC hdc, LPSTR str, int count, LPRECT rect, WORD flags )
{
int x = rect->left, y = rect->top;
if (flags & DT_CENTER) x = (rect->left + rect->right) / 2;
if (flags & DT_VCENTER) y = (rect->top + rect->bottom) / 2;
if (count == -1) count = strlen(str);
if (!TextOut( hdc, x, y, str, count )) return 0;
return 1;
}
/***********************************************************************
* TextOut (GDI.33)
*/
BOOL TextOut( HDC hdc, short x, short y, LPSTR str, short count )
{
int dir, ascent, descent, i;
XCharStruct info;
XFontStruct *font;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return FALSE;
if (!DC_SetupGCForText( dc )) return TRUE;
font = dc->u.x.font.fstruct;
if (dc->w.textAlign & TA_UPDATECP)
{
x = dc->w.CursPosX;
y = dc->w.CursPosY;
}
#ifdef DEBUG_TEXT
printf( "TextOut: %d,%d '%s'\n", x, y, str );
#endif
x = XLPTODP( dc, x );
y = YLPTODP( dc, y );
XTextExtents( font, str, count, &dir, &ascent, &descent, &info );
info.width += count*dc->w.charExtra + dc->w.breakExtra*dc->w.breakCount;
/* Compute starting position */
switch( dc->w.textAlign & (TA_LEFT | TA_RIGHT | TA_CENTER) )
{
case TA_LEFT:
if (dc->w.textAlign & TA_UPDATECP)
dc->w.CursPosX = XDPTOLP( dc, x + info.width );
break;
case TA_RIGHT:
x -= info.width;
if (dc->w.textAlign & TA_UPDATECP) dc->w.CursPosX = XDPTOLP( dc, x );
break;
case TA_CENTER:
x -= info.width / 2;
break;
}
switch( dc->w.textAlign & (TA_TOP | TA_BOTTOM | TA_BASELINE) )
{
case TA_TOP:
y += font->ascent;
break;
case TA_BOTTOM:
y -= font->descent;
break;
case TA_BASELINE:
break;
}
/* Draw text */
if (!dc->w.charExtra && !dc->w.breakExtra)
{
if (dc->w.backgroundMode == TRANSPARENT)
XDrawString( XT_display, dc->u.x.drawable, dc->u.x.gc,
x, y, str, count );
else
XDrawImageString( XT_display, dc->u.x.drawable, dc->u.x.gc,
x, y, str, count );
}
else
{
char * p = str;
int xchar = x;
for (i = 0; i < count; i++, p++)
{
XCharStruct * charStr;
unsigned char ch = *p;
int extraWidth;
if ((ch < font->min_char_or_byte2)||(ch > font->max_char_or_byte2))
ch = font->default_char;
if (!font->per_char) charStr = &font->min_bounds;
else charStr = font->per_char + ch - font->min_char_or_byte2;
extraWidth = dc->w.charExtra;
if (ch == dc->u.x.font.metrics.tmBreakChar)
extraWidth += dc->w.breakExtra;
if (dc->w.backgroundMode == TRANSPARENT)
XDrawString( XT_display, dc->u.x.drawable, dc->u.x.gc,
xchar, y, p, 1 );
else
{
XDrawImageString( XT_display, dc->u.x.drawable, dc->u.x.gc,
xchar, y, p, 1 );
XSetForeground( XT_display, dc->u.x.gc, dc->w.backgroundPixel);
XFillRectangle( XT_display, dc->u.x.drawable, dc->u.x.gc,
xchar + charStr->width, y - font->ascent,
extraWidth, font->ascent + font->descent );
XSetForeground( XT_display, dc->u.x.gc, dc->w.textPixel );
}
xchar += charStr->width + extraWidth;
}
}
/* Draw underline and strike-out if needed */
if (dc->u.x.font.metrics.tmUnderlined)
{
long linePos, lineWidth;
if (!XGetFontProperty( font, XA_UNDERLINE_POSITION, &linePos ))
linePos = font->descent-1;
if (!XGetFontProperty( font, XA_UNDERLINE_THICKNESS, &lineWidth ))
lineWidth = 0;
else if (lineWidth == 1) lineWidth = 0;
XSetLineAttributes( XT_display, dc->u.x.gc, lineWidth,
LineSolid, CapRound, JoinBevel );
XDrawLine( XT_display, dc->u.x.drawable, dc->u.x.gc,
x, y + linePos, x + info.width, y + linePos );
}
if (dc->u.x.font.metrics.tmStruckOut)
{
long lineAscent, lineDescent;
if (!XGetFontProperty( font, XA_STRIKEOUT_ASCENT, &lineAscent ))
lineAscent = font->ascent / 3;
if (!XGetFontProperty( font, XA_STRIKEOUT_DESCENT, &lineDescent ))
lineDescent = -lineAscent;
XSetLineAttributes( XT_display, dc->u.x.gc, lineAscent + lineDescent,
LineSolid, CapRound, JoinBevel );
XDrawLine( XT_display, dc->u.x.drawable, dc->u.x.gc,
x, y - lineAscent, x + info.width, y - lineAscent );
}
return TRUE;
}

90
signal-diffs Normal file
View File

@ -0,0 +1,90 @@
diff -c -r linux.99pl12/linux//kernel/signal.c linux//kernel/signal.c
*** linux.99pl12/linux//kernel/signal.c Sat Aug 28 00:24:01 1993
--- linux//kernel/signal.c Fri Aug 27 22:45:41 1993
***************
*** 195,201 ****
COPY(eip); COPY(eflags);
COPY(ecx); COPY(edx);
COPY(ebx);
! COPY(esp); COPY(ebp);
COPY(edi); COPY(esi);
COPY(cs); COPY(ss);
COPY(ds); COPY(es);
--- 195,202 ----
COPY(eip); COPY(eflags);
COPY(ecx); COPY(edx);
COPY(ebx);
! regs->esp = context.esp_at_signal; /* Can be different with Wine */
! COPY(ebp);
COPY(edi); COPY(esi);
COPY(cs); COPY(ss);
COPY(ds); COPY(es);
***************
*** 353,360 ****
frame = (unsigned long *) regs->esp;
signr = 1;
sa = current->sigaction;
! if (regs->ss != USER_DS)
! printk("Warning: signal handler with nonstandard stack segment\n");
for (mask = 1 ; mask ; sa++,signr++,mask += mask) {
if (mask > handler_signal)
break;
--- 354,360 ----
frame = (unsigned long *) regs->esp;
signr = 1;
sa = current->sigaction;
!
for (mask = 1 ; mask ; sa++,signr++,mask += mask) {
if (mask > handler_signal)
break;
***************
*** 365,370 ****
--- 365,381 ----
sa->sa_handler = NULL;
/* force a supervisor-mode page-in of the signal handler to reduce races */
__asm__("testb $0,%%fs:%0": :"m" (*(char *) sa_handler));
+
+ /* If ss != USER_DS, we cannot rely upon the ss:esp as a */
+ /* stack. We will instead use USER_DS:sa->sa_restorer */
+ if (regs->ss != USER_DS) {
+ frame = (unsigned long *) sa->sa_restorer;
+ if(frame == NULL) {
+ printk("No signal handler stack available\n");
+ do_exit(signr);
+ };
+ };
+
setup_frame(&frame,eip,regs,signr,sa_handler,oldmask);
eip = sa_handler; regs->cs = USER_CS;
current->blocked |= sa->sa_mask;
***************
*** 371,376 ****
--- 382,392 ----
oldmask |= sa->sa_mask;
}
regs->esp = (unsigned long) frame;
+ /* When running the Wine program, the segment registers may be holding
+ unusual values */
+ regs->ss = USER_DS; /* Make sure that this is correct */
+ regs->ds = USER_DS; /* And the same here */
+ regs->es = USER_DS; /* And here again */
regs->eip = eip; /* "return" to the first handler */
return 1;
}
diff -c -r linux.99pl12/linux//kernel/traps.c linux//kernel/traps.c
*** linux.99pl12/linux//kernel/traps.c Thu Aug 19 00:34:24 1993
--- linux//kernel/traps.c Fri Aug 27 09:11:01 1993
***************
*** 66,71 ****
--- 66,76 ----
if ((regs->eflags & VM_MASK) || ((0xffff & regs->cs) == USER_CS))
return;
+
+ /* See if we are using the LDT. If so, pass along the signal. */
+ if((7 & regs->cs) == 7 && current->ldt && (regs->cs >> 3) < 512)
+ return;
+
printk("%s: %04x\n", str, err & 0xffff);
printk("EIP: %04x:%p\nEFLAGS: %p\n", 0xffff & regs->cs,regs->eip,regs->eflags);
printk("eax: %08x ebx: %08x ecx: %08x edx: %08x\n",

BIN
test/hw.exe Executable file

Binary file not shown.

BIN
test/menutest.exe Executable file

Binary file not shown.

BIN
test/winetest2.exe Executable file

Binary file not shown.

17
tools/Makefile Normal file
View File

@ -0,0 +1,17 @@
build: build.c
cc -O2 -o build build.c
clean:
rm -f *.o *~
depend:
$(CC) $(CFLAGS) -M *.c > .depend
dummy:
#
# Dependency lists
#
ifeq (.depend,$(wildcard .depend))
include .depend
endif

View File

@ -610,6 +610,8 @@ main(int argc, char **argv)
if (!odp->valid) if (!odp->valid)
{ {
fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i); fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i);
fprintf(fp, "\tandl\t$0x0000ffff,%%esp\n");
fprintf(fp, "\tandl\t$0x0000ffff,%%ebp\n");
fprintf(fp, "\tmovl\t$%d,%%eax\n", i); fprintf(fp, "\tmovl\t$%d,%%eax\n", i);
fprintf(fp, "\tpushw\t$0\n"); fprintf(fp, "\tpushw\t$0\n");
fprintf(fp, "\tjmp\t_%s_Dispatch\n\n", UpperDLLName); fprintf(fp, "\tjmp\t_%s_Dispatch\n\n", UpperDLLName);
@ -652,6 +654,8 @@ main(int argc, char **argv)
case FUNCTYPE_REG: case FUNCTYPE_REG:
fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i); fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i);
fprintf(fp, "\tandl\t$0x0000ffff,%%esp\n");
fprintf(fp, "\tandl\t$0x0000ffff,%%ebp\n");
fprintf(fp, "\tpushw\t%%ax\n"); fprintf(fp, "\tpushw\t%%ax\n");
fprintf(fp, "\tpushw\t%%cx\n"); fprintf(fp, "\tpushw\t%%cx\n");
fprintf(fp, "\tpushw\t%%dx\n"); fprintf(fp, "\tpushw\t%%dx\n");
@ -673,6 +677,8 @@ main(int argc, char **argv)
case FUNCTYPE_PASCAL: case FUNCTYPE_PASCAL:
fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i); fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i);
fprintf(fp, "\tandl\t$0x0000ffff,%%esp\n");
fprintf(fp, "\tandl\t$0x0000ffff,%%ebp\n");
fprintf(fp, "\tmovl\t$%d,%%eax\n", i); fprintf(fp, "\tmovl\t$%d,%%eax\n", i);
fprintf(fp, "\tpushw\t$%d\n", fdp->arg_16_size); fprintf(fp, "\tpushw\t$%d\n", fdp->arg_16_size);
fprintf(fp, "\tjmp\t_%s_Dispatch\n\n", UpperDLLName); fprintf(fp, "\tjmp\t_%s_Dispatch\n\n", UpperDLLName);
@ -681,6 +687,8 @@ main(int argc, char **argv)
case FUNCTYPE_C: case FUNCTYPE_C:
default: default:
fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i); fprintf(fp, "_%s_Ordinal_%d:\n", UpperDLLName, i);
fprintf(fp, "\tandl\t$0x0000ffff,%%esp\n");
fprintf(fp, "\tandl\t$0x0000ffff,%%ebp\n");
fprintf(fp, "\tmovl\t$%d,%%eax\n", i); fprintf(fp, "\tmovl\t$%d,%%eax\n", i);
fprintf(fp, "\tpushw\t$0\n"); fprintf(fp, "\tpushw\t$0\n");
fprintf(fp, "\tjmp\t_%s_Dispatch\n\n", UpperDLLName); fprintf(fp, "\tjmp\t_%s_Dispatch\n\n", UpperDLLName);

26
user.c
View File

@ -1,26 +0,0 @@
static char RCSId[] = "$Id: user.c,v 1.2 1993/07/04 04:04:21 root Exp root $";
static char Copyright[] = "Copyright Robert J. Amstadt, 1993";
#include <stdio.h>
#include <stdlib.h>
#include "prototypes.h"
#define DEFAULT_MSG_QUEUE_SIZE 8
/**********************************************************************
* USER_InitApp
*
* Load necessary resources?
*/
int
USER_InitApp(int hInstance)
{
/* Initialize built-in window classes */
WIDGETS_Init();
/* Create task message queue */
if (!SetMessageQueue( DEFAULT_MSG_QUEUE_SIZE )) return 0;
return 1;
}

View File

@ -1,43 +0,0 @@
# $Id: user.spec,v 1.3 1993/07/04 04:04:21 root Exp root $
#
name user
id 2
length 540
1 pascal MessageBox(word ptr ptr word) MessageBox(1 2 3 4)
5 pascal InitApp(word) USER_InitApp(1)
6 pascal PostQuitMessage(word) PostQuitMessage(1)
33 pascal GetClientRect(word ptr) GetClientRect(1 2)
39 pascal BeginPaint(word ptr) BeginPaint(1 2)
40 pascal EndPaint(word ptr) EndPaint(1 2)
41 pascal CreateWindow(ptr ptr long word word word word word word word ptr)
CreateWindow(1 2 3 4 5 6 7 8 9 10 11)
42 pascal ShowWindow(word word) ShowWindow(1 2)
53 pascal DestroyWindow(word) DestroyWindow(1)
57 pascal RegisterClass(ptr) RegisterClass(1)
66 pascal GetDC(word) GetDC(1)
85 pascal DrawText(word ptr s_word ptr word) DrawText(1 2 3 4 5)
104 pascal MessageBeep(word) MessageBeep(1)
107 pascal DefWindowProc(word word word long) DefWindowProc(1 2 3 4)
108 pascal GetMessage(ptr word word word) GetMessage(1 2 3 4)
109 pascal PeekMessage(ptr word word word word) PeekMessage(1 2 3 4 5)
110 pascal PostMessage(word word word word) PostMessage(1 2 3 4)
111 pascal SendMessage(word word word word) SendMessage(1 2 3 4)
113 pascal TranslateMessage(ptr) TranslateMessage(1)
114 pascal DispatchMessage(ptr) DispatchMessage(1)
119 pascal GetMessagePos() GetMessagePos()
120 pascal GetMessageTime() GetMessageTime()
124 pascal UpdateWindow(word) UpdateWindow(1)
151 pascal CreateMenu() CreateMenu()
157 pascal GetMenu(word) GetMenu(1)
158 pascal SetMenu(word word) SetMenu(1 2)
173 pascal LoadCursor(word ptr) RSC_LoadCursor(1 2)
174 pascal LoadIcon(word ptr) RSC_LoadIcon(1 2)
175 pascal LoadBitmap(word ptr) RSC_LoadBitmap(1 2)
176 pascal LoadString(word word ptr s_word) RSC_LoadString(1 2 3 4)
266 pascal SetMessageQueue(word) SetMessageQueue(1)
288 pascal GetMessageExtraInfo() GetMessageExtraInfo()
334 pascal GetQueueStatus(word) GetQueueStatus(1)
335 pascal GetInputState() GetInputState()
403 pascal UnregisterClass(ptr word) UnregisterClass(1 2)
411 pascal AppendMenu(word word word ptr) AppendMenu(1 2 3 4)

19
windows/Makefile Normal file
View File

@ -0,0 +1,19 @@
CFLAGS=$(COPTS) $(DEBUGOPTS) -I$(INCLUDE_DIR)
OBJS=class.o dc.o dce.o event.o message.o win.o timer.o graphics.o \
clipping.o mapping.o painting.o keyboard.o
default: windows.o
windows.o: $(OBJS)
$(LD) -r -o windows.o $(OBJS)
clean:
rm -f *.o *~ *.s dll_* *.a
depend:
$(CC) $(CFLAGS) -M *.c > .depend
ifeq (.depend,$(wildcard .depend))
include .depend
endif

View File

@ -7,6 +7,8 @@
static char Copyright[] = "Copyright Alexandre Julliard, 1993"; static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "class.h" #include "class.h"
#include "user.h"
#include "win.h"
static HCLASS firstClass = 0; static HCLASS firstClass = 0;
@ -16,20 +18,15 @@ static HCLASS firstClass = 0;
* CLASS_FindClassByName * CLASS_FindClassByName
* *
* Return a handle and a pointer to the class. * Return a handle and a pointer to the class.
* The caller must GlobalUnlock the pointer.
*/ */
HCLASS CLASS_FindClassByName( char * name, CLASS **ptr ) HCLASS CLASS_FindClassByName( char * name, CLASS **ptr )
{ {
HCLASS class, next; HCLASS class = firstClass;
class = firstClass;
while(class) while(class)
{ {
*ptr = (CLASS *) GlobalLock(class); *ptr = (CLASS *) USER_HEAP_ADDR(class);
if (!strcmp( (*ptr)->wc.lpszClassName, name )) return class; if (!strcmp( (*ptr)->wc.lpszClassName, name )) return class;
next = (*ptr)->hNext; class = (*ptr)->hNext;
GlobalUnlock(class);
class = next;
} }
return 0; return 0;
} }
@ -38,19 +35,14 @@ HCLASS CLASS_FindClassByName( char * name, CLASS **ptr )
* CLASS_FindClassPtr * CLASS_FindClassPtr
* *
* Return a pointer to the CLASS structure corresponding to a HCLASS. * Return a pointer to the CLASS structure corresponding to a HCLASS.
* The caller must GlobalUnlock the pointer.
*/ */
CLASS * CLASS_FindClassPtr( HCLASS hclass ) CLASS * CLASS_FindClassPtr( HCLASS hclass )
{ {
CLASS * ptr; CLASS * ptr;
if (!hclass) return NULL; if (!hclass) return NULL;
ptr = (CLASS *) GlobalLock( hclass ); ptr = (CLASS *) USER_HEAP_ADDR( hclass );
if (ptr->wMagic != CLASS_MAGIC) if (ptr->wMagic != CLASS_MAGIC) return NULL;
{
GlobalUnlock( hclass );
return NULL;
}
return ptr; return ptr;
} }
@ -62,16 +54,15 @@ ATOM RegisterClass( LPWNDCLASS class )
{ {
CLASS * newClass; CLASS * newClass;
HCLASS handle; HCLASS handle;
int i;
#ifdef DEBUG_CLASS #ifdef DEBUG_CLASS
printf( "RegisterClass: wndproc=%08x hinst=%d name='%s'\n", printf( "RegisterClass: wndproc=%08x hinst=%d name='%s'\n",
class->lpfnWndProc, class->hInstance, class->lpszClassName ); class->lpfnWndProc, class->hInstance, class->lpszClassName );
#endif #endif
handle = GlobalAlloc( GMEM_MOVEABLE, sizeof(CLASS)+class->cbClsExtra ); handle = USER_HEAP_ALLOC( GMEM_MOVEABLE, sizeof(CLASS)+class->cbClsExtra );
if (!handle) return 0; if (!handle) return 0;
newClass = (CLASS *) GlobalLock( handle ); newClass = (CLASS *) USER_HEAP_ADDR( handle );
newClass->hNext = firstClass; newClass->hNext = firstClass;
newClass->wMagic = CLASS_MAGIC; newClass->wMagic = CLASS_MAGIC;
newClass->atomName = handle; /* Should be an atom */ newClass->atomName = handle; /* Should be an atom */
@ -79,8 +70,6 @@ ATOM RegisterClass( LPWNDCLASS class )
newClass->cWindows = 0; newClass->cWindows = 0;
newClass->wc = *class; newClass->wc = *class;
newClass->wc.lpszMenuName = 0;
/* Class name should also be set to zero. For now we need the /* Class name should also be set to zero. For now we need the
* name because we don't have atoms. * name because we don't have atoms.
*/ */
@ -88,8 +77,6 @@ ATOM RegisterClass( LPWNDCLASS class )
strcpy( newClass->wc.lpszClassName, class->lpszClassName ); strcpy( newClass->wc.lpszClassName, class->lpszClassName );
if (class->cbClsExtra) memset( newClass->wExtra, 0, class->cbClsExtra ); if (class->cbClsExtra) memset( newClass->wExtra, 0, class->cbClsExtra );
GlobalUnlock( handle );
firstClass = handle; firstClass = handle;
return handle; /* Should be an atom */ return handle; /* Should be an atom */
@ -108,23 +95,16 @@ BOOL UnregisterClass( LPSTR className, HANDLE instance )
class = CLASS_FindClassByName( className, &classPtr ); class = CLASS_FindClassByName( className, &classPtr );
if (!class) return FALSE; if (!class) return FALSE;
if ((classPtr->wc.hInstance != instance) || (classPtr->cWindows > 0)) if ((classPtr->wc.hInstance != instance) || (classPtr->cWindows > 0))
{
GlobalUnlock( class );
return FALSE; return FALSE;
}
/* Remove the class from the linked list */ /* Remove the class from the linked list */
if (firstClass == class) firstClass = classPtr->hNext; if (firstClass == class) firstClass = classPtr->hNext;
else else
{ {
prevClass = firstClass; for (prevClass = firstClass; prevClass; prevClass=prevClassPtr->hNext)
while (prevClass)
{ {
prevClassPtr = (CLASS *) GlobalLock(prevClass); prevClassPtr = (CLASS *) USER_HEAP_ADDR(prevClass);
next == prevClassPtr->hNext; if (prevClassPtr->hNext == class) break;
if (next == class) break;
GlobalUnlock(prevClass);
prevClass = next;
} }
if (!prevClass) if (!prevClass)
{ {
@ -132,10 +112,76 @@ BOOL UnregisterClass( LPSTR className, HANDLE instance )
return FALSE; return FALSE;
} }
prevClassPtr->hNext = classPtr->hNext; prevClassPtr->hNext = classPtr->hNext;
GlobalUnlock( prevClass );
} }
GlobalUnlock( class ); USER_HEAP_FREE( class );
GlobalFree( class );
return TRUE; return TRUE;
} }
/***********************************************************************
* GetClassWord (USER.129)
*/
WORD GetClassWord( HWND hwnd, short offset )
{
return (WORD)GetClassLong( hwnd, offset );
}
/***********************************************************************
* SetClassWord (USER.130)
*/
WORD SetClassWord( HWND hwnd, short offset, WORD newval )
{
CLASS * classPtr;
WND * wndPtr;
WORD retval = 0;
if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return 0;
if ((classPtr = CLASS_FindClassPtr( wndPtr->hClass )))
{
WORD * ptr = (WORD *)(((char *)classPtr->wExtra) + offset);
retval = *ptr;
*ptr = newval;
}
GlobalUnlock( hwnd );
return retval;
}
/***********************************************************************
* GetClassLong (USER.131)
*/
LONG GetClassLong( HWND hwnd, short offset )
{
CLASS * classPtr;
WND * wndPtr;
LONG retval = 0;
if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return 0;
if ((classPtr = CLASS_FindClassPtr( wndPtr->hClass )))
retval = *(LONG *)(((char *)classPtr->wExtra) + offset);
GlobalUnlock( hwnd );
return retval;
}
/***********************************************************************
* SetClassLong (USER.132)
*/
LONG SetClassLong( HWND hwnd, short offset, LONG newval )
{
CLASS * classPtr;
WND * wndPtr;
LONG retval = 0;
if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return 0;
if ((classPtr = CLASS_FindClassPtr( wndPtr->hClass )))
{
LONG * ptr = (LONG *)(((char *)classPtr->wExtra) + offset);
retval = *ptr;
*ptr = newval;
}
GlobalUnlock( hwnd );
return retval;
}

156
windows/clipping.c Normal file
View File

@ -0,0 +1,156 @@
/*
* Window clipping functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdio.h>
#include "windows.h"
#include "win.h"
/***********************************************************************
* InvalidateRgn (USER.126)
*/
void InvalidateRgn( HWND hwnd, HRGN hrgn, BOOL erase )
{
HRGN newRgn;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return;
if (!hrgn)
{
newRgn = CreateRectRgn(0, 0,
wndPtr->rectClient.right-wndPtr->rectClient.left,
wndPtr->rectClient.bottom-wndPtr->rectClient.top );
}
else
{
if (!(newRgn = CreateRectRgn( 0, 0, 0, 0 ))) return;
if (!wndPtr->hrgnUpdate) CombineRgn( newRgn, hrgn, 0, RGN_COPY );
else CombineRgn( newRgn, wndPtr->hrgnUpdate, hrgn, RGN_OR );
}
if (wndPtr->hrgnUpdate) DeleteObject( wndPtr->hrgnUpdate );
wndPtr->hrgnUpdate = newRgn;
if (erase) wndPtr->flags |= WIN_ERASE_UPDATERGN;
}
/***********************************************************************
* InvalidateRect (USER.125)
*/
void InvalidateRect( HWND hwnd, LPRECT rect, BOOL erase )
{
HRGN hrgn = 0;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return;
#ifdef DEBUG_WIN
if (rect) printf( "InvalidateRect: %d %d,%d-%d,%d\n", hwnd,
rect->left, rect->top, rect->right, rect->bottom );
else printf( "InvalidateRect: %d NULL\n", hwnd );
#endif
if (rect) hrgn = CreateRectRgnIndirect( rect );
InvalidateRgn( hwnd, hrgn, erase );
if (hrgn) DeleteObject( hrgn );
}
/***********************************************************************
* ValidateRgn (USER.128)
*/
void ValidateRgn( HWND hwnd, HRGN hrgn )
{
HRGN newRgn;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return;
if (!wndPtr->hrgnUpdate) return;
if (!hrgn) newRgn = 0;
else
{
if (!(newRgn = CreateRectRgn( 0, 0, 0, 0 ))) return;
if (CombineRgn( newRgn, wndPtr->hrgnUpdate, hrgn, RGN_DIFF ) == NULLREGION)
{
DeleteObject( newRgn );
newRgn = 0;
}
}
DeleteObject( wndPtr->hrgnUpdate );
wndPtr->hrgnUpdate = newRgn;
if (!wndPtr->hrgnUpdate) wndPtr->flags &= ~WIN_ERASE_UPDATERGN;
}
/***********************************************************************
* ValidateRect (USER.127)
*/
void ValidateRect( HWND hwnd, LPRECT rect )
{
HRGN hrgn = 0;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return;
if (rect) hrgn = CreateRectRgnIndirect( rect );
ValidateRgn( hwnd, hrgn );
if (hrgn) DeleteObject( hrgn );
}
/***********************************************************************
* GetUpdateRect (USER.190)
*/
BOOL GetUpdateRect( HWND hwnd, LPRECT rect, BOOL erase )
{
BOOL retval;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return FALSE;
retval = (wndPtr->hrgnUpdate != 0);
if (rect)
{
if (wndPtr->hrgnUpdate) GetRgnBox( wndPtr->hrgnUpdate, rect );
else SetRectEmpty( rect );
if (erase && wndPtr->hrgnUpdate)
{
HDC hdc = GetDC( hwnd );
if (hdc)
{
SendMessage( hwnd, WM_ERASEBKGND, hdc, 0 );
ReleaseDC( hwnd, hdc );
}
}
}
GlobalUnlock( hwnd );
return retval;
}
/***********************************************************************
* GetUpdateRgn (USER.237)
*/
int GetUpdateRgn( HWND hwnd, HRGN hrgn, BOOL erase )
{
int retval;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return ERROR;
if (erase && wndPtr->hrgnUpdate)
{
HDC hdc = GetDC( hwnd );
if (hdc)
{
SendMessage( hwnd, WM_ERASEBKGND, hdc, 0 );
ReleaseDC( hwnd, hdc );
}
}
retval = CombineRgn( hrgn, wndPtr->hrgnUpdate, 0, RGN_COPY );
GlobalUnlock( hwnd );
return retval;
}

488
windows/dc.c Normal file
View File

@ -0,0 +1,488 @@
/*
* GDI Device Context functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include <stdlib.h>
#include <X11/Intrinsic.h>
#include "gdi.h"
extern HBITMAP BITMAP_hbitmapMemDC;
static DeviceCaps * displayDevCaps = NULL;
extern const WIN_DC_INFO DCVAL_defaultValues;
/* ROP code to GC function conversion */
const int DC_XROPfunction[16] =
{
GXclear, /* R2_BLACK */
GXnor, /* R2_NOTMERGEPEN */
GXandInverted, /* R2_MASKNOTPEN */
GXcopyInverted, /* R2_NOTCOPYPEN */
GXandReverse, /* R2_MASKPENNOT */
GXinvert, /* R2_NOT */
GXxor, /* R2_XORPEN */
GXnand, /* R2_NOTMASKPEN */
GXand, /* R2_MASKPEN */
GXequiv, /* R2_NOTXORPEN */
GXnoop, /* R2_NOP */
GXorInverted, /* R2_MERGENOTPEN */
GXcopy, /* R2_COPYPEN */
GXorReverse, /* R2_MERGEPENNOT */
GXor, /* R2_MERGEPEN */
GXset /* R2_WHITE */
};
/***********************************************************************
* DC_FillDevCaps
*
* Fill the device caps structure.
*/
void DC_FillDevCaps( DeviceCaps * caps )
{
caps->version = 0x300;
caps->technology = DT_RASDISPLAY;
caps->horzSize = WidthMMOfScreen( XT_screen );
caps->vertSize = HeightMMOfScreen( XT_screen );
caps->horzRes = WidthOfScreen( XT_screen );
caps->vertRes = HeightOfScreen( XT_screen );
caps->bitsPixel = DefaultDepthOfScreen( XT_screen );
caps->planes = 1;
caps->numBrushes = 0;
caps->numPens = 0;
caps->numMarkers = 0;
caps->numFonts = 0;
caps->numColors = 1 << caps->bitsPixel;
caps->pdeviceSize = 0;
caps->curveCaps = CC_CIRCLES | CC_PIE | CC_CHORD | CC_ELLIPSES |
CC_WIDE | CC_STYLED | CC_WIDESTYLED |
CC_INTERIORS | CC_ROUNDRECT;
caps->lineCaps = LC_POLYLINE | LC_MARKER | LC_POLYMARKER | LC_WIDE |
LC_STYLED | LC_WIDESTYLED | LC_INTERIORS;
caps->polygonalCaps = PC_POLYGON | PC_RECTANGLE | PC_WINDPOLYGON |
PC_SCANLINE | PC_WIDE | PC_STYLED |
PC_WIDESTYLED | PC_INTERIORS;
caps->textCaps = TC_OP_CHARACTER | TC_OP_STROKE | TC_CP_STROKE |
TC_IA_ABLE | TC_UA_ABLE | TC_SO_ABLE | TC_RA_ABLE;
caps->clipCaps = CP_REGION;
caps->rasterCaps = RC_BITBLT | RC_BANDING | RC_SCALING | RC_BITMAP64 |
RC_DI_BITMAP | RC_PALETTE | RC_DIBTODEV | RC_BIGFONT|
RC_STRETCHBLT | RC_STRETCHDIB | RC_DEVBITS;
caps->aspectX = 36; /* ?? */
caps->aspectY = 36; /* ?? */
caps->aspectXY = 51;
caps->logPixelsX = (int)(caps->horzRes * 25.4 / caps->horzSize);
caps->logPixelsY = (int)(caps->vertRes * 25.4 / caps->vertSize);
caps->sizePalette = DefaultVisual( XT_display, DefaultScreen(XT_display) )->map_entries;
caps->numReserved = 0;
caps->colorRes = 0;
}
/***********************************************************************
* DC_SetDeviceInfo
*
* Set device-specific info from device-independent info.
*/
void DC_SetDeviceInfo( HDC hdc, DC * dc )
{
SetTextColor( hdc, dc->w.textColor );
SetBkColor( hdc, dc->w.backgroundColor );
SetROP2( hdc, dc->w.ROPmode );
SelectObject( hdc, dc->w.hPen );
SelectObject( hdc, dc->w.hBrush );
SelectObject( hdc, dc->w.hFont );
if (dc->w.hGCClipRgn)
{
RGNOBJ *obj = (RGNOBJ *) GDI_GetObjPtr(dc->w.hGCClipRgn, REGION_MAGIC);
XSetClipMask( XT_display, dc->u.x.gc, obj->region.pixmap );
XSetClipOrigin( XT_display, dc->u.x.gc,
obj->region.box.left, obj->region.box.top );
}
else
{
XSetClipMask( XT_display, dc->u.x.gc, None );
XSetClipOrigin( XT_display, dc->u.x.gc, 0, 0 );
}
}
/***********************************************************************
* DC_SetupDCForBrush
*
* Setup dc->u.x.gc for drawing operations using current brush.
* Return 0 if brush is BS_NULL, 1 otherwise.
*/
int DC_SetupGCForBrush( DC * dc )
{
if (dc->u.x.brush.style == BS_NULL) return 0;
if (dc->u.x.brush.pixel == -1)
{
/* Special case used for monochrome pattern brushes.
* We need to swap foreground and background because
* Windows does it the wrong way...
*/
XSetForeground( XT_display, dc->u.x.gc, dc->w.backgroundPixel );
XSetBackground( XT_display, dc->u.x.gc, dc->w.textPixel );
}
else
{
XSetForeground( XT_display, dc->u.x.gc, dc->u.x.brush.pixel );
XSetBackground( XT_display, dc->u.x.gc, dc->w.backgroundPixel );
}
if (dc->u.x.brush.fillStyle != FillStippled)
XSetFillStyle( XT_display, dc->u.x.gc, dc->u.x.brush.fillStyle );
else
XSetFillStyle( XT_display, dc->u.x.gc,
(dc->w.backgroundMode == OPAQUE) ?
FillOpaqueStippled : FillStippled );
XSetTSOrigin( XT_display, dc->u.x.gc, dc->w.brushOrgX, dc->w.brushOrgY );
XSetFunction( XT_display, dc->u.x.gc, DC_XROPfunction[dc->w.ROPmode-1] );
return 1;
}
/***********************************************************************
* DC_SetupDCForPen
*
* Setup dc->u.x.gc for drawing operations using current pen.
* Return 0 if pen is PS_NULL, 1 otherwise.
*/
int DC_SetupGCForPen( DC * dc )
{
if (dc->u.x.pen.style == PS_NULL) return 0;
XSetForeground( XT_display, dc->u.x.gc, dc->u.x.pen.pixel );
XSetBackground( XT_display, dc->u.x.gc, dc->w.backgroundPixel );
XSetFillStyle( XT_display, dc->u.x.gc, FillSolid );
if ((dc->u.x.pen.style == PS_SOLID) ||
(dc->u.x.pen.style == PS_INSIDEFRAME))
{
XSetLineAttributes( XT_display, dc->u.x.gc, dc->u.x.pen.width,
LineSolid, CapRound, JoinBevel );
}
else
{
XSetLineAttributes( XT_display, dc->u.x.gc, dc->u.x.pen.width,
(dc->w.backgroundMode == OPAQUE) ? LineDoubleDash : LineOnOffDash,
CapRound, JoinBevel );
}
XSetFunction( XT_display, dc->u.x.gc, DC_XROPfunction[dc->w.ROPmode-1] );
return 1;
}
/***********************************************************************
* DC_SetupDCForText
*
* Setup dc->u.x.gc for text drawing operations.
* Return 0 if the font is null, 1 otherwise.
*/
int DC_SetupGCForText( DC * dc )
{
XSetForeground( XT_display, dc->u.x.gc, dc->w.textPixel );
XSetBackground( XT_display, dc->u.x.gc, dc->w.backgroundPixel );
XSetFillStyle( XT_display, dc->u.x.gc, FillSolid );
XSetFunction( XT_display, dc->u.x.gc, DC_XROPfunction[dc->w.ROPmode-1] );
if (!dc->u.x.font.fstruct) return 0;
XSetFont( XT_display, dc->u.x.gc, dc->u.x.font.fstruct->fid );
return 1;
}
/***********************************************************************
* GetDCState (GDI.179)
*/
HDC GetDCState( HDC hdc )
{
DC * newdc, * dc;
HANDLE handle;
if (!(dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ))) return 0;
if (!(handle = GDI_AllocObject( sizeof(DC), DC_MAGIC ))) return 0;
newdc = (DC *) GDI_HEAP_ADDR( handle );
#ifdef DEBUG_DC
printf( "GetDCState(%d): returning %d\n", hdc, handle );
#endif
memcpy( &newdc->w, &dc->w, sizeof(dc->w) );
newdc->saveLevel = 0;
newdc->w.flags |= DC_SAVED;
if (dc->w.hClipRgn)
{
newdc->w.hClipRgn = CreateRectRgn( 0, 0, 0, 0 );
CombineRgn( newdc->w.hClipRgn, dc->w.hClipRgn, 0, RGN_COPY );
}
if (dc->w.hVisRgn)
{
newdc->w.hVisRgn = CreateRectRgn( 0, 0, 0, 0 );
CombineRgn( newdc->w.hVisRgn, dc->w.hVisRgn, 0, RGN_COPY );
}
newdc->w.hGCClipRgn = 0;
return handle;
}
/***********************************************************************
* SetDCState (GDI.180)
*/
void SetDCState( HDC hdc, HDC hdcs )
{
DC * dc, * dcs;
if (!(dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ))) return;
if (!(dcs = (DC *) GDI_GetObjPtr( hdcs, DC_MAGIC ))) return;
if (!dcs->w.flags & DC_SAVED) return;
#ifdef DEBUG_DC
printf( "SetDCState: %d %d\n", hdc, hdcs );
#endif
if (dc->w.hClipRgn) DeleteObject( dc->w.hClipRgn );
if (dc->w.hVisRgn) DeleteObject( dc->w.hVisRgn );
if (dc->w.hGCClipRgn) DeleteObject( dc->w.hGCClipRgn );
memcpy( &dc->w, &dcs->w, sizeof(dc->w) );
dc->w.hClipRgn = dc->w.hVisRgn = dc->w.hGCClipRgn = 0;
dc->w.flags &= ~DC_SAVED;
DC_SetDeviceInfo( hdc, dc );
SelectClipRgn( hdc, dcs->w.hClipRgn );
SelectVisRgn( hdc, dcs->w.hGCClipRgn );
}
/***********************************************************************
* SaveDC (GDI.30)
*/
int SaveDC( HDC hdc )
{
HDC hdcs;
DC * dc, * dcs;
if (!(dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ))) return 0;
if (!(hdcs = GetDCState( hdc ))) return 0;
dcs = (DC *) GDI_HEAP_ADDR( hdcs );
dcs->header.hNext = dc->header.hNext;
dc->header.hNext = hdcs;
#ifdef DEBUG_DC
printf( "SaveDC(%d): returning %d\n", hdc, dc->saveLevel+1 );
#endif
return ++dc->saveLevel;
}
/***********************************************************************
* RestoreDC (GDI.39)
*/
BOOL RestoreDC( HDC hdc, short level )
{
DC * dc, * dcs;
#ifdef DEBUG_DC
printf( "RestoreDC: %d %d\n", hdc, level );
#endif
if (!(dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ))) return FALSE;
if (level == -1) level = dc->saveLevel;
if ((level < 1) || (level > dc->saveLevel)) return FALSE;
while (dc->saveLevel >= level)
{
HDC hdcs = dc->header.hNext;
if (!(dcs = (DC *) GDI_GetObjPtr( hdcs, DC_MAGIC ))) return FALSE;
dc->header.hNext = dcs->header.hNext;
if (--dc->saveLevel < level) SetDCState( hdc, hdcs );
DeleteDC( hdcs );
}
return TRUE;
}
/***********************************************************************
* CreateDC (GDI.53)
*/
HDC CreateDC( LPSTR driver, LPSTR device, LPSTR output, LPSTR initData )
{
DC * dc;
HANDLE handle;
handle = GDI_AllocObject( sizeof(DC), DC_MAGIC );
if (!handle) return 0;
dc = (DC *) GDI_HEAP_ADDR( handle );
#ifdef DEBUG_DC
printf( "CreateDC(%s %s %s): returning %d\n", driver, device, output, handle );
#endif
if (!displayDevCaps)
{
displayDevCaps = (DeviceCaps *) malloc( sizeof(DeviceCaps) );
DC_FillDevCaps( displayDevCaps );
}
dc->saveLevel = 0;
memcpy( &dc->w, &DCVAL_defaultValues, sizeof(DCVAL_defaultValues) );
memset( &dc->u.x, 0, sizeof(dc->u.x) );
dc->u.x.drawable = DefaultRootWindow( XT_display );
dc->u.x.gc = XCreateGC( XT_display, dc->u.x.drawable, 0, NULL );
dc->w.flags = 0;
dc->w.devCaps = displayDevCaps;
dc->w.planes = displayDevCaps->planes;
dc->w.bitsPerPixel = displayDevCaps->bitsPixel;
XSetSubwindowMode( XT_display, dc->u.x.gc, IncludeInferiors );
DC_SetDeviceInfo( handle, dc );
return handle;
}
/***********************************************************************
* CreateCompatibleDC (GDI.52)
*/
HDC CreateCompatibleDC( HDC hdc )
{
DC * dc;
HANDLE handle;
handle = GDI_AllocObject( sizeof(DC), DC_MAGIC );
if (!handle) return 0;
dc = (DC *) GDI_HEAP_ADDR( handle );
#ifdef DEBUG_DC
printf( "CreateCompatibleDC(%d): returning %d\n", hdc, handle );
#endif
dc->saveLevel = 0;
memcpy( &dc->w, &DCVAL_defaultValues, sizeof(DCVAL_defaultValues) );
memset( &dc->u.x, 0, sizeof(dc->u.x) );
dc->u.x.drawable = XCreatePixmap( XT_display,
DefaultRootWindow( XT_display ),
1, 1, 1 );
dc->u.x.gc = XCreateGC( XT_display, dc->u.x.drawable, 0, NULL );
dc->w.flags = DC_MEMORY;
dc->w.planes = 1;
dc->w.bitsPerPixel = 1;
dc->w.devCaps = displayDevCaps;
SelectObject( handle, BITMAP_hbitmapMemDC );
DC_SetDeviceInfo( handle, dc );
return handle;
}
/***********************************************************************
* DeleteDC (GDI.68)
*/
BOOL DeleteDC( HDC hdc )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return FALSE;
#ifdef DEBUG_DC
printf( "DeleteDC: %d\n", hdc );
#endif
while (dc->saveLevel)
{
DC * dcs;
HDC hdcs = dc->header.hNext;
if (!(dcs = (DC *) GDI_GetObjPtr( hdcs, DC_MAGIC ))) break;
dc->header.hNext = dcs->header.hNext;
dc->saveLevel--;
DeleteDC( hdcs );
}
if (!(dc->w.flags & DC_SAVED))
{
SelectObject( hdc, STOCK_BLACK_PEN );
SelectObject( hdc, STOCK_WHITE_BRUSH );
SelectObject( hdc, STOCK_SYSTEM_FONT );
XFreeGC( XT_display, dc->u.x.gc );
if (dc->w.flags & DC_MEMORY) BITMAP_UnselectBitmap( dc );
}
if (dc->w.hClipRgn) DeleteObject( dc->w.hClipRgn );
if (dc->w.hVisRgn) DeleteObject( dc->w.hVisRgn );
if (dc->w.hGCClipRgn) DeleteObject( dc->w.hGCClipRgn );
return GDI_FreeObject( hdc );
}
/***********************************************************************
* GetDeviceCaps (GDI.80)
*/
int GetDeviceCaps( HDC hdc, WORD cap )
{
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
if (cap > sizeof(DeviceCaps)-sizeof(WORD)) return 0;
#ifdef DEBUG_DC
printf( "GetDeviceCaps(%d,%d): returning %d\n",
hdc, cap, *(WORD *)(((char *)dc->w.devCaps) + cap) );
#endif
return *(WORD *)(((char *)dc->w.devCaps) + cap);
}
/***********************************************************************
* SetBkColor (GDI.1)
*/
COLORREF SetBkColor( HDC hdc, COLORREF color )
{
COLORREF oldColor;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0x80000000;
oldColor = dc->w.backgroundColor;
dc->w.backgroundColor = color;
dc->w.backgroundPixel = GetNearestPaletteIndex( dc->w.hPalette, color );
XSetBackground( XT_display, dc->u.x.gc, dc->w.backgroundPixel );
return oldColor;
}
/***********************************************************************
* SetTextColor (GDI.9)
*/
COLORREF SetTextColor( HDC hdc, COLORREF color )
{
COLORREF oldColor;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0x80000000;
oldColor = dc->w.textColor;
dc->w.textColor = color;
dc->w.textPixel = GetNearestPaletteIndex( dc->w.hPalette, color );
XSetForeground( XT_display, dc->u.x.gc, dc->w.textPixel );
return oldColor;
}
/***********************************************************************
* SetDCOrg (GDI.117)
*/
DWORD SetDCOrg( HDC hdc, short x, short y )
{
DWORD prevOrg;
DC * dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC );
if (!dc) return 0;
prevOrg = dc->w.DCOrgX | (dc->w.DCOrgY << 16);
dc->w.DCOrgX = x;
dc->w.DCOrgY = y;
return prevOrg;
}

157
windows/dce.c Normal file
View File

@ -0,0 +1,157 @@
/*
* USER DCE functions
*
* Copyright 1993 Alexandre Julliard
*/
static char Copyright[] = "Copyright Alexandre Julliard, 1993";
#include "dce.h"
#include "win.h"
#include "gdi.h"
#define NB_DCE 5 /* Number of DCEs created at startup */
extern Display * XT_display;
extern Screen * XT_screen;
static HANDLE firstDCE = 0;
static HDC defaultDCstate = 0;
/***********************************************************************
* DCE_Init
*/
void DCE_Init()
{
int i;
HANDLE handle;
DCE * dce;
for (i = 0; i < NB_DCE; i++)
{
handle = GlobalAlloc( GMEM_MOVEABLE, sizeof(DCE) );
if (!handle) return;
dce = (DCE *) GlobalLock( handle );
dce->hdc = CreateDC( "DISPLAY", NULL, NULL, NULL );
if (!dce->hdc)
{
GlobalUnlock( handle );
GlobalFree( handle );
return;
}
dce->hwndCurrent = 0;
dce->flags = 0;
dce->inUse = FALSE;
dce->xOrigin = 0;
dce->yOrigin = 0;
dce->hNext = firstDCE;
firstDCE = handle;
if (!defaultDCstate) defaultDCstate = GetDCState( dce->hdc );
GlobalUnlock( handle );
}
}
/***********************************************************************
* GetDC (USER.66)
*/
HDC GetDC( HWND hwnd )
{
HANDLE hdce, next;
HDC hdc;
DCE * dce;
DC * dc;
WND * wndPtr = NULL;
if (hwnd)
{
wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return 0;
}
for (hdce = firstDCE; (hdce); hdce = next)
{
dce = (DCE *) GlobalLock( hdce );
if (!dce) return 0;
if (!dce->inUse) break;
next = dce->hNext;
GlobalUnlock( hdce );
}
if (!hdce)
{
if (hwnd) GlobalUnlock( hwnd );
return 0;
}
/* Initialize DC */
dc = (DC *) GDI_GetObjPtr( dce->hdc, DC_MAGIC );
if (!dc)
{
if (hwnd) GlobalUnlock( hwnd );
return 0;
}
if (wndPtr)
{
dc->u.x.drawable = XtWindow( wndPtr->winWidget );
dc->u.x.widget = wndPtr->winWidget;
}
else
{
dc->u.x.drawable = DefaultRootWindow( XT_display );
dc->u.x.widget = 0;
}
SetDCState( dce->hdc, defaultDCstate );
dce->hwndCurrent = hwnd;
dce->inUse = TRUE;
hdc = dce->hdc;
GlobalUnlock( hdce );
if (hwnd) GlobalUnlock( hwnd );
#ifdef DEBUG_WIN
printf( "GetDC(%d): returning %d\n", hwnd, hdc );
#endif
return hdc;
}
/***********************************************************************
* ReleaseDC (USER.68)
*/
int ReleaseDC( HWND hwnd, HDC hdc )
{
HANDLE hdce, next;
DCE * dce;
WND * wndPtr = NULL;
#ifdef DEBUG_WIN
printf( "ReleaseDC: %d %d\n", hwnd, hdc );
#endif
if (hwnd)
{
wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return 0;
}
for (hdce = firstDCE; (hdce); hdce = next)
{
dce = (DCE *) GlobalLock( hdce );
if (!dce) return 0;
if (dce->inUse && (dce->hdc == hdc)) break;
next = dce->hNext;
GlobalUnlock( hdce );
}
if (hdce)
{
dce->inUse = FALSE;
GlobalUnlock( hdce );
}
if (hwnd) GlobalUnlock( hwnd );
return (hdce != 0);
}

Some files were not shown because too many files have changed in this diff Show More