From: <m97...@us...> - 2011-12-28 18:28:25
|
Revision: 12326 http://openmsx.svn.sourceforge.net/openmsx/?rev=12326&view=rev Author: m9710797 Date: 2011-12-28 18:28:19 +0000 (Wed, 28 Dec 2011) Log Message: ----------- Implemented basic support for V9990 set adjust I didn't yet test when exactly changes to the adjust register take effect on a real V9990 (at the start of a line or on the start of a frame or immediately). For comparison on a V99x8 vertical set adjust changes take effect on the next frame and horizontal set adjust changes take effect the next line. BiFiMSX asked me to implement this feature because apparently GEM uses this feature for scrolling. I didn't test myself, but BiFiMSX reported it works now with this patch. Modified Paths: -------------- openmsx/trunk/src/video/v9990/V9990.cc openmsx/trunk/src/video/v9990/V9990.hh openmsx/trunk/src/video/v9990/V9990PixelRenderer.cc Modified: openmsx/trunk/src/video/v9990/V9990.cc =================================================================== --- openmsx/trunk/src/video/v9990/V9990.cc 2011-12-27 18:40:33 UTC (rev 12325) +++ openmsx/trunk/src/video/v9990/V9990.cc 2011-12-28 18:28:19 UTC (rev 12326) @@ -254,12 +254,10 @@ break; case STATUS: { - const V9990DisplayPeriod& hor = getHorizontalTiming(); - const V9990DisplayPeriod& ver = getVerticalTiming(); - unsigned left = hor.blank + hor.border1; - unsigned right = left + hor.display; - unsigned top = ver.blank + ver.border1; - unsigned bottom = top + ver.display; + unsigned left = getLeftBorder(); + unsigned right = getRightBorder(); + unsigned top = getTopBorder(); + unsigned bottom = getBottomBorder(); unsigned ticks = getUCTicksThisFrame(time); unsigned x = ticks % V9990DisplayTiming::UC_TICKS_PER_LINE; unsigned y = ticks / V9990DisplayTiming::UC_TICKS_PER_LINE; @@ -623,6 +621,10 @@ case SCROLL_CONTROL_BX1: renderer->updateScrollBX(time); break; + case DISPLAY_ADJUST: + // TODO verify on real V9990: when exactly does a + // change in horizontal/vertical adjust take place + break; } // commit the change regs[reg] = val; @@ -695,16 +697,14 @@ V9990_VSYNC); // schedule DISPLAY_START - int topBorder = getVerticalTiming().blank + getVerticalTiming().border1; setSyncPoint( - frameStartTime + topBorder * V9990DisplayTiming::UC_TICKS_PER_LINE, - V9990_DISPLAY_START); + frameStartTime + getTopBorder() * V9990DisplayTiming::UC_TICKS_PER_LINE, + V9990_DISPLAY_START); // schedule VSCAN - int bottomBorder = topBorder + getVerticalTiming().display; setSyncPoint( - frameStartTime + bottomBorder * V9990DisplayTiming::UC_TICKS_PER_LINE, - V9990_VSCAN); + frameStartTime + getBottomBorder() * V9990DisplayTiming::UC_TICKS_PER_LINE, + V9990_VSCAN); renderer->frameStart(time); } @@ -846,7 +846,7 @@ offset = ticks - (ticks % V9990DisplayTiming::UC_TICKS_PER_LINE); } else { int line = regs[INTERRUPT_1] + 256 * (regs[INTERRUPT_2] & 3) + - getVerticalTiming().blank + getVerticalTiming().border1; + getTopBorder(); offset = line * V9990DisplayTiming::UC_TICKS_PER_LINE; } int mult = (status & 0x04) ? 3 : 2; // MCLK / XTAL1 Modified: openmsx/trunk/src/video/v9990/V9990.hh =================================================================== --- openmsx/trunk/src/video/v9990/V9990.hh 2011-12-27 18:40:33 UTC (rev 12325) +++ openmsx/trunk/src/video/v9990/V9990.hh 2011-12-28 18:28:19 UTC (rev 12326) @@ -287,12 +287,34 @@ return *horTiming; } + /** Get the number of VDP clockticks between the start of the line and + * the end of the left border. + */ + inline int getLeftBorder() const { + return horTiming->blank + horTiming->border1 + + (((regs[DISPLAY_ADJUST] & 0x0F) ^ 7) - 8) * 8; + } + /** Get the number of VDP clockticks between the start of the line and + * the end of the right border. + */ + inline int getRightBorder() const { + return getLeftBorder() + horTiming->display; + } + /** Get vertical display timings */ inline const V9990DisplayPeriod& getVerticalTiming() const { return *verTiming; } + inline int getTopBorder() const { + return verTiming->blank + verTiming->border1 + + (((regs[DISPLAY_ADJUST] >> 4) ^ 7) - 8); + } + inline int getBottomBorder() const { + return getTopBorder() + verTiming->display; + } + inline unsigned getPriorityControlX() const { unsigned t = regs[PRIORITY_CONTROL] & 0x03; return (t == 0) ? 256 : t << 6; Modified: openmsx/trunk/src/video/v9990/V9990PixelRenderer.cc =================================================================== --- openmsx/trunk/src/video/v9990/V9990PixelRenderer.cc 2011-12-27 18:40:33 UTC (rev 12325) +++ openmsx/trunk/src/video/v9990/V9990PixelRenderer.cc 2011-12-28 18:28:19 UTC (rev 12326) @@ -95,8 +95,7 @@ accuracy = renderSettings.getAccuracy().getValue(); lastX = 0; lastY = 0; - const V9990DisplayPeriod& verTiming = vdp.getVerticalTiming(); - verticalOffsetA = verticalOffsetB = verTiming.blank + verTiming.border1; + verticalOffsetA = verticalOffsetB = vdp.getTopBorder(); // Make sure that the correct timing is used setDisplayMode(vdp.getDisplayMode(), time); @@ -143,8 +142,6 @@ void V9990PixelRenderer::renderUntil(EmuTime::param time) { - const V9990DisplayPeriod& horTiming = vdp.getHorizontalTiming(); - // Translate time to pixel position int limitTicks = vdp.getUCTicksThisFrame(time); assert(limitTicks <= @@ -170,8 +167,8 @@ if ((toX == lastX) && (toY == lastY)) return; // edges of the DISPLAY part of the vdp output - int left = horTiming.blank + horTiming.border1; - int right = left + horTiming.display; + int left = vdp.getLeftBorder(); + int right = vdp.getRightBorder(); int rightEdge = V9990DisplayTiming::UC_TICKS_PER_LINE; if (displayEnabled) { @@ -232,10 +229,8 @@ } else { assert(type == DRAW_DISPLAY); - const V9990DisplayPeriod& horTiming = vdp.getHorizontalTiming(); - const V9990DisplayPeriod& verTiming = vdp.getVerticalTiming(); - int displayX = fromX - horTiming.blank - horTiming.border1; - int displayY = fromY - verTiming.blank - verTiming.border1; + int displayX = fromX - vdp.getLeftBorder(); + int displayY = fromY - vdp.getTopBorder(); int displayYA = fromY - verticalOffsetA; int displayYB = fromY - verticalOffsetB; This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |