[Scummvm-cvs-logs] SF.net SVN: scummvm:[44565] scummvm/trunk

wjpalenstijn at users.sourceforge.net wjpalenstijn at users.sourceforge.net
Sat Oct 3 22:49:26 CEST 2009


Revision: 44565
          http://scummvm.svn.sourceforge.net/scummvm/?rev=44565&view=rev
Author:   wjpalenstijn
Date:     2009-10-03 20:49:18 +0000 (Sat, 03 Oct 2009)

Log Message:
-----------
SCI: Merge new GUI code written by m_kiewitz.

This is a major rewrite of the graphics code. A slightly adapted
version of the old code is still available and currently the default.
The new code is selectable in sci.cpp, but is not yet finished.

Modified Paths:
--------------
    scummvm/trunk/dists/msvc8/sci.vcproj
    scummvm/trunk/dists/msvc9/sci.vcproj
    scummvm/trunk/engines/sci/engine/kernel.cpp
    scummvm/trunk/engines/sci/engine/kernel.h
    scummvm/trunk/engines/sci/engine/kevent.cpp
    scummvm/trunk/engines/sci/engine/kgraphics.cpp
    scummvm/trunk/engines/sci/engine/kmisc.cpp
    scummvm/trunk/engines/sci/engine/state.h
    scummvm/trunk/engines/sci/gfx/gfx_driver.cpp
    scummvm/trunk/engines/sci/gfx/gfx_driver.h
    scummvm/trunk/engines/sci/gfx/res_view.cpp
    scummvm/trunk/engines/sci/module.mk
    scummvm/trunk/engines/sci/sci.cpp
    scummvm/trunk/engines/sci/sci.h

Added Paths:
-----------
    scummvm/trunk/engines/sci/gui/
    scummvm/trunk/engines/sci/gui/gui.cpp
    scummvm/trunk/engines/sci/gui/gui.h
    scummvm/trunk/engines/sci/gui/gui_dbllist.cpp
    scummvm/trunk/engines/sci/gui/gui_dbllist.h
    scummvm/trunk/engines/sci/gui/gui_font.cpp
    scummvm/trunk/engines/sci/gui/gui_font.h
    scummvm/trunk/engines/sci/gui/gui_gfx.cpp
    scummvm/trunk/engines/sci/gui/gui_gfx.h
    scummvm/trunk/engines/sci/gui/gui_helpers.h
    scummvm/trunk/engines/sci/gui/gui_memmgr.cpp
    scummvm/trunk/engines/sci/gui/gui_memmgr.h
    scummvm/trunk/engines/sci/gui/gui_picture.cpp
    scummvm/trunk/engines/sci/gui/gui_picture.h
    scummvm/trunk/engines/sci/gui/gui_screen.cpp
    scummvm/trunk/engines/sci/gui/gui_screen.h
    scummvm/trunk/engines/sci/gui/gui_view.cpp
    scummvm/trunk/engines/sci/gui/gui_view.h
    scummvm/trunk/engines/sci/gui/gui_windowmgr.cpp
    scummvm/trunk/engines/sci/gui/gui_windowmgr.h
    scummvm/trunk/engines/sci/gui32/
    scummvm/trunk/engines/sci/gui32/gui32.cpp
    scummvm/trunk/engines/sci/gui32/gui32.h

Modified: scummvm/trunk/dists/msvc8/sci.vcproj
===================================================================
--- scummvm/trunk/dists/msvc8/sci.vcproj	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/dists/msvc8/sci.vcproj	2009-10-03 20:49:18 UTC (rev 44565)
@@ -92,6 +92,29 @@
 			<File RelativePath="..\..\engines\sci\gfx\seq_decoder.cpp" />
 			<File RelativePath="..\..\engines\sci\gfx\seq_decoder.h" />
 		</Filter>
+		<Filter	Name="gui">
+			<File RelativePath="..\..\engines\sci\gui\gui.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_dbllist.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_dbllist.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_font.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_font.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_gfx.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_gfx.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_helpers.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_memmgr.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_memmgr.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_picture.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_picture.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_screen.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_screen.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_view.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_view.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_windowmgr.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_windowmgr.h" />
+			<File RelativePath="..\..\engines\sci\gui32\gui32.h" />
+			<File RelativePath="..\..\engines\sci\gui32\gui32.cpp" />
+		</Filter>
 		<Filter	Name="sfx">
 			<File RelativePath="..\..\engines\sci\sfx\core.cpp" />
 			<File RelativePath="..\..\engines\sci\sfx\core.h" />

Modified: scummvm/trunk/dists/msvc9/sci.vcproj
===================================================================
--- scummvm/trunk/dists/msvc9/sci.vcproj	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/dists/msvc9/sci.vcproj	2009-10-03 20:49:18 UTC (rev 44565)
@@ -93,6 +93,29 @@
 			<File RelativePath="..\..\engines\sci\gfx\seq_decoder.cpp" />
 			<File RelativePath="..\..\engines\sci\gfx\seq_decoder.h" />
 		</Filter>
+		<Filter	Name="gui">
+			<File RelativePath="..\..\engines\sci\gui\gui.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_dbllist.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_dbllist.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_font.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_font.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_gfx.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_gfx.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_helpers.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_memmgr.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_memmgr.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_picture.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_picture.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_screen.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_screen.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_view.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_view.h" />
+			<File RelativePath="..\..\engines\sci\gui\gui_windowmgr.cpp" />
+			<File RelativePath="..\..\engines\sci\gui\gui_windowmgr.h" />
+			<File RelativePath="..\..\engines\sci\gui32\gui32.h" />
+			<File RelativePath="..\..\engines\sci\gui32\gui32.cpp" />
+		</Filter>
 		<Filter	Name="sfx">
 			<File RelativePath="..\..\engines\sci\sfx\core.cpp" />
 			<File RelativePath="..\..\engines\sci\sfx\core.h" />

Modified: scummvm/trunk/engines/sci/engine/kernel.cpp
===================================================================
--- scummvm/trunk/engines/sci/engine/kernel.cpp	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/engine/kernel.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -332,18 +332,18 @@
 	DEFUN("ShowMovie", kShowMovie, "..*"),
 	DEFUN("SetVideoMode", kSetVideoMode, "i"),
 	DEFUN("Platform", kPlatform, "i*"),
-	DEFUN("PalVary", kPalVary, "ii*"),
+	DEFUN("TextColors", kTextColors, ".*"),
+	DEFUN("TextFonts", kTextFonts, ".*"),
 
 #if 0
 	// Stub functions
+	DEFUN("PalVary", kPalVary, "ii*"),
 	DEFUN("ShiftScreen", kShiftScreen, ".*"),
 	DEFUN("MemorySegment", kMemorySegment, ".*"),
 	DEFUN("ListOps", kListOps, ".*"),
 	DEFUN("ATan", kATan, ".*"),
 	DEFUN("MergePoly", kMergePoly, ".*"),
 	DEFUN("AssertPalette", kAssertPalette, ".*"),
-	DEFUN("TextColors", kTextColors, ".*"),
-	DEFUN("TextFonts", kTextFonts, ".*"),
 	DEFUN("Record", kRecord, ".*"),
 	DEFUN("PlayBack", kPlayBack, ".*"),
 	DEFUN("DbugStr", kDbugStr, ".*"),

Modified: scummvm/trunk/engines/sci/engine/kernel.h
===================================================================
--- scummvm/trunk/engines/sci/engine/kernel.h	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/engine/kernel.h	2009-10-03 20:49:18 UTC (rev 44565)
@@ -454,7 +454,8 @@
 reg_t kSetVideoMode(EngineState *s, int argc, reg_t *argv);
 reg_t kStrSplit(EngineState *s, int argc, reg_t *argv);
 reg_t kPlatform(EngineState *s, int argc, reg_t *argv);
-reg_t kPalVary(EngineState *s, int argc, reg_t *argv);
+reg_t kTextColors(EngineState *s, int argc, reg_t *argv);
+reg_t kTextFonts(EngineState *s, int argc, reg_t *argv);
 
 } // End of namespace Sci
 

Modified: scummvm/trunk/engines/sci/engine/kevent.cpp
===================================================================
--- scummvm/trunk/engines/sci/engine/kevent.cpp	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/engine/kevent.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -206,11 +206,13 @@
 	SegManager *segMan = s->segMan;
 
 	if (obj.segment) {
-		int x = GET_SEL32V(obj, x);
-		int y = GET_SEL32V(obj, y);
+		int16 x = GET_SEL32V(obj, x);
+		int16 y = GET_SEL32V(obj, y);
 
-		PUT_SEL32V(obj, x, x - s->port->zone.x);
-		PUT_SEL32V(obj, y, y - s->port->zone.y);
+		s->gui->globalToLocal(&x, &y);
+
+		PUT_SEL32V(obj, x, x);
+		PUT_SEL32V(obj, y, y);
 	}
 
 	return s->r_acc;
@@ -222,11 +224,13 @@
 	SegManager *segMan = s->segMan;
 
 	if (obj.segment) {
-		int x = GET_SEL32V(obj, x);
-		int y = GET_SEL32V(obj, y);
+		int16 x = GET_SEL32V(obj, x);
+		int16 y = GET_SEL32V(obj, y);
 
-		PUT_SEL32V(obj, x, x + s->port->zone.x);
-		PUT_SEL32V(obj, y, y + s->port->zone.y);
+		s->gui->localToGlobal(&x, &y);
+
+		PUT_SEL32V(obj, x, x);
+		PUT_SEL32V(obj, y, y);
 	}
 
 	return s->r_acc;

Modified: scummvm/trunk/engines/sci/engine/kgraphics.cpp
===================================================================
--- scummvm/trunk/engines/sci/engine/kgraphics.cpp	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/engine/kgraphics.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -105,7 +105,8 @@
 		return value;
 }
 
-static void assert_primary_widget_lists(EngineState *s) {
+// was static
+void assert_primary_widget_lists(EngineState *s) {
 	if (!s->dyn_views) {
 		rect_t bounds = s->picture_port->_bounds;
 
@@ -123,7 +124,8 @@
 	}
 }
 
-static void reparentize_primary_widget_lists(EngineState *s, GfxPort *newport) {
+// static
+void reparentize_primary_widget_lists(EngineState *s, GfxPort *newport) {
 	if (!newport)
 		newport = s->picture_port;
 
@@ -264,24 +266,6 @@
 	}
 }
 
-static gfx_color_t graph_map_color(EngineState *s, int color, int priority, int control) {
-	gfx_color_t retval;
-
-	if (!s->resMan->isVGA()) {
-		retval = s->ega_colors[(color >=0 && color < 16)? color : 0];
-		gfxop_set_color(s->gfx_state, &retval, (color < 0) ? -1 : retval.visual.r, retval.visual.g, retval.visual.b,
-		                (color == -1) ? 255 : 0, priority, control);
-	} else {
-		retval.visual = get_pic_color(s, color);
-		retval.alpha = 0;
-		retval.priority = priority;
-		retval.control = control;
-		retval.mask = GFX_MASK_VISUAL | ((priority >= 0) ? GFX_MASK_PRIORITY : 0) | ((control >= 0) ? GFX_MASK_CONTROL : 0);
-	};
-
-	return retval;
-}
-
 static reg_t kSetCursorSci0(EngineState *s, int argc, reg_t *argv) {
 	int16 cursor = argv[0].toSint16();
 
@@ -353,27 +337,8 @@
 }
 
 reg_t kMoveCursor(EngineState *s, int argc, reg_t *argv) {
-	Common::Point newPos;
-
-	newPos = s->gfx_state->pointer_pos;
-
-	if (argc == 1) {
-		// Case ignored on IBM PC
-	} else {
-		newPos.x = argv[0].toSint16() + s->port->zone.x;
-		newPos.y = argv[1].toSint16() + s->port->zone.y;
-
-		if (newPos.x > s->port->zone.x + s->port->zone.width)
-			newPos.x = s->port->zone.x + s->port->zone.width;
-		if (newPos.y > s->port->zone.y + s->port->zone.height)
-			newPos.y = s->port->zone.y + s->port->zone.height;
-
-		if (newPos.x < 0) newPos.x = 0;
-		if (newPos.y < 0) newPos.y = 0;
-	}
-
-	gfxop_set_pointer_position(s->gfx_state, newPos);
-
+	if (argc == 2)
+		s->gui->moveCursor(argv[0].toSint16(), argv[1].toSint16());
 	return s->r_acc;
 }
 
@@ -439,117 +404,74 @@
 #endif
 }
 
-void _k_graph_rebuild_port_with_color(EngineState *s, gfx_color_t newbgcolor) {
-	GfxPort *port = s->port;
-	GfxPort *newport;
+reg_t kGraph(EngineState *s, int argc, reg_t *argv) {
+	int rectLeft = 0, rectTop = 0, rectRight = 0, rectBottom = 0;
+	uint16 flags;
+	int16 priority, control, color, colorMask;
 
-	newport = sciw_new_window(s, port->zone, port->_font, port->_color, newbgcolor,
-	                          s->titlebar_port->_font, s->ega_colors[15], s->ega_colors[8],
-	                          port->_title_text.c_str(), port->port_flags & ~kWindowTransparent);
-
-	if (s->dyn_views) {
-		int found = 0;
-		GfxContainer *parent = s->dyn_views->_parent;
-
-		while (parent && !(found |= (parent == port)))
-			parent = parent->_parent;
-
-		s->dyn_views = NULL;
+	Common::Rect rect;
+	if (argc>=5) {
+		rectLeft = argv[2].toSint16(); rectTop = argv[1].toSint16();
+		rectRight = argv[4].toSint16(); rectBottom = argv[3].toSint16();
+		// Fixup data, so that a valid rectangle is formed
+		if (rectLeft > rectRight) {
+			rectRight = rectLeft; rectLeft = argv[4].toSint16();
+		}
+		if (rectTop > rectBottom) {
+			rectBottom = rectTop; rectTop = argv[3].toSint16();
+		}
+		rect = Common::Rect (rectLeft, rectTop, rectRight, rectBottom);
 	}
 
-	port->_parent->add((GfxContainer *)port->_parent, newport);
-	delete port;
-}
-
-static bool activated_icon_bar = false;	// FIXME: Avoid non-const global vars
-static int port_origin_x = 0;	// FIXME: Avoid non-const global vars
-static int port_origin_y = 0;	// FIXME: Avoid non-const global vars
-
-reg_t kGraph(EngineState *s, int argc, reg_t *argv) {
-	rect_t area;
+	// old code, may be removed later after class migration
 	GfxPort *port = s->port;
 	int redraw_port = 0;
-
+	rect_t area;
 	area = gfx_rect(argv[2].toSint16(), argv[1].toSint16() , argv[4].toSint16(), argv[3].toSint16());
-
 	area.width = area.width - area.x; // Since the actual coordinates are absolute
 	area.height = area.height - area.y;
 
 	switch (argv[0].toSint16()) {
 
 	case K_GRAPH_GET_COLORS_NR:
-
 		return make_reg(0, !s->resMan->isVGA() ? 0x10 : 0x100);
 		break;
 
-	case K_GRAPH_DRAW_LINE: {
-		int16 priority = (argc > 6) ? argv[6].toSint16() : -1;
-		int16 control = (argc > 7) ? argv[7].toSint16() : -1;
-		gfx_color_t gfxcolor = graph_map_color(s, argv[5].toSint16(), priority, control);
+	case K_GRAPH_DRAW_LINE:
+		priority = (argc > 6) ? argv[6].toSint16() : -1;
+		control = (argc > 7) ? argv[7].toSint16() : -1;
+		color = argv[5].toSint16();
 
-		debugC(2, kDebugLevelGraphics, "draw_line((%d, %d), (%d, %d), col=%d, p=%d, c=%d, mask=%d)\n",
-		          argv[2].toSint16(), argv[1].toSint16(), argv[4].toSint16(), argv[3].toSint16(), argv[5].toSint16(), priority, control, gfxcolor.mask);
+		// FIXME: rect must be changed to 2 Common::Point
+		s->gui->graphDrawLine(rect, color, priority, control);
+		break;
 
-		redraw_port = 1;
-
-		// Note: it's quite possible that the coordinates of the line will *not* form a valid rectangle (e.g. it might
-		// have negative width/height). The actual dirty rectangle is constructed in gfxdr_add_dirty().
-		// FIXME/TODO: We need to change the semantics of this call, so that no fake rectangles are used. As it is, it's
-		// not possible change rect_t to Common::Rect, as we assume that Common::Rect forms a *valid* rectangle.
-		ADD_TO_CURRENT_PICTURE_PORT(gfxw_new_line(Common::Point(argv[2].toSint16(), argv[1].toSint16()), Common::Point(argv[4].toSint16(), argv[3].toSint16()),
-		                               gfxcolor, GFX_LINE_MODE_CORRECT, GFX_LINE_STYLE_NORMAL));
-
-	}
-	break;
-
 	case K_GRAPH_SAVE_BOX:
-
-		area.x += s->port->zone.x + port_origin_x;
-		area.y += s->port->zone.y + port_origin_y;
-		area.width += -port_origin_x;
-		area.height += -port_origin_y;
-
-		return(graph_save_box(s, area));
+		flags = (argc > 5) ? argv[5].toUint16() : 0;
+		return s->gui->graphSaveBox(rect, flags);
 		break;
 
 	case K_GRAPH_RESTORE_BOX:
-
-		graph_restore_box(s, argv[1]);
+		s->gui->graphRestoreBox(argv[1]);
 		break;
 
 	case K_GRAPH_FILL_BOX_BACKGROUND:
-
-		_k_graph_rebuild_port_with_color(s, port->_bgcolor);
-		port = s->port;
-
-		redraw_port = 1;
+		s->gui->graphFillBoxBackground(rect);
 		break;
 
 	case K_GRAPH_FILL_BOX_FOREGROUND:
+		s->gui->graphFillBoxForeground(rect);
+		break;
 
-		_k_graph_rebuild_port_with_color(s, port->_color);
-		port = s->port;
+	case K_GRAPH_FILL_BOX_ANY:
+		priority = (argc > 7) ? argv[7].toSint16() : -1;
+		control = (argc > 8) ? argv[8].toSint16() : -1;
+		color = argv[6].toSint16();
+		colorMask = argv[5].toUint16();
 
-		redraw_port = 1;
+		s->gui->graphFillBox(rect, colorMask, color, priority, control);
 		break;
 
-	case K_GRAPH_FILL_BOX_ANY: {
-		int16 priority = (argc > 7) ? argv[7].toSint16() : -1;
-		int16 control = (argc > 8) ? argv[8].toSint16() : -1;
-		gfx_color_t color = graph_map_color(s, argv[6].toSint16(), priority, control);
-
-		color.mask = (byte)argv[5].toUint16();
-
-		debugC(2, kDebugLevelGraphics, "fill_box_any((%d, %d), (%d, %d), col=%d, p=%d, c=%d, mask=%d)\n",
-		          argv[2].toSint16(), argv[1].toSint16(), argv[4].toSint16(), argv[3].toSint16(), argv[6].toSint16(), priority, control, argv[5].toUint16());
-
-		// FIXME/TODO: this is not right, as some of the dialogs are drawn *behind* some widgets. But at least it works for now
-		//ADD_TO_CURRENT_PICTURE_PORT(gfxw_new_box(s->gfx_state, area, color, color, GFX_BOX_SHADE_FLAT));	// old code
-		s->picture_port->add((GfxContainer *)s->picture_port, gfxw_new_box(s->gfx_state, area, color, color, GFX_BOX_SHADE_FLAT));
-
-	}
-	break;
-
 	case K_GRAPH_UPDATE_BOX: {
 
 		debugC(2, kDebugLevelGraphics, "update_box(%d, %d, %d, %d)\n", argv[1].toSint16(), argv[2].toSint16(), argv[3].toSint16(), argv[4].toSint16());
@@ -557,14 +479,12 @@
 		area.x += s->port->zone.x;
 		area.y += s->port->zone.y;
 
-		gfxop_update_box(s->gfx_state, area);
-
+		// FIXME: Change to class calling
+		//gfxop_update_box(s->gfx_state, area);
 	}
 	break;
 
 	case K_GRAPH_REDRAW_BOX: {
-
-
 		debugC(2, kDebugLevelGraphics, "redraw_box(%d, %d, %d, %d)\n", argv[1].toSint16(), argv[2].toSint16(), argv[3].toSint16(), argv[4].toSint16());
 
 		area.x += s->port->zone.x;
@@ -573,10 +493,9 @@
 		if (s->dyn_views && s->dyn_views->_parent == (GfxContainer *)s->port)
 			s->dyn_views->draw(Common::Point(0, 0));
 
-		gfxop_update_box(s->gfx_state, area);
-
+		// FIXME: Change to class calling
+		//gfxop_update_box(s->gfx_state, area);
 	}
-
 	break;
 
 	case K_GRAPH_ADJUST_PRIORITY:
@@ -601,22 +520,19 @@
 }
 
 reg_t kTextSize(EngineState *s, int argc, reg_t *argv) {
-	int width, height;
+	int16 textWidth, textHeight;
 	Common::String text = s->segMan->getString(argv[1]);
 	reg_t *dest = s->segMan->derefRegPtr(argv[0], 4);
 	int maxwidth = (argc > 3) ? argv[3].toUint16() : 0;
 	int font_nr = argv[2].toUint16();
 
 	Common::String sep_str;
-	const char *sep = NULL; 
+	const char *sep = NULL;
 	if ((argc > 4) && (argv[4].segment)) {
 		sep_str = s->segMan->getString(argv[4]);
 		sep = sep_str.c_str();
 	}
 
-	if (maxwidth < 0)
-		maxwidth = 0;
-
 	dest[0] = dest[1] = NULL_REG;
 
 	if (text.empty() || !dest) { // Empty text
@@ -625,20 +541,19 @@
 		return s->r_acc;
 	}
 
-	gfxop_get_text_params(s->gfx_state, font_nr, s->strSplit(text.c_str(), sep).c_str(), maxwidth ? maxwidth : MAX_TEXT_WIDTH_MAGIC_VALUE,
-	                                 &width, &height, 0, NULL, NULL, NULL);
-	debugC(2, kDebugLevelStrings, "GetTextSize '%s' -> %dx%d\n", text.c_str(), width, height);
+	textWidth = dest[3].toUint16(); textHeight = dest[2].toUint16();
+	s->gui->textSize(s->strSplit(text.c_str(), sep).c_str(), font_nr, maxwidth, &textWidth, &textHeight);
+	debugC(2, kDebugLevelStrings, "GetTextSize '%s' -> %dx%d\n", text.c_str(), textWidth, textHeight);
 
-	dest[2] = make_reg(0, height);
-//	dest[3] = make_reg(0, maxwidth? maxwidth : width);
-	dest[3] = make_reg(0, width);
-
+	dest[2] = make_reg(0, textHeight);
+	dest[3] = make_reg(0, textWidth);
 	return s->r_acc;
 }
 
 reg_t kWait(EngineState *s, int argc, reg_t *argv) {
-	uint32 time;
 	int sleep_time = argv[0].toUint16();
+#if 0
+	uint32 time;
 
 	time = g_system->getMillis();
 	s->r_acc = make_reg(0, ((long)time - (long)s->last_wait_time) * 60 / 1000);
@@ -650,7 +565,12 @@
 	// Reset speed throttler: Game is playing along nicely anyway
 	if (sleep_time > 0)
 		s->speedThrottler->reset();
+#endif
 
+	// FIXME: we should not be asking from the GUI to wait. The kernel sounds
+	// like a better place
+	s->gui->wait(sleep_time);
+
 	return s->r_acc;
 }
 
@@ -977,72 +897,25 @@
 #define K_DRAWPIC_FLAG_MIRRORED (1 << 14)
 
 reg_t kDrawPic(EngineState *s, int argc, reg_t *argv) {
-	drawn_pic_t dp;
-	bool add_to_pic = (argc > 2) ? !argv[2].toSint16() : false;
-	gfx_color_t transparent = s->wm_port->_bgcolor;
-	int picFlags = DRAWPIC01_FLAG_FILL_NORMALLY;
+	sciResourceId pictureId = argv[0].toUint16();
+	uint16 flags = 0;
+	uint16 style = 1;
+	int16 EGApaletteNo = -1;
 
-	if (s->_kernel->usesOldGfxFunctions())
-		add_to_pic = (argc > 2) ? argv[2].toSint16() : false;
-
-	dp.nr = argv[0].toSint16();
-	dp.palette = (argc > 3) ? argv[3].toSint16() : 0;
-
-	if ((argc > 1) && (argv[1].toUint16() & K_DRAWPIC_FLAG_MIRRORED))
-		picFlags |= DRAWPIC1_FLAG_MIRRORED;
-
-	gfxop_disable_dirty_frames(s->gfx_state);
-
-	if (NULL != s->old_screen) {
-		gfxop_free_pixmap(s->gfx_state, s->old_screen);
+	if (argc >= 2)
+		style = argv[1].toUint16();
+	if (argc >= 3) {
+		if (!s->_kernel->usesOldGfxFunctions())
+			flags = !argv[2].toUint16();
+		else
+			flags = argv[2].toUint16();
 	}
+	if (argc >= 4)
+		EGApaletteNo = argv[3].toUint16();
 
-	s->old_screen = gfxop_grab_pixmap(s->gfx_state, gfx_rect(0, 10, 320, 190));
+	s->gui->drawPicture(pictureId, style, flags, EGApaletteNo);
 
-	debugC(2, kDebugLevelGraphics, "Drawing pic.%03d\n", argv[0].toSint16());
-
-	if (add_to_pic) {
-		gfxop_add_to_pic(s->gfx_state, dp.nr, picFlags, dp.palette);
-	} else {
-		gfxop_new_pic(s->gfx_state, dp.nr, picFlags, dp.palette);
-	}
-
-	delete s->wm_port;
-	delete s->picture_port;
-	delete s->iconbar_port;
-
-	s->wm_port = new GfxPort(s->visual, s->gfx_state->pic_port_bounds, s->ega_colors[0], transparent);
-	s->picture_port = new GfxPort(s->visual, s->gfx_state->pic_port_bounds, s->ega_colors[0], transparent);
-
-	s->iconbar_port = new GfxPort(s->visual, gfx_rect(0, 0, 320, 200), s->ega_colors[0], transparent);
-	s->iconbar_port->_flags |= GFXW_FLAG_NO_IMPLICIT_SWITCH;
-
-	s->visual->add((GfxContainer *)s->visual, s->picture_port);
-	s->visual->add((GfxContainer *)s->visual, s->wm_port);
-	s->visual->add((GfxContainer *)s->visual, s->iconbar_port);
-
-	s->port = s->picture_port;
-
-	s->pic_priority_table = gfxop_get_pic_metainfo(s->gfx_state);
-
-	if (argc > 1)
-		s->pic_animate = argv[1].toSint16() & 0xff; // The animation used during kAnimate() later on
-
-	s->dyn_views = NULL;
-	s->drop_views = NULL;
-
-	s->priority_first = 42;
-
-	if (s->_kernel->usesOldGfxFunctions())
-		s->priority_last = 200;
-	else
-		s->priority_last = 190;
-
-	s->pic_not_valid = 1;
-	s->pic_is_new = 1;
-
 	return s->r_acc;
-
 }
 
 Common::Rect set_base(EngineState *s, reg_t object) {
@@ -1230,9 +1103,14 @@
 }
 
 reg_t kPalette(EngineState *s, int argc, reg_t *argv) {
+//	warning("kPalette %d", argv[0].toUint16());
 	switch (argv[0].toUint16()) {
 	case 1:
-		debug(5, "STUB: kPalette() effect 1, direct palette set");
+		if (argc==3) {
+			int resourceNo = argv[1].toUint16();
+			int flags = argv[2].toUint16();
+			s->gui->paletteSet(resourceNo, flags);
+		}
 		break;
 	case 2:
 		debug(5, "STUB: kPalette() effect 2, set flag to colors");
@@ -1263,26 +1141,15 @@
 		int g = argv[2].toUint16();
 		int b = argv[3].toUint16();
 
-		int i, delta, bestindex = -1, bestdelta = 200000;
-
-		for (i = 0; i < s->gfx_state->gfxResMan->getColorCount(); i++) {
-			int dr = abs(s->gfx_state->gfxResMan->getColor(i).r - r);
-			int dg = abs(s->gfx_state->gfxResMan->getColor(i).g - g);
-			int db = abs(s->gfx_state->gfxResMan->getColor(i).b - b);
-
-			delta = dr * dr + dg * dg + db * db;
-
-			if (delta < bestdelta) {
-				bestdelta = delta;
-				bestindex = i;
-			}
-		}
-		// Don't warn about inexact mappings -- it's actually the
-		// rule rather than the exception
-		return make_reg(0, bestindex);
+		return make_reg(0, s->gui->paletteFind(r, g, b));
 	}
 	case 6:
-		debug(5, "STUB: kPalette() effect 6, animate palette");
+		if (argc==4) {
+			int fromColor = argv[1].toUint16();
+			int toColor = argv[2].toUint16();
+			int speed = argv[3].toSint16();
+			s->gui->paletteAnimate(fromColor, toColor, speed);
+		}
 		break;
 	case 7:
 		debug(5, "STUB: kPalette() effect 7, save palette to heap");
@@ -1297,13 +1164,8 @@
 	return s->r_acc;
 }
 
-reg_t kPalVary(EngineState *s, int argc, reg_t *argv) {
-	warning("STUB: kPalVary()");
-	return NULL_REG;
-}
+static void _k_draw_control(EngineState *s, reg_t obj, bool inverse);
 
-static void _k_draw_control(EngineState *s, reg_t obj, int inverse);
-
 static void disableCertainButtons(SegManager *segMan, Common::String gameName, reg_t obj) {
 	reg_t text_pos = GET_SEL32(obj, text);
 	Common::String text;
@@ -1349,15 +1211,15 @@
 	reg_t obj = argv[0];
 
 	disableCertainButtons(s->segMan, s->_gameName, obj);
-	_k_draw_control(s, obj, 0);
-	FULL_REDRAW();
+	_k_draw_control(s, obj, false);
+//	FULL_REDRAW();
 	return NULL_REG;
 }
 
 reg_t kHiliteControl(EngineState *s, int argc, reg_t *argv) {
 	reg_t obj = argv[0];
 
-	_k_draw_control(s, obj, 1);
+	_k_draw_control(s, obj, true);
 
 	return s->r_acc;
 }
@@ -1541,15 +1403,17 @@
 		case K_CONTROL_ICON:
 		case K_CONTROL_BOX:
 		case K_CONTROL_BUTTON:
-			if (event.segment) PUT_SEL32V(event, claimed, 1);
-			_k_draw_control(s, obj, 0);
+			// Control shall not be redrawn here, Original Sierra interpreter doesn't do it and it will mangle up
+			// menus in at least SQ5
+			//if (event.segment) PUT_SEL32V(event, claimed, 1);
+			//_k_draw_control(s, obj, false);
 			return NULL_REG;
 			break;
 
 		case K_CONTROL_TEXT: {
 			int state = GET_SEL32V(obj, state);
 			PUT_SEL32V(obj, state, state | kControlStateDitherFramed);
-			_k_draw_control(s, obj, 0);
+			_k_draw_control(s, obj, false);
 			PUT_SEL32V(obj, state, state);
 		}
 		break;
@@ -1562,7 +1426,7 @@
 	return s->r_acc;
 }
 
-static void _k_draw_control(EngineState *s, reg_t obj, int inverse) {
+static void _k_draw_control(EngineState *s, reg_t obj, bool inverse) {
 	SegManager *segMan = s->segMan;
 	int x = (int16)GET_SEL32V(obj, nsLeft);
 	int y = (int16)GET_SEL32V(obj, nsTop);
@@ -1570,6 +1434,9 @@
 	int yl = (int16)GET_SEL32V(obj, nsBottom) - y;
 	rect_t area = gfx_rect(x, y, xl, yl);
 
+	Common::Rect rect;
+	rect = Common::Rect (x, y, (int16)GET_SEL32V(obj, nsRight), (int16)GET_SEL32V(obj, nsBottom));
+
 	int font_nr = GET_SEL32V(obj, font);
 	reg_t text_pos = GET_SEL32(obj, text);
 	Common::String text;
@@ -1578,7 +1445,7 @@
 	int view = GET_SEL32V(obj, view);
 	int cel = sign_extend_byte(GET_SEL32V(obj, cel));
 	int loop = sign_extend_byte(GET_SEL32V(obj, loop));
-	gfx_alignment_t mode;
+	int mode;
 
 	int type = GET_SEL32V(obj, type);
 	int state = GET_SEL32V(obj, state);
@@ -1588,19 +1455,15 @@
 	switch (type) {
 	case K_CONTROL_BUTTON:
 		debugC(2, kDebugLevelGraphics, "drawing button %04x:%04x to %d,%d\n", PRINT_REG(obj), x, y);
-		ADD_TO_CURRENT_PICTURE_PORT(sciw_new_button_control(s->port, obj, area, s->strSplit(text.c_str(), NULL).c_str(), font_nr,
-		                          (int8)(state & kControlStateFramed), (int8)inverse, (int8)(state & kControlStateDisabled)));
-		break;
+		s->gui->drawControlButton(rect, obj, s->strSplit(text.c_str(), NULL).c_str(), font_nr, state, inverse);
+		return;
 
 	case K_CONTROL_TEXT:
 		mode = (gfx_alignment_t) GET_SEL32V(obj, mode);
-
 		debugC(2, kDebugLevelGraphics, "drawing text %04x:%04x to %d,%d, mode=%d\n", PRINT_REG(obj), x, y, mode);
+		s->gui->drawControlText(rect, obj, s->strSplit(text.c_str(), NULL).c_str(), font_nr, mode, state, inverse);
+		return;
 
-		ADD_TO_CURRENT_PICTURE_PORT(sciw_new_text_control(s->port, obj, area, s->strSplit(text.c_str()).c_str(), font_nr, mode,
-									(int8)(!!(state & kControlStateDitherFramed)), (int8)inverse));
-		break;
-
 	case K_CONTROL_EDIT:
 		debugC(2, kDebugLevelGraphics, "drawing edit control %04x:%04x to %d,%d\n", PRINT_REG(obj), x, y);
 
@@ -1676,9 +1539,9 @@
 					selection = i + 1;
 			}
 		}
+
 		ADD_TO_CURRENT_PICTURE_PORT(sciw_new_list_control(s->port, obj, area, font_nr, entries_list, entries_nr,
 		                          list_top, selection, (int8)inverse));
-
 		free(entries_list);
 		delete[] strings;
 	}
@@ -2350,75 +2213,34 @@
 }
 
 reg_t kGetPort(EngineState *s, int argc, reg_t *argv) {
-	return make_reg(0, s->port->_ID);
+	return s->gui->getPort();
 }
 
 reg_t kSetPort(EngineState *s, int argc, reg_t *argv) {
-	if (activated_icon_bar && argc == 6) {
-		port_origin_x = port_origin_y = 0;
-		activated_icon_bar = false;
-		return s->r_acc;
-	}
-
+	uint16 portPtr;
+	Common::Rect picRect;
+	int16 picTop, picLeft;
+	
 	switch (argc) {
-	case 1 : {
-		unsigned int port_nr = argv[0].toSint16();
-		GfxPort *new_port;
+		case 1:
+		portPtr = argv[0].toSint16();
+		s->gui->setPort(portPtr);
+		break;
 
-		/* We depart from official semantics here, sorry!
-		   Reasoning: Sierra SCI does not clip ports while we do.
-		   Therefore a draw to the titlebar port (which is the
-		   official semantics) would cut off the lower part of the
-		   icons in an SCI1 icon bar. Instead we have an
-		   iconbar_port that does not exist in SSCI. */
-		if (port_nr == (unsigned int) - 1) port_nr = s->iconbar_port->_ID;
-
-		new_port = s->visual->getPort(port_nr);
-
-		if (!new_port) {
-			warning("Invalid port %04x requested", port_nr);
-			return NULL_REG;
-		}
-
-		s->port->draw(gfxw_point_zero); // Update the port we're leaving
-		s->port = new_port;
-		return s->r_acc;
-	}
-	case 6 : {
-		port_origin_y = argv[0].toSint16();
-		port_origin_x = argv[1].toSint16();
-
-		if (argv[0].toSint16() == -10) {
-			s->port->draw(gfxw_point_zero); // Update the port we're leaving
-			s->port = s->iconbar_port;
-			activated_icon_bar = true;
-			return s->r_acc;
-		}
-
-		// Notify the graphics resource manager that the pic port bounds changed
-		s->gfx_state->gfxResMan->changePortBounds(argv[5].toUint16(), argv[4].toUint16(), argv[3].toUint16() + argv[5].toUint16(), argv[2].toUint16() + argv[4].toUint16());
-
-		// LSL6 calls kSetPort to extend the screen to draw the GUI. If we free all resources
-		// here, the background picture is freed too, and this makes everything a big mess.
-		// FIXME/TODO: This code really needs to be rewritten to conform to the original behavior
-		if (s->_gameName != "lsl6") {
-			s->gfx_state->pic_port_bounds = gfx_rect(argv[5].toUint16(), argv[4].toUint16(), argv[3].toUint16(), argv[2].toUint16());
-
-			// FIXME: Should really only invalidate all loaded pic resources here;
-			// this is overkill
-			s->gfx_state->gfxResMan->freeAllResources();
-		} else {
-			// WORKAROUND for LSL6
-			printf("SetPort case 6 called in LSL6. Origin: %d, %d - Clip rect: %d, %d, %d, %d\n", argv[1].toSint16(), argv[0].toSint16(), argv[5].toUint16(), argv[4].toUint16(), argv[3].toUint16(), argv[2].toUint16());
-		}
-
+		case 6:
+		picRect.top = argv[0].toSint16();
+		picRect.left = argv[1].toSint16();
+		picRect.bottom = argv[2].toSint16();
+		picRect.right = argv[3].toSint16();
+		picTop = argv[4].toSint16();
+		picLeft = argv[5].toSint16();
+		s->gui->setPortPic(picRect, picTop, picLeft);
 		break;
-	}
-	default :
+
+		default:
 		error("SetPort was called with %d parameters", argc);
 		break;
 	}
-
 	return NULL_REG;
 }
 
@@ -2428,142 +2250,43 @@
 	int cel = argv[2].toSint16();
 	int x = argv[3].toSint16();
 	int y = argv[4].toSint16();
-	int priority = (argc > 5) ? argv[5].toSint16() : -1;
-	GfxView *new_view;
+	int priority = (argc > 5) ? argv[5].toUint16()  : -1;
+	int paletteNo = (argc > 6) ? argv[6].toSint16() : 0;
 
-	gfxop_check_cel(s->gfx_state, view, &loop, &cel);
+	s->gui->drawCell(view, loop, cel, x, y, priority, paletteNo);
 
-	debugC(2, kDebugLevelGraphics, "DrawCel((%d,%d), (view.%d, %d, %d), p=%d)\n", x, y, view, loop, cel, priority);
-
-	new_view = gfxw_new_view(s->gfx_state, Common::Point(x, y), view, loop, cel, 0, priority, -1,
-	                         ALIGN_LEFT, ALIGN_TOP, GFXW_VIEW_FLAG_DONT_MODIFY_OFFSET);
-
-	ADD_TO_CURRENT_PICTURE_PORT(new_view);
-	FULL_REDRAW();
-
 	return s->r_acc;
 }
 
 reg_t kDisposeWindow(EngineState *s, int argc, reg_t *argv) {
-	unsigned int goner_nr = argv[0].toSint16();
-	GfxPort *goner;
-	GfxPort *pred;
+	int goner_nr = argv[0].toSint16();
+	int arg2 = (argc != 2 || argv[2].toUint16() == 0 ? 0 : 1);
 
-	goner = s->visual->getPort(goner_nr);
-	if ((goner_nr < 3) || (goner == NULL)) {
-		error("Removal of invalid window %04x requested", goner_nr);
-		return s->r_acc;
-	}
-
-	if (s->dyn_views && (GfxContainer *)s->dyn_views->_parent == (GfxContainer *)goner) {
-		reparentize_primary_widget_lists(s, (GfxPort *) goner->_parent);
-	}
-
-	if (s->drop_views && (GfxContainer *)s->drop_views->_parent == (GfxContainer *)goner)
-		s->drop_views = NULL; // Kill it
-
-	pred = gfxw_remove_port(s->visual, goner);
-
-	if (goner == s->port) // Did we kill the active port?
-		s->port = pred;
-
-	// Find the last port that exists and that isn't marked no-switch
-	int id = s->visual->_portRefs.size() - 1;
-	while (id > 0 && (!s->visual->_portRefs[id] || (s->visual->_portRefs[id]->_flags & GFXW_FLAG_NO_IMPLICIT_SWITCH)))
-		id--;
-
-	debugC(2, kDebugLevelGraphics, "Activating port %d after disposing window %d\n", id, goner_nr);
-	s->port = (id >= 0) ? s->visual->_portRefs[id] : 0;
-
-	if (!s->port)
-		s->port = gfxw_find_default_port(s->visual);
-
-	gfxop_update(s->gfx_state);
-
+	s->gui->disposeWindow(goner_nr, arg2);
 	return s->r_acc;
 }
 
 reg_t kNewWindow(EngineState *s, int argc, reg_t *argv) {
-	GfxPort *window;
-	int x, y, xl, yl, flags;
-	gfx_color_t bgcolor;
-	gfx_color_t fgcolor;
-	gfx_color_t black;
-	gfx_color_t lWhite;
-	int priority;
+	Common::Rect rect1 (argv[1].toSint16(), argv[0].toSint16(), argv[3].toSint16(), argv[2].toSint16());
+	Common::Rect rect2;
 	int argextra = argc == 13 ? 4 : 0; // Triggers in PQ3 and SCI1.1 games
+	int	style = argv[5 + argextra].toSint16();
+	int	priority = (argc > 6 + argextra) ? argv[6 + argextra].toSint16() : -1;
+	int colorPen = (argc > 7 + argextra) ? argv[7 + argextra].toSint16() : 0;
+	int colorBack = (argc > 8 + argextra) ? argv[8 + argextra].toSint16() : 255;
 
-	y = argv[0].toSint16();
-	x = argv[1].toSint16();
-	yl = argv[2].toSint16() - y;
-	xl = argv[3].toSint16() - x;
-
-	y += s->wm_port->_bounds.y;
-
-	if (x + xl > 319)
-		x -= ((x + xl) - 319);
-
-	flags = argv[5 + argextra].toSint16();
-
-	priority = (argc > 6 + argextra) ? argv[6 + argextra].toSint16() : -1;
-	bgcolor.mask = 0;
-
-	int16 bgColor = (argc > 8 + argextra) ? argv[8 + argextra].toSint16() : 255;
-
-	if (bgColor >= 0) {
-		if (!s->resMan->isVGA())
-			bgcolor.visual = get_pic_color(s, MIN<int>(bgColor, 15));
-		else
-			bgcolor.visual = get_pic_color(s, bgColor);
-		bgcolor.mask = GFX_MASK_VISUAL;
-	} else {
-		bgcolor.visual = PaletteEntry(0,0,0);
+	//	const char *title = argv[4 + argextra].segment ? kernel_dereference_char_pointer(s, argv[4 + argextra], 0) : NULL;
+	if (argc==13) {
+		rect2 = Common::Rect (argv[5].toSint16(), argv[4].toSint16(), argv[7].toSint16(), argv[6].toSint16());
 	}
 
-	bgcolor.priority = priority;
-	bgcolor.mask |= priority >= 0 ? GFX_MASK_PRIORITY : 0;
-	bgcolor.alpha = 0;
-	bgcolor.control = -1;
-	debugC(2, kDebugLevelGraphics, "New window with params %d, %d, %d, %d\n", argv[0].toSint16(), argv[1].toSint16(), argv[2].toSint16(), argv[3].toSint16());
-
-	int16 visualColor = (argc > 7 + argextra) ? argv[7 + argextra].toSint16() : 0;
-	fgcolor.visual = get_pic_color(s, visualColor);
-	fgcolor.mask = GFX_MASK_VISUAL;
-	fgcolor.control = -1;
-	fgcolor.priority = -1;
-	fgcolor.alpha = 0;
-	black.visual = get_pic_color(s, 0);
-	black.mask = GFX_MASK_VISUAL;
-	black.alpha = 0;
-	black.control = -1;
-	black.priority = -1;
-	lWhite.visual = get_pic_color(s, !s->resMan->isVGA() ? 15 : 255);
-	lWhite.mask = GFX_MASK_VISUAL;
-	lWhite.alpha = 0;
-	lWhite.priority = -1;
-	lWhite.control = -1;
 	Common::String title;
 	if (argv[4 + argextra].segment) {
 		title = s->segMan->getString(argv[4 + argextra]);
 		title = s->strSplit(title.c_str(), NULL);
 	}
 
-	window = sciw_new_window(s, gfx_rect(x, y, xl, yl), s->titlebar_port->_font, fgcolor, bgcolor,
-							s->titlebar_port->_font, lWhite, black, title.c_str(), flags);
-
-	// PQ3 and SCI1.1 games have the interpreter store underBits implicitly
-	if (argextra)
-		gfxw_port_auto_restore_background(s->visual, window, gfx_rect(argv[5].toSint16(), argv[4].toSint16() + s->wm_port->_bounds.y, argv[7].toSint16() - argv[5].toSint16(), argv[6].toSint16() - argv[4].toSint16()));
-
-	ADD_TO_WINDOW_PORT(window);
-	FULL_REDRAW();
-
-	window->draw(gfxw_point_zero);
-	gfxop_update(s->gfx_state);
-
-	s->port = window; // Set active port
-
-	return make_reg(0, window->_ID);
+	return s->gui->newWindow(rect1, rect2, style, priority, colorPen, colorBack, title.c_str());
 }
 
 #define K_ANIMATE_CENTER_OPEN_H  0 // horizontally open from center
@@ -3130,208 +2853,21 @@
 	return s->r_acc;
 }
 
-#define K_DISPLAY_SET_COORDS 100
-#define K_DISPLAY_SET_ALIGNMENT 101
-#define K_DISPLAY_SET_COLOR 102
-#define K_DISPLAY_SET_BGCOLOR 103
-#define K_DISPLAY_SET_GRAYTEXT 104
-#define K_DISPLAY_SET_FONT 105
-#define K_DISPLAY_WIDTH 106
-#define K_DISPLAY_SAVE_UNDER 107
-#define K_DISPLAY_RESTORE_UNDER 108
-#define K_DONT_UPDATE_IMMEDIATELY 121
-
 reg_t kDisplay(EngineState *s, int argc, reg_t *argv) {
-	int argpt;
 	reg_t textp = argv[0];
 	int index = (argc > 1) ? argv[1].toUint16() : 0;
-	int temp;
-	bool save_under = false;
-	gfx_color_t transparent = { PaletteEntry(), 0, -1, -1, 0 };
+
 	Common::String text;
-	GfxPort *port = (s->port) ? s->port : s->picture_port;
-	bool update_immediately = true;
 
-	gfx_color_t color0, *color1, bg_color;
-	gfx_alignment_t halign = ALIGN_LEFT;
-	rect_t area = gfx_rect(port->draw_pos.x, port->draw_pos.y, 320 - port->draw_pos.x, 200 - port->draw_pos.y);
-	int gray = port->gray_text;
-	int font_nr = port->_font;
-	GfxText *text_handle;
-
-	color0 = port->_color;
-	bg_color = port->_bgcolor;
-	// TODO: in SCI1VGA the default colors for text and background are #0 (black)
-	// SCI0 case should be checked
-
 	if (textp.segment) {
-		argpt = 1;
+		argc--; argv++;
 		text = s->segMan->getString(textp);
 	} else {
-		argpt = 2;
+		argc--; argc--; argv++; argv++;
 		text = kernel_lookup_text(s, textp, index);
 	}
 
-#if 0
-	if (!text) {
-		error("Display with invalid reference %04x:%04x", PRINT_REG(textp));
-		return NULL_REG;
-	}
-#endif
-
-	while (argpt < argc) {
-		switch (argv[argpt++].toUint16()) {
-
-		case K_DISPLAY_SET_COORDS:
-
-			area.x = argv[argpt++].toUint16();
-			area.y = argv[argpt++].toUint16();
-			debugC(2, kDebugLevelGraphics, "Display: set_coords(%d, %d)\n", area.x, area.y);
-			break;
-
-		case K_DISPLAY_SET_ALIGNMENT:
-
-			halign = (gfx_alignment_t)argv[argpt++].toSint16();
-			debugC(2, kDebugLevelGraphics, "Display: set_align(%d)\n", halign);
-			break;
-
-		case K_DISPLAY_SET_COLOR:
-
-			temp = argv[argpt++].toSint16();
-			debugC(2, kDebugLevelGraphics, "Display: set_color(%d)\n", temp);
-			if (!s->resMan->isVGA() && temp >= 0 && temp <= 15)
-				color0 = (s->ega_colors[temp]);
-			else
-				if (s->resMan->isVGA() && temp >= 0 && temp < 256) {
-					color0.visual = get_pic_color(s, temp);
-					color0.mask = GFX_MASK_VISUAL;
-				} else
-					if (temp == -1)
-						color0 = transparent;
-					else
-						warning("Display: Attempt to set invalid fg color %d", temp);
-			break;
-
-		case K_DISPLAY_SET_BGCOLOR:
-
-			temp = argv[argpt++].toSint16();
-			debugC(2, kDebugLevelGraphics, "Display: set_bg_color(%d)\n", temp);
-			if (!s->resMan->isVGA() && temp >= 0 && temp <= 15)
-				bg_color = s->ega_colors[temp];
-			else
-				if (s->resMan->isVGA() && temp >= 0 && temp <= 256) {
-					bg_color.visual = get_pic_color(s, temp);
-					bg_color.mask = GFX_MASK_VISUAL;
-				} else
-					if (temp == -1)
-						bg_color = transparent;
-					else
-						warning("Display: Attempt to set invalid fg color %d", temp);
-			break;
-
-		case K_DISPLAY_SET_GRAYTEXT:
-
-			gray = argv[argpt++].toSint16();
-			debugC(2, kDebugLevelGraphics, "Display: set_graytext(%d)\n", gray);
-			break;
-
-		case K_DISPLAY_SET_FONT:
-
-			font_nr = argv[argpt++].toUint16();
-
-			debugC(2, kDebugLevelGraphics, "Display: set_font(\"font.%03d\")\n", font_nr);
-			break;
-
-		case K_DISPLAY_WIDTH:
-
-			area.width = argv[argpt++].toUint16();
-			if (area.width == 0)
-				area.width = MAX_TEXT_WIDTH_MAGIC_VALUE;
-
-			debugC(2, kDebugLevelGraphics, "Display: set_width(%d)\n", area.width);
-			break;
-
-		case K_DISPLAY_SAVE_UNDER:
-
-			save_under = true;
-			debugC(2, kDebugLevelGraphics, "Display: set_save_under()\n");
-			break;
-
-		case K_DISPLAY_RESTORE_UNDER:
-
-			debugC(2, kDebugLevelGraphics, "Display: restore_under(%04x)\n", argv[argpt].toUint16());
-			graph_restore_box(s, argv[argpt++]);
-			update_immediately = true;
-			argpt++;
-			return s->r_acc;
-
-		case K_DONT_UPDATE_IMMEDIATELY:
-
-			update_immediately = false;
-			debugC(2, kDebugLevelGraphics, "Display: set_dont_update()\n");
-			argpt++;
-			break;
-
-		default:
-			debugC(2, kDebugLevelGraphics, "Unknown Display() command %x\n", argv[argpt - 1].toUint16());
-			return NULL_REG;
-		}
-	}
-
-	if (halign == ALIGN_LEFT) {
-		// If the text does not fit on the screen, move it to the left and upwards until it does
-		gfxop_get_text_params(s->gfx_state, font_nr, text.c_str(), area.width, &area.width, &area.height, 0, NULL, NULL, NULL);
-
-		// Make the text fit on the screen
-		if (area.x + area.width > 320)
-			area.x += 320 - area.x - area.width; // Plus negative number = subtraction
-
-		if (area.y + area.height > 200)
-			area.y += 200 - area.y - area.height; // Plus negative number = subtraction
-	} else {
-		// If the text does not fit on the screen, clip it till it does
-		if (area.x + area.width > s->gfx_state->pic_port_bounds.width)
-			area.width = s->gfx_state->pic_port_bounds.width - area.x;
-
-		if (area.y + area.height > s->gfx_state->pic_port_bounds.height)
-			area.height = s->gfx_state->pic_port_bounds.height - area.y;
-	}
-
-	if (gray)
-		color1 = &bg_color;
-	else
-		color1 = &color0;
-
-	assert_primary_widget_lists(s);
-
-	text_handle = gfxw_new_text(s->gfx_state, area, font_nr, s->strSplit(text.c_str()).c_str(), halign, ALIGN_TOP, color0, *color1, bg_color, 0);
-
-	if (!text_handle) {
-		error("Display: Failed to create text widget");
-		return NULL_REG;
-	}
-
-	if (save_under) {    // Backup
-		rect_t save_area = text_handle->_bounds;
-		save_area.x += port->_bounds.x;
-		save_area.y += port->_bounds.y;
-
-		s->r_acc = graph_save_box(s, save_area);
-		text_handle->_serial++; // This is evil!
-
-		debugC(2, kDebugLevelGraphics, "Saving (%d, %d) size (%d, %d) as %04x:%04x\n", save_area.x, save_area.y, save_area.width, save_area.height, PRINT_REG(s->r_acc));
-	}
-
-	debugC(2, kDebugLevelGraphics, "Display: Commiting text '%s'\n", text.c_str());
-
-	//ADD_TO_CURRENT_PICTURE_PORT(text_handle);
-
-	ADD_TO_CURRENT_PICTURE_PORT(text_handle);
-	if ((!s->pic_not_valid) && update_immediately) { // Refresh if drawn to valid picture
-		FULL_REDRAW();
-		debugC(2, kDebugLevelGraphics, "Refreshing display...\n");
-	}
-
+	s->gui->display(s->strSplit(text.c_str()).c_str(), argc, argv);
 	return s->r_acc;
 }
 
@@ -3488,4 +3024,16 @@
 	return s->r_acc;
 }
 
+// New calls for SCI11. Using those is only needed when using text-codes so that one is able to change
+//  font and/or color multiple times during kDisplay and kDrawControl
+reg_t kTextFonts(EngineState *s, int argc, reg_t *argv) {
+	s->gui->textFonts(argc, argv);
+	return s->r_acc;
+}
+
+reg_t kTextColors(EngineState *s, int argc, reg_t *argv) {
+	s->gui->textColors(argc, argv);
+	return s->r_acc;
+}
+
 } // End of namespace Sci

Modified: scummvm/trunk/engines/sci/engine/kmisc.cpp
===================================================================
--- scummvm/trunk/engines/sci/engine/kmisc.cpp	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/engine/kmisc.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -131,7 +131,8 @@
 
 	switch (mode) {
 	case K_NEW_GETTIME_TICKS :
-		retval = start_time * 60 / 1000;
+		retval = s->gui->getTimeTicks();	// FIXME
+		//retval = start_time * 60 / 1000;
 		debugC(2, kDebugLevelTime, "GetTime(elapsed) returns %d", retval);
 		break;
 	case K_NEW_GETTIME_TIME_12HOUR :

Modified: scummvm/trunk/engines/sci/engine/state.h
===================================================================
--- scummvm/trunk/engines/sci/engine/state.h	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/engine/state.h	2009-10-03 20:49:18 UTC (rev 44565)
@@ -44,6 +44,7 @@
 #include "sci/engine/seg_manager.h"
 #include "sci/gfx/gfx_system.h"
 #include "sci/sfx/core.h"
+#include "sci/gui/gui.h"
 
 namespace Sci {
 
@@ -175,6 +176,8 @@
 
 	/* Non-VM information */
 
+	SciGUI *gui; /* Currently active GUI */
+
 	GfxState *gfx_state; /**< Graphics state and driver */
 	gfx_pixmap_t *old_screen; /**< Old screen content: Stored during kDrawPic() for kAnimate() */
 
@@ -319,6 +322,12 @@
  */
 PaletteEntry get_pic_color(EngineState *s, int color);
 
+/* Functions used in gui32\gui32.cpp */
+reg_t graph_save_box(EngineState *s, rect_t area);
+void graph_restore_box(EngineState *s, reg_t handle);
+void assert_primary_widget_lists(EngineState *s);
+void reparentize_primary_widget_lists(EngineState *s, GfxPort *newport);
+
 } // End of namespace Sci
 
 #endif // SCI_INCLUDE_ENGINE_H

Modified: scummvm/trunk/engines/sci/gfx/gfx_driver.cpp
===================================================================
--- scummvm/trunk/engines/sci/gfx/gfx_driver.cpp	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/gfx/gfx_driver.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -248,4 +248,19 @@
 	cursorData = 0;
 }
 
+void GfxDriver::animatePalette(int fromColor, int toColor, int stepCount) {
+	int i;
+	PaletteEntry firstColor = _mode->palette->getColor(fromColor);
+	PaletteEntry loopColor;
+	for (i=fromColor+1; i<=toColor; i++) {
+		loopColor = _mode->palette->getColor(i);
+		loopColor.r = 0;
+		loopColor.g = 0;
+		loopColor.b = 0;
+		_mode->palette->makeSystemColor(i-1, loopColor); // loopColor.r, loopColor.g, loopColor.b);
+	}
+//	_mode->palette->setColor(toColor, firstColor.r, firstColor.g, firstColor.b);
+	_mode->palette->makeSystemColor(toColor, firstColor);
+}
+
 } // End of namespace Sci

Modified: scummvm/trunk/engines/sci/gfx/gfx_driver.h
===================================================================
--- scummvm/trunk/engines/sci/gfx/gfx_driver.h	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/gfx/gfx_driver.h	2009-10-03 20:49:18 UTC (rev 44565)
@@ -228,6 +228,11 @@
 	gfx_mode_t *getMode() { return _mode; }
 	byte *getVisual0() { return _visual[0]; }
 
+	/**
+	 * Animates palette
+	 */
+	void animatePalette(int fromColor, int toColor, int stepCount);
+
 private:
 	gfx_pixmap_t *_priority[2];
 	byte *_visual[2];

Modified: scummvm/trunk/engines/sci/gfx/res_view.cpp
===================================================================
--- scummvm/trunk/engines/sci/gfx/res_view.cpp	2009-10-03 20:42:26 UTC (rev 44564)
+++ scummvm/trunk/engines/sci/gfx/res_view.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -365,6 +365,12 @@
 	return retval;
 }
 
+// SCI1:
+// [LoopCount:WORD] [MirrorMask:WORD] [??:WORD] [PaletteOffset:WORD] [LoopOffset0:WORD] [LoopOffset1:WORD]...
+// Loop-data:
+// [CellCount:WORD] [Unknown:WORD] [CellOffset0:WORD] [CellOffset1:WORD]...
+// SCI11:
+// [HeaderSize:WORD] [LoopCount:BYTE] [Unknown:BYTE] [??:WORD] [??:WORD] [PaletteOffset:WORD]
 gfxr_view_t *getVGAView(int id, byte *resource, int size, ViewType viewType) {
 	uint16 palOffset = READ_LE_UINT16(resource + V1_PALETTE_OFFSET + ((viewType == kViewVga11) ? 2 : 0));
 	uint16 headerSize = (viewType == kViewVga11) ? READ_LE_UINT16(resource + V2_HEADER_SIZE) : 0;

Added: scummvm/trunk/engines/sci/gui/gui.cpp
===================================================================
--- scummvm/trunk/engines/sci/gui/gui.cpp	                        (rev 0)
+++ scummvm/trunk/engines/sci/gui/gui.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -0,0 +1,330 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/util.h"
+
+#include "sci/sci.h"
+#include "sci/engine/state.h"
+#include "sci/tools.h"
+#include "sci/gui/gui_screen.h"
+#include "sci/gui/gui_gfx.h"
+#include "sci/gui/gui_windowmgr.h"
+#include "sci/gui/gui_memmgr.h"
+#include "sci/gui/gui_view.h"
+
+#include "sci/gfx/operations.h"
+
+namespace Sci {
+
+SciGUI::SciGUI(OSystem *system, EngineState *state)
+	: _system(system), _s(state) {
+	_screen = new SciGUIscreen(_system, _s);
+	_gfx = new SciGUIgfx(_system, _s, _screen);
+	_windowMgr = new SciGUIwindowMgr(_s, _gfx);
+}
+
+SciGUI::SciGUI() {
+}
+
+SciGUI::~SciGUI() {
+}
+
+void SciGUI::init(bool oldGfxFunctions) {
+	_usesOldGfxFunctions = oldGfxFunctions;
+
+	/* Set default SCI0 palette */
+}
+
+int16 SciGUI::getTimeTicks() {
+	return _gfx->_sysTicks;
+}
+
+void SciGUI::wait(int16 ticks) {
+	uint32 waitto = _gfx->_sysTicks + ticks;
+	do {
+		//eventMgr->pollEvents();
+		_system->delayMillis(_gfx->_sysSpeed >> 11);
+	} while (_gfx->_sysTicks < waitto);
+}
+
+void SciGUI::setPort(uint16 portPtr) {
+	switch (portPtr) {
+		case 0: _gfx->SetPort(_windowMgr->_wmgrPort); break;
+		case 0xFFFF: _gfx->SetPort(_gfx->_menuPort); break;
+		default:
+			_gfx->SetPort((sciPort *)heap2Ptr(portPtr));
+	};
+}
+
+void SciGUI::setPortPic(Common::Rect rect, int16 picTop, int16 picLeft) {
+	_windowMgr->_picWind->rect = rect;
+	_windowMgr->_picWind->top = picTop;
+	_windowMgr->_picWind->left = picLeft;
+	//if (argc >= 7)
+		//InitPri(42,190);
+}
+
+reg_t SciGUI::getPort() {
+	return make_reg(0, ptr2heap((byte *)_gfx->GetPort()));
+}
+
+void SciGUI::globalToLocal(int16 *x, int16 *y) {
+	sciPort *curPort = _gfx->GetPort();
+	*x = *x - curPort->left;
+	*y = *y - curPort->top;
+}
+
+void SciGUI::localToGlobal(int16 *x, int16 *y) {
+	sciPort *curPort = _gfx->GetPort();
+	*x = *x + curPort->left;
+	*y = *y + curPort->top;
+}
+
+reg_t SciGUI::newWindow(Common::Rect rect1, Common::Rect rect2, uint16 style, int16 priority, int16 colorPen, int16 colorBack, const char *title) {
+	sciWnd *wnd = NULL;
+
+	if (rect2.top != 0 && rect2.left != 0 && rect2.height() != 0 && rect2.width() != 0)
+		wnd = _windowMgr->NewWindow(&rect1, &rect2, "", style, priority, 0);
+	else
+		wnd = _windowMgr->NewWindow(&rect1, NULL, "", style, priority, 0);
+	wnd->penClr = colorPen;
+	wnd->backClr = colorBack;
+	_windowMgr->DrawWindow(wnd);
+	return make_reg(0, ptr2heap((byte *)wnd));
+}
+
+void SciGUI::disposeWindow(uint16 windowPtr, int16 arg2) {
+	sciWnd *wnd = (sciWnd *)heap2Ptr(windowPtr);
+	_windowMgr->DisposeWindow(wnd, arg2);
+}
+
+void SciGUI::display(const char *text, int argc, reg_t *argv) {
+	int displayArg;
+	sciPort oldPort;
+	int16 align = 0;
+	int16 bgcolor = -1, width = 0xFFFF, bRedraw = 1;
+	byte bSaveUnder = false;
+	Common::Rect rect, *orect = &((sciWnd *)_gfx->GetPort())->rect0;
+
+	memcpy(&oldPort, _gfx->GetPort(), sizeof(sciPort));
+	// setting defaults
+	_gfx->PenMode(0);
+	_gfx->PenColor(0);
+	_gfx->TextFace(0);
+	// processing codes in argv
+	while (argc > 0) {
+		displayArg = argv[0].toUint16();
+		argc--; argv++;
+		switch (displayArg - 100) {
+		case 0:
+			_gfx->MoveTo(argv[0].toUint16(), argv[1].toUint16());
+			argc -= 2; argv += 2;
+			break;// move pen
+		case 1:
+			align = argv[0].toUint16();
+			argc--; argv++;
+			break;// set alignment
+		case 2:
+			_gfx->PenColor(argv[0].toUint16());
+			argc--; argv++;
+			break;// set pen color
+		case 3:
+			bgcolor = argv[0].toUint16();
+			argc--; argv++;
+			break;
+		case 4:
+			_gfx->TextFace(argv[0].toUint16());
+			argc--; argv++;
+			break;// set text grayout flag
+		case 5:
+			_gfx->SetFont(argv[0].toUint16());
+			argc--; argv++;
+			break;// set font
+		case 6:
+			width = argv[0].toUint16();
+			argc--; argv++;
+			break;
+		case 7:
+			bSaveUnder = 1;
+			break;
+		case 8: // restore under
+//			if (hunk2Ptr(*pArgs)) {
+//				memcpy(&rect, hunk2Ptr(*pArgs), sizeof(Common::Rect));
+//				// rect is now absolute. Have to move it to be port-relative
+//				rect.translate(-_gfx->RGetPort()->left, -_gfx->RGetPort()->top);
+//				_gfx->RestoreBits(*pArgs);
+//				ReAnimate(&rect);
+//			}
+			// finishing loop
+			argc = 0;
+			break;
+		case 0x15:
+			bRedraw = 0;
+			break;
+		default:
+			warning("Unknown kDisplay argument %X", displayArg);
+			break;
+		}
+	}
+	// now drawing the text
+	_gfx->TextSize(rect, text, -1, width);
+	_gfx->Move((orect->left <= 320 ? 0 : 320 - orect->left), (orect->top <= 200 ? 0 : 200 - orect->top)); // move port to (0,0)
+	rect.moveTo(_gfx->GetPort()->curLeft, _gfx->GetPort()->curTop);
+//	if (bSaveUnder)
+//		_acc = _gfx->SaveBits(rect, 1);
+	if (bgcolor != -1)
+		_gfx->FillRect(rect, 1, bgcolor, 0, 0);
+	_gfx->TextBox(text, 0, rect, align, 0xFFFF);
+//	if (_picNotValid == 0 && bRedraw)
+//		_gfx->ShowBits(rect, 1);
+	// restoring port and cursor pos
+	sciPort *currport = _gfx->GetPort();
+	uint16 tTop = currport->curTop;
+	uint16 tLeft = currport->curLeft;
+	memcpy(currport, &oldPort, sizeof(sciPort));
+	currport->curTop = tTop;
+	currport->curLeft = tLeft;
+
+	_screen->UpdateWhole();
+}
+
+void SciGUI::textSize(const char *text, int16 font, int16 maxWidth, int16 *textWidth, int16 *textHeight) {
+	Common::Rect rect(0, 0, *textWidth, *textHeight);
+	_gfx->TextSize(rect, text, font, maxWidth);
+	*textWidth = rect.width(); *textHeight = rect.height();
+}
+
+// Used SCI1+ for text codes
+void SciGUI::textFonts(int argc, reg_t *argv) {
+}
+
+// Used SCI1+ for text codes
+void SciGUI::textColors(int argc, reg_t *argv) {
+}
+
+void SciGUI::drawPicture(sciResourceId pictureId, uint16 style, uint16 flags, int16 EGApaletteNo) {
+	bool addToFlag = flags ? true : false;
+
+	sciPort *oldPort = _gfx->SetPort((sciPort *)_windowMgr->_picWind);
+
+	if (_windowMgr->isFrontWindow(_windowMgr->_picWind)) {
+		_gfx->drawPicture(pictureId, style, addToFlag, EGApaletteNo);
+	} else {
+		_windowMgr->BeginUpdate(_windowMgr->_picWind);
+		_gfx->drawPicture(pictureId, style, addToFlag, EGApaletteNo);
+		_windowMgr->EndUpdate(_windowMgr->_picWind);
+	}
+	_screen->UpdateWhole();
+
+	_gfx->SetPort(oldPort);
+	_s->pic_not_valid = 1;
+}
+
+void SciGUI::drawCell(sciResourceId viewId, uint16 loopNo, uint16 cellNo, uint16 leftPos, uint16 topPos, int16 priority, uint16 paletteNo) {
+	_gfx->drawCell(viewId, loopNo, cellNo, leftPos, topPos, priority, paletteNo);
+	_gfx->SetCLUT(&_gfx->_sysPalette);
+	_screen->UpdateWhole();
+}
+
+void SciGUI::drawControlButton(Common::Rect rect, reg_t obj, const char *text, int16 fontId, int16 style, bool inverse) {
+	rect.grow(1);
+	_gfx->EraseRect(rect);
+	_gfx->FrameRect(rect);
+	rect.grow(-2);
+	_gfx->TextFace(style & 1 ? 0 : 1);
+	_gfx->TextBox(text, 0, rect, 1, fontId);
+	_gfx->TextFace(0);
+	if (style & 8) { // selected
+		rect.grow(1);
+		_gfx->FrameRect(rect);
+	}
+	_screen->UpdateWhole();
+}
+
+void SciGUI::drawControlText(Common::Rect rect, reg_t obj, const char *text, int16 fontId, int16 mode, int16 style, bool inverse) {
+	rect.grow(1);
+	_gfx->EraseRect(rect);
+	rect.grow(-1);
+	_gfx->TextBox(text, 0, rect, mode, fontId);
+	if (style & 8) { // selected
+		_gfx->FrameRect(rect);
+	}
+	_screen->UpdateWhole();
+}
+
+void SciGUI::graphFillBoxForeground(Common::Rect rect) {
+	_gfx->PaintRect(rect);
+	_screen->UpdateWhole();
+}
+
+void SciGUI::graphFillBoxBackground(Common::Rect rect) {
+	_gfx->EraseRect(rect);
+	_screen->UpdateWhole();
+}
+
+void SciGUI::graphFillBox(Common::Rect rect, uint16 colorMask, int16 color, int16 priority, int16 control) {
+	_gfx->FillRect(rect, colorMask, color, priority, control);
+	_screen->UpdateWhole();
+}
+
+void SciGUI::graphDrawLine(Common::Rect rect, int16 color, int16 priority, int16 control) {
+	_gfx->Draw_Line(rect.left, rect.top, rect.right, rect.bottom, color, priority, control);
+	_screen->UpdateWhole();
+}
+
+reg_t SciGUI::graphSaveBox(Common::Rect rect, uint16 flags) {
+	return _gfx->SaveBits(rect, flags);
+}
+
+void SciGUI::graphRestoreBox(reg_t handle) {
+	_gfx->RestoreBits(handle);
+	_screen->UpdateWhole();
+}
+
+void SciGUI::paletteSet(int resourceNo, int flags) {
+   _gfx->SetResPalette(resourceNo, flags);
+}
+
+int16 SciGUI::paletteFind(int r, int g, int b) {
+	return _gfx->MatchColor(&_gfx->_sysPalette, r, g, b) & 0xFF;
+}
+
+void SciGUI::paletteAnimate(int fromColor, int toColor, int speed) {
+	_gfx->animatePalette(fromColor, toColor, speed);
+}
+
+void SciGUI::moveCursor(int16 x, int16 y) {
+	Common::Point newPos;
+	sciPort *curPort = _gfx->GetPort();
+	
+	x += _windowMgr->_picWind->rect.left;
+	y += _windowMgr->_picWind->rect.top;
+	newPos.x = CLIP<int16> (x, _windowMgr->_picWind->rect.left, _windowMgr->_picWind->rect.right - 1);
+	newPos.y = CLIP<int16> (y, _windowMgr->_picWind->rect.top, _windowMgr->_picWind->rect.bottom - 1);
+
+	gfxop_set_pointer_position(_s->gfx_state, newPos);
+}
+
+} // End of namespace Sci


Property changes on: scummvm/trunk/engines/sci/gui/gui.cpp
___________________________________________________________________
Added: svn:mime-type
   + text/plain
Added: svn:eol-style
   + native

Added: scummvm/trunk/engines/sci/gui/gui.h
===================================================================
--- scummvm/trunk/engines/sci/gui/gui.h	                        (rev 0)
+++ scummvm/trunk/engines/sci/gui/gui.h	2009-10-03 20:49:18 UTC (rev 44565)
@@ -0,0 +1,86 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "sci/gui/gui_helpers.h"
+
+namespace Sci {
+
+class SciGUIscreen;
+class SciGUIgfx;
+class SciGUIresources;
+class SciGUIwindowMgr;
+class SciGUI {
+public:
+	SciGUI(OSystem *system, EngineState *s);
+	SciGUI();
+	~SciGUI();
+
+	virtual void init(bool oldGfxFunctions);
+
+	virtual int16 getTimeTicks();
+	virtual void wait(int16 ticks);
+	virtual void setPort(uint16 portPtr);
+	virtual void setPortPic(Common::Rect rect, int16 picTop, int16 picLeft);
+	virtual reg_t getPort();
+	virtual void globalToLocal(int16 *x, int16 *y);
+	virtual void localToGlobal(int16 *x, int16 *y);
+	virtual reg_t newWindow(Common::Rect rect1, Common::Rect rect2, uint16 style, int16 priority, int16 colorPen, int16 colorBack, const char *title);
+	virtual void disposeWindow(uint16 windowPtr, int16 arg2);
+
+	virtual void display(const char *text, int argc, reg_t *argv);
+
+	virtual void textSize(const char *text, int16 font, int16 maxWidth, int16 *textWidth, int16 *textHeight);
+	virtual void textFonts(int argc, reg_t *argv);
+	virtual void textColors(int argc, reg_t *argv);
+
+	virtual void drawPicture(sciResourceId pictureId, uint16 showStyle, uint16 flags, int16 EGApaletteNo);
+	virtual void drawCell(sciResourceId viewId, uint16 loopNo, uint16 cellNo, uint16 leftPos, uint16 topPos, int16 priority, uint16 paletteNo);
+	virtual void drawControlButton(Common::Rect rect, reg_t obj, const char *text, int16 fontId, int16 style, bool inverse);
+	virtual void drawControlText(Common::Rect rect, reg_t obj, const char *text, int16 fontId, int16 mode, int16 style, bool inverse);
+
+	virtual void graphFillBoxForeground(Common::Rect rect);
+	virtual void graphFillBoxBackground(Common::Rect rect);
+	virtual void graphFillBox(Common::Rect rect, uint16 colorMask, int16 color, int16 priority, int16 control);
+	virtual void graphDrawLine(Common::Rect rect, int16 color, int16 priority, int16 control);
+	virtual reg_t graphSaveBox(Common::Rect rect, uint16 flags);
+	virtual void graphRestoreBox(reg_t handle);
+
+	virtual void paletteSet(int resourceNo, int flags);
+	virtual int16 paletteFind(int r, int g, int b);
+	virtual void paletteAnimate(int fromColor, int toColor, int speed);
+
+	virtual void moveCursor(int16 x, int16 y);
+
+private:
+	OSystem *_system;
+	EngineState *_s;
+	SciGUIscreen *_screen;
+	SciGUIgfx *_gfx;
+	SciGUIresources *_resources;
+	SciGUIwindowMgr *_windowMgr;
+	bool _usesOldGfxFunctions;
+};
+
+} // End of namespace Sci


Property changes on: scummvm/trunk/engines/sci/gui/gui.h
___________________________________________________________________
Added: svn:mime-type
   + text/plain
Added: svn:eol-style
   + native

Added: scummvm/trunk/engines/sci/gui/gui_dbllist.cpp
===================================================================
--- scummvm/trunk/engines/sci/gui/gui_dbllist.cpp	                        (rev 0)
+++ scummvm/trunk/engines/sci/gui/gui_dbllist.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -0,0 +1,257 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/util.h"
+
+#include "sci/sci.h"
+#include "sci/gui/gui_helpers.h"
+#include "sci/gui/gui_memmgr.h"
+#include "sci/gui/gui_dbllist.h"
+
+namespace Sci {
+
+DblList::DblList() {
+	_hFirst = 0;
+	_hLast = 0;
+}
+
+DblList::DblList(HEAPHANDLE heap) {
+	byte *ptr = heap2Ptr(heap);
+	_hFirst = READ_UINT16(ptr);
+	_hLast = READ_UINT16(ptr + 2);
+}
+
+DblList::~DblList(void) {
+}
+//--------------------------------------
+// Prints all list contents
+void DblList::Dump(char*caption) {
+	debug("DumpList %s:", caption);
+	debug("  First: %04X Last: %04X", _hFirst, _hLast);
+	HEAPHANDLE node = _hFirst;
+	while (node) {
+		sciNode *pNode = (sciNode *)heap2Ptr(node);
+		debug("  %04X key=%04X prev=%04X next=%04X add.data=%db", node,
+				pNode->key, pNode->prev, pNode->next, heapGetDataSize(node) - 6);
+		node = pNode->next;
+	}
+	debug("End of list");
+}
+//--------------------------------------
+// Add a new node to front of the list
+HEAPHANDLE DblList::AddToFront(HEAPHANDLE node, uint16 key) {
+	if (!node) {
+		warning("Bad node handler (%04X) passed to DblList::AddToFront !",
+				node);
+		return node;
+	}
+	sciNode *pNode = (sciNode *)heap2Ptr(node);
+	pNode->key = key;
+	if (_hFirst) { // we already have  a 1st node
+		sciNode *pnext = (sciNode *)heap2Ptr(_hFirst);
+		pnext->prev = node;
+		pNode->next = _hFirst;
+	} else { // list is empty, to passed node becames 1st one
+		_hLast = node;
+		pNode->next = 0;
+	}
+	_hFirst = node;
+	pNode->prev = 0;
+	return node;
+}
+
+//-------------------------------------
+//
+HEAPHANDLE DblList::AddToEnd(HEAPHANDLE node, uint16 key) {
+	if (!node) {
+		warning("Bad node handler (%04X) passed to DblList::AddToEnd !", node);
+		return node;
+	}
+	sciNode *pNode = (sciNode *)heap2Ptr(node);
+	if (_hFirst) { // list is not empty
+		sciNode *plast = (sciNode *)heap2Ptr(_hLast);
+		plast->next = node;
+		pNode->prev = _hLast;
+	} else { // list is empty, so the node becames 1st one
+		_hFirst = node;
+		pNode->prev = 0;
+	}
+	_hLast = node;
+	pNode->next = 0;
+	pNode->key = key;
+
+	return node;
+}
+
+//------------------------------------------------
+// returns node that contains the key
+HEAPHANDLE DblList::FindKey(uint16 key) {
+	HEAPHANDLE node = _hFirst;
+	while (node) {
+		sciNode *pNode = (sciNode *)heap2Ptr(node);
+		if (pNode->key == key)
+			break;
+		node = pNode->next;
+	}
+	return node;
+}
+//------------------------------------------------
+// detaches node with specified key and returning the node
+HEAPHANDLE DblList::DeleteKey(uint16 key) {
+	HEAPHANDLE node = FindKey(key);
+	if (node)
+		DeleteNode(node);
+	return node;
+}
+//------------------------------------------------
+// detaches specified node from list
+byte DblList::DeleteNode(HEAPHANDLE node) {
+	if (!node) {
+		warning("Bad node handler (%04X) passed to DblList::AddToEnd !", node);
+		return node;
+	}
+	// updating the links
+	sciNode *pNode = (sciNode *)heap2Ptr(node);
+	if (pNode->prev) {
+		sciNode *pprev = (sciNode *)heap2Ptr(pNode->prev);
+		pprev->next = pNode->next;
+	}
+	if (pNode->next) {
+		sciNode *pnext = (sciNode *)heap2Ptr(pNode->next);
+		pnext->prev = pNode->prev;
+	}
+	// updating list head if needed
+	if (_hFirst == node)
+		_hFirst = pNode->next;
+	if (_hLast == node)
+		_hLast = pNode->prev;
+	pNode->prev = 0;
+	pNode->next = 0;
+	return 1;
+}
+//------------------------------------------------
+// Moves node to the end of the list
+HEAPHANDLE DblList::MoveToEnd(HEAPHANDLE node) {
+	if (!node) {
+		warning("Bad node handler (%04X) passed to DblList::MoveToEnd !", node);
+		return node;
+	}
+	sciNode *pNode = (sciNode *)heap2Ptr(node);
+	if (pNode->next) { // node is not the last one in list
+		DeleteNode(node);
+		AddToEnd(node, pNode->key);
+	}
+	return node;
+}
+//------------------------------------------------
+// Moves node to the front of the list
+HEAPHANDLE DblList::MoveToFront(HEAPHANDLE node) {
+	if (!node) {
+		warning("Bad node handler (%04X) passed to DblList::MoveToFront !",
+				node);
+		return node;
+	}
+	sciNode *pNode = (sciNode *)heap2Ptr(node);
+	if (pNode->prev) { // node is not 1st one in list
+		DeleteNode(node);
+		AddToFront(node, pNode->key);
+	}
+	return node;
+}
+//------------------------------------------------
+HEAPHANDLE DblList::AddAfter(HEAPHANDLE ref, HEAPHANDLE node, uint16 key) {
+	if (!node) {
+		warning("Bad node handler (%04X) passed to DblList::AddAfter !", node);
+		return node;
+	}
+	sciNode *pNode = (sciNode *)heap2Ptr(node);
+	sciNode *pref = (sciNode *)heap2Ptr(ref);
+	pNode->key = key;
+	if (pref->next == 0) { // ref node is the last one
+		pNode->next = 0;
+		_hLast = node;
+	} else {
+		sciNode *pnext = (sciNode *)heap2Ptr(pref->next);
+		pNode->next = pref->next;
+		pnext->prev = node;
+	}
+	pref->next = node;
+	pNode->prev = ref;
+	return node;
+}
+//------------------------------------------------
+//
+HEAPHANDLE DblList::AddBefore(HEAPHANDLE ref, HEAPHANDLE node, uint16 key) {
+	if (!node) {
+		warning("Bad node handler (%04X) passed to DblList::AddBefore !", node);
+		return node;
+	}
+	sciNode *pNode = (sciNode *)heap2Ptr(node);
+	sciNode *pref = (sciNode *)heap2Ptr(ref);
+	pNode->key = key;
+	if (pref->prev == 0) { // ref node is the 1st one
+		pNode->prev = 0;
+		_hFirst = node;
+	} else {
+		sciNode*pprev = (sciNode *)heap2Ptr(pref->prev);
+		pNode->prev = pref->prev;
+		pprev->next = node;
+	}
+	pref->prev = node;
+	pNode->next = ref;
+	return node;
+}
+//------------------------------------------------
+void DblList::toHeap(HEAPHANDLE heap) {
+	byte *ptr = heap2Ptr(heap);
+	WRITE_UINT16(ptr, _hFirst);
+	WRITE_UINT16(ptr + 2, _hLast);
+}
+//------------------------------------------------
+void DblList::DeleteList() {
+	HEAPHANDLE node = getFirst(), next;
+	sciNode *pNode;
+	while (node) {
+		pNode = (sciNode *)heap2Ptr(node);
+		next = pNode->next;
+		heapDisposePtr(node);
+		node = next;
+	}
+	_hFirst = _hLast = 0;
+}
+//------------------------------------------------
+uint16 DblList::getSize() {
+	uint16 cnt = 0;
+	HEAPHANDLE node = getFirst();
+	sciNode *pNode;
+	while (node) {
+		pNode = (sciNode *)heap2Ptr(node);
+		node = pNode->next;
+		cnt++;
+	}
+	return cnt;
+}
+//------------------------------------------------
+} // end of namespace


Property changes on: scummvm/trunk/engines/sci/gui/gui_dbllist.cpp
___________________________________________________________________
Added: svn:mime-type
   + text/plain
Added: svn:eol-style
   + native

Added: scummvm/trunk/engines/sci/gui/gui_dbllist.h
===================================================================
--- scummvm/trunk/engines/sci/gui/gui_dbllist.h	                        (rev 0)
+++ scummvm/trunk/engines/sci/gui/gui_dbllist.h	2009-10-03 20:49:18 UTC (rev 44565)
@@ -0,0 +1,74 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+/*
+ Each node contains handles to next and previous node and an optional key for searching
+ Head node contains handles to first and last node
+ */
+
+namespace Sci {
+
+typedef uint16 HEAPHANDLE;
+
+class DblList {
+public:
+	DblList();
+	DblList(HEAPHANDLE heap);
+	~DblList(void);
+protected:
+	HEAPHANDLE _hFirst, _hLast;
+public:
+	// Add a new node to front of the list
+	HEAPHANDLE AddToFront(HEAPHANDLE node, uint16 key = 0);
+	HEAPHANDLE AddToEnd(HEAPHANDLE node, uint16 key = 0);
+	HEAPHANDLE MoveToEnd(HEAPHANDLE node);
+	HEAPHANDLE MoveToFront(HEAPHANDLE node);
+	HEAPHANDLE AddAfter(HEAPHANDLE ref, HEAPHANDLE node, uint16 key = 0);
+	HEAPHANDLE AddBefore(HEAPHANDLE ref, HEAPHANDLE node, uint16 key = 0);
+
+	HEAPHANDLE FindKey(uint16 key);
+	HEAPHANDLE DeleteKey(uint16 key);
+	byte DeleteNode(HEAPHANDLE node);
+	void DeleteList();
+	void Dump(char*caption = ""); // for debug
+	HEAPHANDLE getFirst() {
+		return _hFirst;
+	}
+	HEAPHANDLE getLast() {
+		return _hLast;
+	}
+	void toHeap(HEAPHANDLE heap);
+	bool isEmpty() {
+		return (_hFirst == 0 && _hLast == 0);
+	}
+	uint16 getSize();
+	void set(HEAPHANDLE first, HEAPHANDLE last){
+		_hFirst = first;
+		_hLast = last;
+	}
+
+};
+
+} // end of namespace


Property changes on: scummvm/trunk/engines/sci/gui/gui_dbllist.h
___________________________________________________________________
Added: svn:mime-type
   + text/plain
Added: svn:eol-style
   + native

Added: scummvm/trunk/engines/sci/gui/gui_font.cpp
===================================================================
--- scummvm/trunk/engines/sci/gui/gui_font.cpp	                        (rev 0)
+++ scummvm/trunk/engines/sci/gui/gui_font.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -0,0 +1,100 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "sci/sci.h"
+#include "sci/engine/state.h"
+#include "sci/tools.h"
+#include "sci/gui/gui_screen.h"
+#include "sci/gui/gui_font.h"
+
+namespace Sci {
+
+SciGUIfont::SciGUIfont(OSystem *system, EngineState *state, SciGUIscreen *screen, sciResourceId resourceId)
+	: _system(system), _s(state), _screen(screen), _resourceId(resourceId) {
+	assert(resourceId != -1);
+	initData(resourceId);
+}
+
+SciGUIfont::~SciGUIfont() {
+}
+
+void SciGUIfont::initData(sciResourceId resourceId) {
+	Resource *fontResource = _s->resMan->findResource(ResourceId(kResourceTypeFont, resourceId), false);
+	if (!fontResource) {
+		error("font resource %d not found", resourceId);
+	}
+	_resourceData = fontResource->data;
+
+	mCharMax = READ_LE_UINT16(_resourceData + 2);
+	mFontH = READ_LE_UINT16(_resourceData + 4);
+	mChars = new charinfo[mCharMax];
+	// filling info for every char
+	for (int16 i = 0; i < mCharMax; i++) {
+		mChars[i].offset = READ_LE_UINT16(_resourceData + 6 + i * 2);
+		mChars[i].w = _resourceData[mChars[i].offset];
+		mChars[i].h = _resourceData[mChars[i].offset + 1];
+	}
+}
+
+sciResourceId SciGUIfont::getResourceId() {
+	return _resourceId;
+}
+
+byte SciGUIfont::getHeight() {
+	return mFontH;
+}
+byte SciGUIfont::getCharWidth(byte chr) {
+	return chr < mCharMax ? mChars[chr].w : 0;
+}
+byte SciGUIfont::getCharHeight(byte chr) {
+	return chr < mCharMax ? mChars[chr].h : 0;
+}
+byte *SciGUIfont::getCharData(byte chr) {
+	return chr < mCharMax ? _resourceData + mChars[chr].offset + 2 : 0;
+}
+
+void SciGUIfont::draw(int16 chr, int16 top, int16 left, byte color, byte textface) {
+	int charWidth = MIN<int>(getCharWidth(chr), _screen->_width - left);
+	int charHeight = MIN<int>(getCharHeight(chr), 200 - top);
+	byte b = 0, mask = 0xFF;
+	int pitch = _screen->_width;
+	int y = top;
+
+	byte *pIn = getCharData(chr);
+	for (int i = 0; i < charHeight; i++, y++) {
+		if (textface & 1) // "grayed" output
+			mask = top++ % 2 ? 0xAA : 0x55;
+		for (int done = 0; done < charWidth; done++) {
+			if ((done & 7) == 0) // fetching next data byte
+				b = *(pIn++) & mask;
+			if (b & 0x80) // if MSB is set - paint it
+				_screen->Put_Pixel(left + done, y, 1, color, 0, 0);
+			b = b << 1;
+		}
+	}
+
+}
+
+} // end of namespace Sci


Property changes on: scummvm/trunk/engines/sci/gui/gui_font.cpp
___________________________________________________________________
Added: svn:mime-type
   + text/plain
Added: svn:eol-style
   + native

Added: scummvm/trunk/engines/sci/gui/gui_font.h
===================================================================
--- scummvm/trunk/engines/sci/gui/gui_font.h	                        (rev 0)
+++ scummvm/trunk/engines/sci/gui/gui_font.h	2009-10-03 20:49:18 UTC (rev 44565)
@@ -0,0 +1,59 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+namespace Sci {
+
+class SciGUIfont {
+public:
+	SciGUIfont(OSystem *system, EngineState *state, SciGUIscreen *screen, sciResourceId resourceId);
+	~SciGUIfont();
+
+	sciResourceId getResourceId();
+	byte getHeight();
+	byte getCharWidth(byte chr);
+	byte getCharHeight(byte chr);
+	byte *getCharData(byte chr);
+	void draw(int16 chr, int16 top, int16 left, byte color, byte textface);
+
+private:
+	void initData(sciResourceId resourceId);
+
+	OSystem *_system;
+	EngineState *_s;
+	SciGUIscreen *_screen;
+
+	sciResourceId _resourceId;
+	byte *_resourceData;
+
+	struct charinfo {
+		byte w, h;
+		int16 offset;
+	};
+	byte mFontH;
+	uint16 mCharMax;
+	charinfo* mChars;
+};
+
+} // end of namespace Sci


Property changes on: scummvm/trunk/engines/sci/gui/gui_font.h
___________________________________________________________________
Added: svn:mime-type
   + text/plain
Added: svn:eol-style
   + native

Added: scummvm/trunk/engines/sci/gui/gui_gfx.cpp
===================================================================
--- scummvm/trunk/engines/sci/gui/gui_gfx.cpp	                        (rev 0)
+++ scummvm/trunk/engines/sci/gui/gui_gfx.cpp	2009-10-03 20:49:18 UTC (rev 44565)
@@ -0,0 +1,1194 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/timer.h"
+#include "common/util.h"
+
+#include "sci/sci.h"
+#include "sci/engine/state.h"
+#include "sci/tools.h"
+#include "sci/gui/gui_font.h"
+#include "sci/gui/gui_picture.h"
+#include "sci/gui/gui_view.h"
+#include "sci/gui/gui_screen.h"
+#include "sci/gui/gui_gfx.h"
+
+namespace Sci {
+
+static uint32 _sysTicks;
+
+SciGUIgfx::SciGUIgfx(OSystem *system, EngineState *state, SciGUIscreen *screen)
+	: _system(system), _s(state), _screen(screen) {
+	init();
+	initPalette();
+	initTimer();
+}
+
+SciGUIgfx::~SciGUIgfx() {
+	_system->getTimerManager()->removeTimerProc(&timerHandler);
+}
+
+void SciGUIgfx::init() {
+	uint16 a = 0;
+
+	_font = NULL;
+
+	_mainPort = mallocPort();
+	SetPort(_mainPort);
+	OpenPort(_mainPort);
+
+	_menuPort = mallocPort();
+	OpenPort(_menuPort);
+	SetFont(0);
+	_menuPort->rect = Common::Rect(0, 0, _screen->_width, _screen->_height);
+
+//	HEAPHANDLE theMenuBarH = heapNewPtr(34, kDataPort, "MenuBar");
+//	heapClearPtr(theMenuBarH);
+//	_theMenuBar = (Common::Rect *)heap2Ptr(theMenuBarH);
+//	*_theMenuBar = Common::Rect(_gfx->RGetPort()->rect.right, 10);
+
+	_sysTicks = 0;
+}
+
+void SciGUIgfx::initPalette() {
+	int16 i;
+	for (i = 0; i < 256; i++) {
+		_sysPalette.colors[i].used = 0;
+		_sysPalette.colors[i].r = 0;
+		_sysPalette.colors[i].g = 0;
+		_sysPalette.colors[i].b = 0;
+		_sysPalette.intencity[i] = 100;
+		_sysPalette.mapping[i] = i;
+	}
+	_sysPalette.colors[0].used = 1;
+	_sysPalette.colors[255].used = 1;
+	_sysPalette.colors[255].r = 255;
+	_sysPalette.colors[255].g = 255;
+	_sysPalette.colors[255].b = 255;
+	//if (g_sci->getPlatform() == Common::kPlatformAmiga)
+	//	setAmigaPalette();
+	//else 
+
+	// Load default palette from resource 999
+	if (!SetResPalette(999, 2)) {
+		// if not found, we set EGA palette
+		SetEGApalette();
+	};
+
+	// Init _clrPowers used in MatchColor
+	for(int16 i = 0; i < 256; i++)
+	  _clrPowers[i] = i*i;
+}
+
+void SciGUIgfx::initTimer() {
+	_sysSpeed = 1000000 / 60;
+	Common::TimerManager *tm = _system->getTimerManager();
+	tm->removeTimerProc(&timerHandler);
+	tm->installTimerProc(&timerHandler, _sysSpeed, this);
+}
+
+void SciGUIgfx::timerHandler(void *ref) {
+	((SciGUIgfx *)ref)->_sysTicks++;
+}
+
+sciPort *SciGUIgfx::mallocPort () {
+	sciPort *newPort = (sciPort *)malloc(sizeof(sciPort));
+	assert(newPort);
+	memset(newPort, 0, sizeof(sciPort));
+	return newPort;
+}
+
+#define SCI_PAL_FORMAT_CONSTANT 1
+#define SCI_PAL_FORMAT_VARIABLE 0
+
+void SciGUIgfx::SetEGApalette() {
+	int i;
+	_sysPalette.colors[1].r  = 0x000; _sysPalette.colors[1].g  = 0x000; _sysPalette.colors[1].b  = 0x0AA;
+	_sysPalette.colors[2].r  = 0x000; _sysPalette.colors[2].g  = 0x0AA; _sysPalette.colors[2].b  = 0x000;
+	_sysPalette.colors[3].r  = 0x000; _sysPalette.colors[3].g  = 0x0AA; _sysPalette.colors[3].b  = 0x0AA;
+	_sysPalette.colors[4].r  = 0x0AA; _sysPalette.colors[4].g  = 0x000; _sysPalette.colors[4].b  = 0x000;
+	_sysPalette.colors[5].r  = 0x0AA; _sysPalette.colors[5].g  = 0x000; _sysPalette.colors[5].b  = 0x0AA;
+	_sysPalette.colors[6].r  = 0x0AA; _sysPalette.colors[6].g  = 0x055; _sysPalette.colors[6].b  = 0x000;
+	_sysPalette.colors[7].r  = 0x0AA; _sysPalette.colors[7].g  = 0x0AA; _sysPalette.colors[7].b  = 0x0AA;
+	_sysPalette.colors[8].r  = 0x055; _sysPalette.colors[8].g  = 0x055; _sysPalette.colors[8].b  = 0x055;
+	_sysPalette.colors[9].r  = 0x055; _sysPalette.colors[9].g  = 0x055; _sysPalette.colors[9].b  = 0x0FF;
+	_sysPalette.colors[10].r = 0x055; _sysPalette.colors[10].g = 0x0FF; _sysPalette.colors[10].b = 0x055;
+	_sysPalette.colors[11].r = 0x055; _sysPalette.colors[11].g = 0x0FF; _sysPalette.colors[11].b = 0x0FF;
+	_sysPalette.colors[12].r = 0x0FF; _sysPalette.colors[12].g = 0x055; _sysPalette.colors[12].b = 0x055;
+	_sysPalette.colors[13].r = 0x0FF; _sysPalette.colors[13].g = 0x055; _sysPalette.colors[13].b = 0x0FF;
+	_sysPalette.colors[14].r = 0x0FF; _sysPalette.colors[14].g = 0x0FF; _sysPalette.colors[14].b = 0x055;
+	_sysPalette.colors[15].r = 0x0FF; _sysPalette.colors[15].g = 0x0FF; _sysPalette.colors[15].b = 0x0FF;
+	for (i = 0; i <= 15; i++) {
+		_sysPalette.colors[i].used = 1;
+	}
+	for (i = 16; i <= 254; i++) {
+		_sysPalette.colors[i].r = 200;
+		_sysPalette.colors[i].used = 1;
+	}
+	SetCLUT(&_sysPalette);
+}
+
+void SciGUIgfx::CreatePaletteFromData(byte *data, sciPalette *paletteOut) {
+	int palFormat = 0;
+	int palOffset = 0;
+	int palColorStart = 0;
+	int palColorCount = 0;
+	int colorNo = 0;
+
+	memset(paletteOut, 0, sizeof(sciPalette));
+	if (data[0] == 0 && data[1] == 1) {
+		// SCI0/SCI1 palette
+		palFormat = SCI_PAL_FORMAT_VARIABLE; // CONSTANT;
+		palOffset = 260;
+		palColorStart = 0; palColorCount = 256;
+	} else {
+		// SCI1.1 palette
+		palFormat = data[32];
+		palOffset = 37;
+		palColorStart = READ_LE_UINT16(data + 25); palColorCount = READ_LE_UINT16(data + 29);
+	}
+	switch (palFormat) {
+		case SCI_PAL_FORMAT_CONSTANT:
+			for (colorNo = palColorStart; colorNo < palColorStart + palColorCount; colorNo++) {
+				paletteOut->colors[colorNo].used = 1;
+				paletteOut->colors[colorNo].r = data[palOffset++];
+				paletteOut->colors[colorNo].g = data[palOffset++];
+				paletteOut->colors[colorNo].b = data[palOffset++];
+			}
+			break;
+		case SCI_PAL_FORMAT_VARIABLE:
+			for (colorNo = palColorStart; colorNo < palColorStart + palColorCount; colorNo++) {
+				paletteOut->colors[colorNo].used = data[palOffset++];
+				paletteOut->colors[colorNo].r = data[palOffset++];
+				paletteOut->colors[colorNo].g = data[palOffset++];
+				paletteOut->colors[colorNo].b = data[palOffset++];
+			}
+			break;
+	}
+}
+
+bool SciGUIgfx::SetResPalette(int16 resourceNo, int16 flag) {
+	Resource *palResource = _s->resMan->findResource(ResourceId(kResourceTypePalette, resourceNo), 0);
+	int palFormat = 0;
+	int palOffset = 0;
+	int palColorStart = 0;
+	int palColorCount = 0;
+	int colorNo = 0;
+	sciPalette palette = {0};
+
+	if (palResource) {
+		CreatePaletteFromData(palResource->data, &palette);
+		SetPalette(&palette, 2);
+		return true;
+	}
+	return false;
+}
+
+void SciGUIgfx::SetPalette(sciPalette *sciPal, int16 flag) {
+	uint32 systime = _sysPalette.timestamp;
+	if (flag == 2 || sciPal->timestamp != systime) {
+		MergePalettes(sciPal, &_sysPalette, flag);
+		sciPal->timestamp = _sysPalette.timestamp;
+		if (_s->pic_not_valid == 0 && systime != _sysPalette.timestamp)
+			SetCLUT(&_sysPalette);
+	}
+}
+
+void SciGUIgfx::MergePalettes(sciPalette *pFrom, sciPalette *pTo, uint16 flag) {
+	uint16 res;
+	int i,j;
+	// colors 0 (black) and 255 (white) are not affected by merging
+	for (i = 1 ; i < 255; i++) {
+		if (!pFrom->colors[i].used)// color is not used - so skip it
+			continue;
+		// forced palette merging or dest color is not used yet
+		if (flag == 2 || (!pTo->colors[i].used)) { 
+			pTo->colors[i].used = pFrom->colors[i].used;
+			pTo->colors[i].r = pFrom->colors[i].r;
+			pTo->colors[i].g = pFrom->colors[i].g;
+			pTo->colors[i].b = pFrom->colors[i].b;
+			pFrom->mapping[i] = i;
+			continue;
+		}
+		// check if exact color could be matched
+		res = MatchColor(pTo, pFrom->colors[i].r, pFrom->colors[i].g, pFrom->colors[i].b);
+		if (res & 0x8000) { // exact match was found
+			pFrom->mapping[i] = res & 0xFF;
+			continue;
+		}
+		// no exact match - see if there is an unused color
+		for (j = 1; j < 256; j++)
+			if (!pTo->colors[j].used) {
+				pTo->colors[j].used = pFrom->colors[i].used;
+				pTo->colors[j].r = pFrom->colors[i].r;
+				pTo->colors[j].g = pFrom->colors[i].g;
+				pTo->colors[j].b = pFrom->colors[i].b;
+				pFrom->mapping[i] = j;
+				break;
+			}
+		// if still no luck - set an approximate color
+		if (j == 256) {
+			pFrom->mapping[i] = res & 0xFF;
+			pTo->colors[res & 0xFF].used |= 0x10;
+		}
+	}
+	pTo->timestamp = _sysTicks;
+}
+
+uint16 SciGUIgfx::MatchColor(sciPalette*pPal, byte r, byte g, byte b) {
+	byte found = 0xFF;
+	int diff = 0x2FFFF, cdiff;
+	int16 dr,dg,db;
+
+	for (int i = 0; i < 256; i++) {
+		if ((!pPal->colors[i].used))
+			continue;
+		dr = pPal->colors[i].r - r;
+		dg = pPal->colors[i].g - g;
+		db = pPal->colors[i].b - b;
+//		minimum squares match
+		cdiff = _clrPowers[ABS(dr)] + _clrPowers[ABS(dg)] + _clrPowers[ABS(db)];
+//		minimum sum match (Sierra's)
+//		cdiff = ABS(dr) + ABS(dg) + ABS(db);
+		if (cdiff < diff) {
+			if (cdiff == 0)
+				return i | 0x8000; // setting this flag to indicate exact match
+			found = i;
+			diff = cdiff;
+		}
+	}
+	return found;
+}
+
+void SciGUIgfx::SetCLUT(sciPalette*pal) {
+	if (pal != &_sysPalette)
+		memcpy(&_sysPalette,pal,sizeof(sciPalette));
+	// just copy palette to system
+	byte bpal[4 * 256];
+	// Get current palette, update it and put back
+	_system->grabPalette(bpal, 0, 256);
+	for (int16 i = 0; i < 256; i++) {
+		if (!pal->colors[i].used)
+			continue;
+		bpal[i * 4] = pal->colors[i].r * pal->intencity[i] / 100;
+		bpal[i * 4 + 1] = pal->colors[i].g * pal->intencity[i] / 100;
+		bpal[i * 4 + 2] = pal->colors[i].b * pal->intencity[i] / 100;
+		bpal[i * 4 + 3] = 100;
+	}
+	_system->setPalette(bpal, 0, 256);
+	_system->updateScreen();
+}
+
+void SciGUIgfx::GetCLUT(sciPalette*pal) {
+	if (pal != &_sysPalette)
+		memcpy(pal,&_sysPalette,sizeof(sciPalette));
+}
+
+sciPort *SciGUIgfx::SetPort(sciPort *newPort) {
+	sciPort *oldPort = _curPort;
+	_curPort = newPort;
+	return oldPort;
+}
+
+sciPort *SciGUIgfx::GetPort(void) {
+	return _curPort;
+}
+
+void SciGUIgfx::SetOrigin(int16 left, int16 top) {
+	_curPort->left = left;
+	_curPort->top = top;
+}
+
+void SciGUIgfx::MoveTo(int16 left, int16 top) {
+	_curPort->curTop = top;
+	_curPort->curLeft = left;
+}
+
+void SciGUIgfx::Move(int16 left, int16 top) {
+	_curPort->curTop += top;
+	_curPort->curLeft += left;
+}
+
+int16 SciGUIgfx::GetFontId() {
+	return _curPort->fontId;
+}
+
+SciGUIfont *SciGUIgfx::GetFont() {
+	if ((_font == NULL) || (_font->getResourceId() != _curPort->fontId)) {
+		_font = new SciGUIfont(_system, _s, _screen, _curPort->fontId);
+	}
+	return _font;
+}
+
+void SciGUIgfx::SetFont(int16 fontId) {
+	if ((_font == NULL) || (_font->getResourceId() != fontId)) {
+		_font = new SciGUIfont(_system, _s, _screen, fontId);
+	}
+	_curPort->fontId = fontId;
+	_curPort->fontH = _font->getHeight();
+}
+
+void SciGUIgfx::OpenPort(sciPort *port) {
+	port->fontId = 0;
+	port->fontH = 8;
+
+	sciPort *tmp = _curPort;
+	_curPort = port;
+	SetFont(port->fontId);
+	_curPort = tmp;
+
+	port->top = 0;
+	port->left = 0;
+	port->textFace = 0;
+	port->penClr = 0;
+	port->backClr = 0xFF;
+	port->penMode = 0;
+	memcpy(&port->rect, &_bounds, sizeof(_bounds));
+}
+
+void SciGUIgfx::PenColor(int16 color) {
+	_curPort->penClr = color;
+}
+
+void SciGUIgfx::PenMode(int16 mode) {
+	_curPort->penMode = mode;
+}
+
+void SciGUIgfx::TextFace(int16 textFace) {
+	_curPort->textFace = textFace;
+}
+
+int16 SciGUIgfx::GetPointSize(void) {
+	return _curPort->fontH;
+}
+
+void SciGUIgfx::ClearScreen(byte color) {
+	FillRect(_curPort->rect, SCI_SCREEN_MASK_ALL, color, 0, 0);
+}
+
+void SciGUIgfx::InvertRect(const Common::Rect &rect) {
+	int16 oldpenmode = _curPort->penMode;
+	_curPort->penMode = 2;
+	FillRect(rect, 1, _curPort->penClr, _curPort->backClr);
+	_curPort->penMode = oldpenmode;
+}
+//-----------------------------
+void SciGUIgfx::EraseRect(const Common::Rect &rect) {
+	FillRect(rect, 1, _curPort->backClr);
+}
+//-----------------------------
+void SciGUIgfx::PaintRect(const Common::Rect &rect) {
+	FillRect(rect, 1, _curPort->penClr);
+}
+
+void SciGUIgfx::FillRect(const Common::Rect &rect, int16 drawFlags, byte clrPen, byte clrBack, byte bControl) {
+	Common::Rect r(rect.left, rect.top, rect.right, rect.bottom);
+	r.clip(_curPort->rect);
+	if (r.isEmpty()) // nothing to fill
+		return;
+
+	int16 oldPenMode = _curPort->penMode;
+	OffsetRect(r);
+	int16 w = r.width();
+	int16 h = r.height();
+	int16 x, y;
+	byte curVisual;
+
+	// Doing visual first
+	if (drawFlags & SCI_SCREEN_MASK_VISUAL) {
+		if (oldPenMode == 2) { // invert mode
+			for (y = r.top; y < r.bottom; y++) {
+				for (x = r.left; x < r.right; x++) {
+					curVisual = _screen->Get_Visual(x, y);
+					if (curVisual == clrPen) {
+						_screen->Put_Pixel(x, y, 1, clrBack, 0, 0);
+					} else if (curVisual == clrBack) {
+						_screen->Put_Pixel(x, y, 1, clrPen, 0, 0);
+					}
+				}
+			}
+		} else { // just fill rect with ClrPen
+			for (y = r.top; y < r.bottom; y++) {
+				for (x = r.left; x < r.right; x++) {
+					_screen->Put_Pixel(x, y, 1, clrPen, 0, 0);
+				}
+			}
+		}
+	}
+
+	if (drawFlags < 2)
+		return;
+	drawFlags &= SCI_SCREEN_MASK_PRIORITY|SCI_SCREEN_MASK_CONTROL;
+
+	if (oldPenMode != 2) {
+		for (y = r.top; y < r.bottom; y++) {
+			for (x = r.left; x < r.right; x++) {
+				_screen->Put_Pixel(x, y, drawFlags, 0, clrBack, bControl);
+			}
+		}
+	} else {
+		for (y = r.top; y < r.bottom; y++) {
+			for (x = r.left; x < r.right; x++) {
+				_screen->Put_Pixel(x, y, drawFlags, 0, !_screen->Get_Priority(x, y), !_screen->Get_Control(x, y));
+			}
+		}
+	}
+}
+
+void SciGUIgfx::FrameRect(const Common::Rect &rect) {
+	Common::Rect r;
+	// left
+	r = rect;
+	r.right = rect.left + 1;
+	PaintRect(r);
+	// right
+	r.right = rect.right;
+	r.left = rect.right - 1;
+	PaintRect(r);
+	//top
+	r.left = rect.left;
+	r.bottom = rect.top + 1;
+	PaintRect(r);
+	//bottom
+	r.bottom = rect.bottom;
+	r.top = rect.bottom - 1;
+	PaintRect(r);
+}
+
+void SciGUIgfx::OffsetRect(Common::Rect &r) {
+	r.top += _curPort->top;
+	r.bottom += _curPort->top;
+	r.left += _curPort->left;
+	r.right += _curPort->left;
+}
+
+byte SciGUIgfx::CharHeight(int16 ch) {
+#if 0
+	CResFont *res = getResFont();
+	return res ? res->getCharH(ch) : 0;
+#endif
+	return 0;
+}
+//-----------------------------
+byte SciGUIgfx::CharWidth(int16 ch) {
+	SciGUIfont *font = GetFont();
+	return font ? font->getCharWidth(ch) : 0;
+}
+//-----------------------------
+int16 SciGUIgfx::TextWidth(const char *text, int16 from, int16 len) {
+	SciGUIfont *font = GetFont();
+	if (font) {
+		int16 width = 0;
+		for (int i = from; i < len; i++)
+			width += _font->getCharWidth(text[i]);
+		return width;
+	}
+	return 0;
+}
+//-----------------------------
+void SciGUIgfx::ClearChar(int16 chr) {
+	if (_curPort->penMode != 1)
+		return;
+	Common::Rect rect;
+	rect.top = _curPort->curTop;
+	rect.bottom = rect.top + _curPort->fontH;
+	rect.left = _curPort->curLeft;
+	rect.right = rect.left + CharWidth(chr);
+	EraseRect(rect);
+}
+//-----------------------------
+void SciGUIgfx::DrawChar(int16 chr) {
+	chr = chr & 0xFF;
+	ClearChar(chr);
+	StdChar(chr);
+	_curPort->curLeft += CharWidth(chr);
+}
+//-----------------------------
+void SciGUIgfx::StdChar(int16 chr) {
+#if 0
+	CResFont*res = getResFont();
+	if (res)
+		res->Draw(chr, _curPort->top + _curPort->curTop, _curPort->left
+				+ _curPort->curLeft, _vSeg, 320, _curPort->penClr,
+				_curPort->textFace);
+#endif
+}
+
+SCILanguage SciGUIgfx::getSCILanguage() {
+	return kLangEnglish;
+}
+
+char *SciGUIgfx::StrSplit(char *buff, const char *msg, const char *fmt) {
+	SCILanguage gameLang = getSCILanguage();
+	SCILanguage subtitleLang = kLangNone;
+	char *retval;
+//	if (_theGame.getHandle())
+		//subtitleLang = (SCILanguage)_theGame.getProperty(0x58); // subtitleLang property
+
+	if (buff == msg) {
+		char str[2000];
+		getIntlString(str, msg, fmt, gameLang, subtitleLang);
+		retval = strcpy(buff, str);
+	} else
+		retval = getIntlString(buff, msg, fmt, gameLang, subtitleLang);
+	return retval;
+}
+//--------------------------------
+// In multilanguage game the msg has format ___english_text__#I___italian_text___
+// The function should place in buff a translated part of msg or the 1st one if a translation
+// does not exist
+char *SciGUIgfx::getIntlString(char *buff, const char *msg, const char *fmt, SCILanguage gameLang, SCILanguage subtitleLang) {
+
+	// prefer subtitleLang if set
+	SCILanguage lang = subtitleLang != kLangNone ? subtitleLang : gameLang;
+	const char *ptr = msg, *szFrom;
+	char ch;
+	int nLen = 0;
+	// searching for language code in msg
+	while (*ptr) {
+		ch = *(ptr + 1);
+		if(*ptr == '#' && (ch == 'I' || ch == 'F' || ch == 'G' || ch == 'S')) {
+			ptr +=2;
+			break;
+		}
+	ptr++;
+	}
+	// if a language code was found...
+	if (*ptr) {
+		if ((lang == kLangItalian && ch == 'I') || (lang == kLangFrench && ch == 'F') ||
+				(lang == kLangGerman && ch == 'G') || (lang == kLangSpanish && ch == 'S')) {
+			nLen = (int)strlen(ptr);
+			szFrom = ptr;
+		} else {
+			nLen = ptr - msg - 2;
+			szFrom = msg;
+		}
+	} else {
+		nLen = ptr - msg;
+		szFrom = msg;
+	}
+	if (fmt && subtitleLang != kLangNone) {
+		strcpy(buff, fmt);
+		strncat(buff, szFrom, nLen);
+		buff[nLen + strlen(fmt)] = 0;
+	} else {
+		strncpy(buff, szFrom, nLen);
+		buff[nLen] = 0;
+	}
+	return buff;
+}
+
+// TODO: implement codes
+int16 SciGUIgfx::TextSize(Common::Rect &rect, const char *str, int16 fontId, int16 maxwidth) {
+	char buff[1000] = { 0 };
+	int16 oldfont = GetFontId();
+	if (fontId != -1)
+		SetFont(fontId);
+	rect.top = rect.left = 0;
+
+	if (maxwidth < 0) { // force output as single line
+		rect.bottom = GetPointSize();
+		rect.right = StringWidth(str);
+	} else {
+		// rect.right=found widest line with RTextWidth and GetLongest
+		// rect.bottom=num. lines * GetPointSize
+		rect.right = (maxwidth ? maxwidth : 192);
+		int16 height = 0, maxWidth = 0, width, nc;
+		const char*p = str;
+		while (*p) {
+			if (*p == 0xD || *p == 0xA) {
+				p++;
+				continue;
+			}
+			nc = GetLongest(p, rect.right);
+			if (nc == 0)
+				break;
+			width = TextWidth(p, 0, nc);
+			maxWidth = MAX(width, maxWidth);
+			p += nc;
+			height++;
+		}
+		rect.bottom = height * GetPointSize();
+		rect.right = maxwidth ? maxwidth : MIN(rect.right, maxWidth);
+	}
+	SetFont(oldfont);
+	return rect.right;
+}
+
+// TODO: implement codes
+// return max # of chars to fit maxwidth with full words
+int16 SciGUIgfx::GetLongest(const char *str, int16 maxWidth) {
+	SciGUIfont *font = GetFont();
+	if (!font)
+		return 0;
+
+	int16 chars = 0, to = 0;
+	uint16 width = 0;
+	while (width <= maxWidth) {
+		switch (str[to]) {
+		case ' ':
+			chars = to + 1;
+			break;
+		case 0:
+		case 0xD:
+		case 0xA:
+			return to;
+		}
+		width += font->getCharWidth(str[to]);
+		to++;
+	}
+	return chars;
+}
+
+// TODO: implement codes
+void SciGUIgfx::DrawText(const char *text, int16 from, int16 len) {
+	int16 chr, width;
+	SciGUIfont *font = GetFont();
+	Common::Rect rect;
+
+	if (!font)
+		return;
+
+	text += from;
+	rect.top = _curPort->curTop;
+	rect.bottom = rect.top + _curPort->fontH;
+	while (len--) {
+		chr = (*text++) & 0xFF;
+		width = font->getCharWidth(chr);
+		// clear char
+		if (_curPort->penMode == 1) {
+			rect.left = _curPort->curLeft;
+			rect.right = rect.left + width;
+			EraseRect(rect);
+		}
+		// CharStd
+		font->draw(chr, _curPort->top + _curPort->curTop, _curPort->left + _curPort->curLeft, _curPort->penClr, _curPort->textFace);
+		_curPort->curLeft += width;
+	}
+}
+
+void SciGUIgfx::ShowText(const char *text, int16 from, int16 len) {
+	Common::Rect rect;
+
+	rect.top = _curPort->curTop;
+	rect.bottom = rect.top + GetPointSize();
+	rect.left = _curPort->curLeft;
+	DrawText(text, from, len);
+	rect.right = _curPort->curLeft;
+	ShowBits(rect, 1);
+}
+
+// Draws a text in rect.
+// align : -1-right , 0-left, 1-center
+void SciGUIgfx::TextBox(const char *text, int16 bshow, const Common::Rect &rect, int16 align, int16 fontId) {
+	int16 w, nc, offset;
+	int16 hline = 0;
+	int16 oldfont = GetFontId();
+	int16 rectWidth = rect.width();
+
+	if (fontId != -1)
+		SetFont(fontId);
+
+	while (*text) {
+		if (*text == 0xD || *text == 0xA) {
+			text++;
+			continue;
+		}
+		nc = GetLongest(text, rect.width());
+		if (nc == 0)
+			break;
+		w = TextWidth(text, 0, nc);
+		switch (align) {
+		case -1:
+			offset = rect.width() - w;
+			break;
+		case 1:
+			offset = (rect.width() - w) / 2;
+			break;
+		default:
+			offset = 0;
+		}
+		MoveTo(rect.left + offset, rect.top + hline);
+
+		if (bshow)
+			ShowText(text, 0, nc);
+		else
+			DrawText(text, 0, nc);
+		hline += GetPointSize();
+		text += nc;
+	}
+	SetFont(oldfont);
+}
+
+// Update (part of) screen
+void SciGUIgfx::ShowBits(const Common::Rect &r, uint16 flags) {
+	Common::Rect rect(r.left, r.top, r.right, r.bottom);
+	rect.clip(_curPort->rect);
+	if (rect.isEmpty()) // nothing to show
+		return;
+
+	OffsetRect(rect);
+	uint16 w = rect.width();
+	uint16 h = rect.height();
+	assert((flags&0x8000) == 0);
+	_screen->UpdateWhole();
+//	_system->copyRectToScreen(GetSegment(flags) + _baseTable[rect.top] + rect.left, 320, rect.left, rect.top, w, h);
+//	_system->updateScreen();
+}
+
+sciMemoryHandle SciGUIgfx::SaveBits(const Common::Rect &rect, byte screenMask) {
+	sciMemoryHandle memoryId;
+	byte *memoryPtr;
+	int size;
+	
+	Common::Rect r(rect.left, rect.top, rect.right, rect.bottom);
+	r.clip(_curPort->rect);
+	if (r.isEmpty()) // nothing to save
+		return NULL_REG;
+
+	OffsetRect(r); //local port coords to screen coords
+
+	// now actually ask _screen how much space it will need for saving
+	size = _screen->BitsGetDataSize(r, screenMask);
+
+	memoryId = kalloc(_s->segMan, "SaveBits()", size);
+	memoryPtr = kmem(_s->segMan, memoryId);
+	_screen->BitsSave(r, screenMask, memoryPtr);
+	return memoryId;
+}
+
+void SciGUIgfx::RestoreBits(sciMemoryHandle memoryHandle) {
+	byte *memoryPtr = kmem(_s->segMan, memoryHandle);;
+
+	if (memoryPtr) {
+		_screen->BitsRestore(memoryPtr);
+		kfree(_s->segMan, memoryHandle);
+	}
+}
+
+void SciGUIgfx::Draw_Line(int16 left, int16 top, int16 right, int16 bottom, byte color, byte prio, byte control) {
+	//set_drawing_flag
+	byte flag = _screen->GetDrawingMask(color, prio, control);
+	prio &= 0xF0;
+	control &= 0x0F;
+
+	// offseting the line
+	left += _curPort->left;
+	right += _curPort->left;
+	top += _curPort->top;
+	bottom += _curPort->top;
+	// horizontal line
+	if (top == bottom) {
+		Draw_Horiz(left, right, top, flag, color, prio, control);
+		return;
+	}
+	// vertical line
+	if (left == right) {
+		Draw_Vert(top, bottom, left, flag, color, prio, control);
+		return;
+	}
+	// sloped line - draw with Bresenham algorithm
+	int dy = bottom - top;
+	int dx = right - left;
+	int stepy = dy < 0 ? -1 : 1;
+	int stepx = dx < 0 ? -1 : 1;
+	dy = ABS(dy) << 1;
+	dx = ABS(dx) << 1;
+
+	// setting the 1st and last pixel
+	_screen->Put_Pixel(left, top, flag, color, prio, control);
+	_screen->Put_Pixel(right, bottom, flag, color, prio, control);
+	// drawing the line
+	if (dx > dy) // going horizontal
+	{
+		int fraction = dy - (dx >> 1);
+		while (left != right) {
+			if (fraction >= 0) {
+				top += stepy;
+				fraction -= dx;
+			}
+			left += stepx;
+			fraction += dy;
+			_screen->Put_Pixel(left, top, flag, color, prio, control);
+		}
+	} else // going vertical
+	{
+		int fraction = dx - (dy >> 1);
+		while (top != bottom) {
+			if (fraction >= 0) {
+				left += stepx;
+				fraction -= dy;
+			}
+			top += stepy;
+			fraction += dx;
+			_screen->Put_Pixel(left, top, flag, color, prio, control);
+		}
+	}
+	//g_sci->eventMgr->waitUntil(5);
+	//ShowBits(&_rThePort->rect,6);
+}
+
+void SciGUIgfx::Draw_Horiz(int16 left, int16 right, int16 top, byte flag, byte color, byte prio, byte control) {
+	if (right < left)
+		SWAP(right, left);
+	for (int i = left; i <= right; i++)
+		_screen->Put_Pixel(i, top, flag, color, prio, control);
+}
+
+//--------------------------------
+void SciGUIgfx::Draw_Vert(int16 top, int16 bottom, int16 left, byte flag, byte color, byte prio, byte control) {
+	if (top > bottom)
+		SWAP(top, bottom);
+	for (int i = top; i <= bottom; i++)
+		_screen->Put_Pixel(left, i, flag, color, prio, control);
+}
+
+// Bitmap for drawing sierra circles
+const byte pattern_Circles[8][15] = {
+	{ 0x01 },
+	{ 0x03, 0x03, 0x03 },
+	{ 0x02, 0x07, 0x07, 0x07, 0x02 },
+	{ 0x06, 0x06, 0x0F, 0x0F, 0x0F, 0x06, 0x06 },
+	{ 0x04, 0x0E, 0x1F, 0x1F, 0x1F, 0x1F, 0x1F, 0x0E, 0x04 },
+	{ 0x0C, 0x1E, 0x1E, 0x1E, 0x3F, 0x3F, 0x3F, 0x1E, 0x1E, 0x1E, 0x0C },
+	{ 0x1C, 0x3E, 0x3E, 0x3E, 0x7F, 0x7F, 0x7F, 0x7F, 0x7F, 0x3E, 0x3E, 0x3E, 0x1C },
+	{ 0x18, 0x3C, 0x7E, 0x7E, 0x7E, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7E, 0x7E, 0x7E, 0x3C, 0x18 }
+};
+
+const bool pattern_Textures[32 * 8 * 2] = {
+	false, false, false, false, false,  true, false, false, // 0x20
+	false, false,  true, false, true,  false, false,  true, // 0x94
+	false,  true, false, false, false, false, false, false, // 0x02
+	false, false,  true, false, false,  true, false, false, // 0x24
+	false, false, false, false,  true, false, false,  true, // 0x90
+	false,  true, false, false, false, false, false,  true, // 0x82
+	false, false,  true, false, false,  true, false,  true, // 0xA4
+	false,  true, false, false, false,  true, false,  true, // 0xA2
+	false,  true, false, false, false, false, false,  true, // 0x82
+	 true, false, false,  true, false, false, false, false, // 0x09
+	false,  true, false,  true, false, false, false, false, // 0x0A
+	false,  true, false, false, false,  true, false, false, // 0x22
+	false,  true, false, false,  true, false, false, false, // 0x12
+	false, false, false, false,  true, false, false, false, // 0x10
+	false,  true, false, false, false, false,  true, false, // 0x42
+	false, false,  true, false,  true, false, false, false, // 0x14
+	 true, false, false, false,  true, false, false,  true, // 0x91
+	false,  true, false,  true, false, false,  true, false, // 0x4A
+	 true, false, false, false,  true, false, false,  true, // 0x91
+	 true, false, false, false,  true, false, false, false, // 0x11
+	false, false, false,  true, false, false, false, false, // 0x08
+	false,  true, false, false,  true, false, false, false, // 0x12
+	 true, false,  true, false, false,  true, false, false, // 0x25
+	false, false, false, false,  true, false, false, false, // 0x10
+	false,  true, false, false, false,  true, false, false, // 0x22

@@ Diff output truncated at 100000 characters. @@

This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.




More information about the Scummvm-git-logs mailing list