From: Toni Wilen Date: Sat, 23 Oct 2021 17:01:11 +0000 (+0300) Subject: Screenshot height update X-Git-Tag: 4900~37 X-Git-Url: https://git.unchartedbackwaters.co.uk/w/?a=commitdiff_plain;h=f21ab16649bd72ad91c1ca84144499400794a069;p=francis%2Fwinuae.git Screenshot height update --- diff --git a/drawing.cpp b/drawing.cpp index 8e9f46b0..706de627 100644 --- a/drawing.cpp +++ b/drawing.cpp @@ -483,6 +483,39 @@ static void reset_hblanking_limits(void) } } +static void get_vblanking_limits(int *vbstrtp, int *vbstopp, bool overscanonly) +{ + int vbstrt = vblank_firstline_hw; + if (!ecs_denise) { + vbstrt--; + } + int vbstop = maxvpos + lof_store; + if (!ecs_denise && !ecs_agnus) { + vbstop++; + } else if (ecs_agnus && !ecs_denise) { + // hide hblank bug by faking vblank start 1 line earlier + if (currprefs.gfx_overscanmode < OVERSCANMODE_BROADCAST) { + vbstrt++; + vbstop--; + } + } + if (currprefs.gfx_overscanmode < OVERSCANMODE_OVERSCAN && !overscanonly) { + int mult = (OVERSCANMODE_OVERSCAN - currprefs.gfx_overscanmode) * 5; + vbstrt += mult; + vbstop -= mult; + } + vbstrt <<= currprefs.gfx_vresolution; + vbstop <<= currprefs.gfx_vresolution; + if (vblank_top_start < vbstrt) { + vblank_top_start = vbstrt; + } + if (vblank_bottom_stop > vbstop) { + vblank_bottom_stop = vbstop; + } + *vbstrtp = vbstrt; + *vbstopp = vbstop; +} + // this handles hardwired vblank // vb_state in do_color_changes() handles programmed vblank static void set_vblanking_limits(void) @@ -502,26 +535,8 @@ static void set_vblanking_limits(void) hardwired = (new_beamcon0 & 0x1000) == 0; } if (hardwired) { - int vbstrt = vblank_firstline_hw; - if (!ecs_denise) { - vbstrt--; - } - int vbstop = maxvpos; - if (!ecs_denise && !ecs_agnus) { - vbstop++; - } else if (ecs_agnus && !ecs_denise) { - // hide hblank bug by faking vblank start 1 line earlier - if (currprefs.gfx_overscanmode < OVERSCANMODE_BROADCAST) { - vbstop--; - } - } - if (currprefs.gfx_overscanmode < OVERSCANMODE_OVERSCAN) { - int mult = (OVERSCANMODE_OVERSCAN - currprefs.gfx_overscanmode) * 5; - vbstrt += mult; - vbstop -= mult; - } - vbstrt <<= currprefs.gfx_vresolution; - vbstop <<= currprefs.gfx_vresolution; + int vbstrt, vbstop; + get_vblanking_limits(&vbstrt, &vbstop, false); if (vblank_top_start < vbstrt) { vblank_top_start = vbstrt; } @@ -531,6 +546,32 @@ static void set_vblanking_limits(void) } } +int get_vertical_visible_height(void) +{ + struct vidbuf_description *vidinfo = &adisplays[0].gfxvidinfo; + int h = vidinfo->drawbuffer.inheight; + int vbstrt, vbstop; + + if (programmedmode <= 1) { + h = (maxvpos_display + maxvpos_display_vsync - minfirstline) << currprefs.gfx_vresolution; + } + if (interlace_seen && currprefs.gfx_vresolution > 0) { + h -= 1 << (currprefs.gfx_vresolution - 1); + } + bool hardwired = true; + if (ecs_agnus) { + hardwired = (new_beamcon0 & 0x1000) == 0; + } + if (hardwired) { + get_vblanking_limits(&vbstrt, &vbstop, true); + int hh = vbstop - vbstrt; + if (h > hh) { + h = hh; + } + } + return h; +} + static void set_hblanking_limits(void) { // horizontal blanking @@ -4861,7 +4902,7 @@ bool notice_interlace_seen (bool lace) void allocvidbuffer(int monid, struct vidbuffer *buf, int width, int height, int depth) { - memset (buf, 0, sizeof (struct vidbuffer)); + memset(buf, 0, sizeof (struct vidbuffer)); buf->monitor_id = monid; buf->pixbytes = (depth + 7) / 8; buf->width_allocated = (width + 7) & ~7; @@ -4872,10 +4913,10 @@ void allocvidbuffer(int monid, struct vidbuffer *buf, int width, int height, int buf->inwidth = buf->width_allocated; buf->inheight = buf->height_allocated; - int size = width * height * buf->pixbytes; - buf->realbufmem = xcalloc (uae_u8, size); + buf->rowbytes = buf->width_allocated * buf->pixbytes; + int size = buf->rowbytes * buf->height_allocated; + buf->realbufmem = xcalloc(uae_u8, size); buf->bufmem_allocated = buf->bufmem = buf->realbufmem; - buf->rowbytes = width * buf->pixbytes; buf->bufmemend = buf->realbufmem + size - buf->rowbytes; buf->bufmem_lockable = true; } diff --git a/include/drawing.h b/include/drawing.h index 34713abc..b6cb91ac 100644 --- a/include/drawing.h +++ b/include/drawing.h @@ -375,6 +375,7 @@ extern void putpixel (uae_u8 *buf, uae_u8 *genlockbuf, int bpp, int x, xcolnr c8 extern void allocvidbuffer(int monid, struct vidbuffer *buf, int width, int height, int depth); extern void freevidbuffer(int monid, struct vidbuffer *buf); extern void check_prefs_picasso(void); +extern int get_vertical_visible_height(void); /* Finally, stuff that shouldn't really be shared. */ diff --git a/od-win32/rp.cpp b/od-win32/rp.cpp index de4045d3..13038bd8 100644 --- a/od-win32/rp.cpp +++ b/od-win32/rp.cpp @@ -1251,6 +1251,51 @@ static int screenoverlay(LPCVOID pData) return D3D_extoverlay(&eo); } +extern int screenshotf(int monid, const TCHAR *spath, int mode, int doprepare, int imagemode, struct vidbuffer *vb); +extern int screenshotmode; +static int screencap(LPCVOID pData, struct AmigaMonitor *mon) +{ + struct RPScreenCapture *rpsc = (struct RPScreenCapture *)pData; + if (rpsc->szScreenFiltered[0] || rpsc->szScreenRaw[0]) { + int ossm = screenshotmode; + DWORD ret = 0; + int ok = 0; + screenshotmode = 0; + if (log_rp & 2) + write_log(_T("'%s' '%s'\n"), rpsc->szScreenFiltered, rpsc->szScreenRaw); + if (rpsc->szScreenFiltered[0]) + ok = screenshotf(0, rpsc->szScreenFiltered, 1, 1, 0, NULL); + if (rpsc->szScreenRaw[0]) { + struct vidbuf_description *avidinfo = &adisplays[0].gfxvidinfo; + struct vidbuffer vb; + int w = avidinfo->drawbuffer.inwidth; + int h = get_vertical_visible_height(); + allocvidbuffer(0, &vb, w, h, avidinfo->drawbuffer.pixbytes * 8); + set_custom_limits(0, 0, 0, 0); + draw_frame(&vb); + ok |= screenshotf(0, rpsc->szScreenRaw, 1, 1, 1, &vb); + if (log_rp & 2) + write_log(_T("Rawscreenshot %dx%d\n"), w, h); + //ok |= screenshotf (_T("c:\\temp\\1.bmp"), 1, 1, 1, &vb); + freevidbuffer(0, &vb); + } + screenshotmode = ossm; + if (log_rp & 2) + write_log(_T("->%d\n"), ok); + if (!ok) + return RP_SCREENCAPTURE_ERROR; + if (WIN32GFX_IsPicassoScreen(mon)) { + ret |= RP_GUESTSCREENFLAGS_MODE_DIGITAL; + } else { + ret |= currprefs.gfx_resolution == RES_LORES ? RP_GUESTSCREENFLAGS_HORIZONTAL_LORES : ((currprefs.gfx_resolution == RES_SUPERHIRES) ? RP_GUESTSCREENFLAGS_HORIZONTAL_SUPERHIRES : 0); + ret |= currprefs.ntscmode ? RP_GUESTSCREENFLAGS_MODE_NTSC : RP_GUESTSCREENFLAGS_MODE_PAL; + ret |= currprefs.gfx_vresolution ? RP_GUESTSCREENFLAGS_VERTICAL_INTERLACED : 0; + } + return ret; + } + return RP_SCREENCAPTURE_ERROR; +} + static LRESULT CALLBACK RPHostMsgFunction2 (UINT uMessage, WPARAM wParam, LPARAM lParam, LPCVOID pData, DWORD dwDataSize, LPARAM lMsgFunctionParam) { @@ -1362,53 +1407,7 @@ static LRESULT CALLBACK RPHostMsgFunction2 (UINT uMessage, WPARAM wParam, LPARAM } case RP_IPC_TO_GUEST_SCREENCAPTURE: { - extern int screenshotf(int monid, const TCHAR *spath, int mode, int doprepare, int imagemode, struct vidbuffer *vb); - extern int screenshotmode; - struct RPScreenCapture *rpsc = (struct RPScreenCapture*)pData; - if (rpsc->szScreenFiltered[0] || rpsc->szScreenRaw[0]) { - int ossm = screenshotmode; - DWORD ret = 0; - int ok = 0; - screenshotmode = 0; - if (log_rp & 2) - write_log (_T("'%s' '%s'\n"), rpsc->szScreenFiltered, rpsc->szScreenRaw); - if (rpsc->szScreenFiltered[0]) - ok = screenshotf(0, rpsc->szScreenFiltered, 1, 1, 0, NULL); - if (rpsc->szScreenRaw[0]) { - struct vidbuf_description *avidinfo = &adisplays[0].gfxvidinfo; - struct vidbuffer vb; - int w = avidinfo->drawbuffer.inwidth; - int h = avidinfo->drawbuffer.inheight; - if (programmedmode <= 1) { - h = (maxvpos + lof_store - minfirstline) << currprefs.gfx_vresolution; - } - if (interlace_seen && currprefs.gfx_vresolution > 0) { - h -= 1 << (currprefs.gfx_vresolution - 1); - } - allocvidbuffer (0, &vb, w, h, avidinfo->drawbuffer.pixbytes * 8); - set_custom_limits(0, 0, 0, 0); - draw_frame (&vb); - ok |= screenshotf(0, rpsc->szScreenRaw, 1, 1, 1, &vb); - if (log_rp & 2) - write_log (_T("Rawscreenshot %dx%d\n"), w, h); - //ok |= screenshotf (_T("c:\\temp\\1.bmp"), 1, 1, 1, &vb); - freevidbuffer(0, &vb); - } - screenshotmode = ossm; - if (log_rp & 2) - write_log (_T("->%d\n"), ok); - if (!ok) - return RP_SCREENCAPTURE_ERROR; - if (WIN32GFX_IsPicassoScreen(mon)) { - ret |= RP_GUESTSCREENFLAGS_MODE_DIGITAL; - } else { - ret |= currprefs.gfx_resolution == RES_LORES ? RP_GUESTSCREENFLAGS_HORIZONTAL_LORES : ((currprefs.gfx_resolution == RES_SUPERHIRES) ? RP_GUESTSCREENFLAGS_HORIZONTAL_SUPERHIRES : 0); - ret |= currprefs.ntscmode ? RP_GUESTSCREENFLAGS_MODE_NTSC : RP_GUESTSCREENFLAGS_MODE_PAL; - ret |= currprefs.gfx_vresolution ? RP_GUESTSCREENFLAGS_VERTICAL_INTERLACED : 0; - } - return ret; - } - return RP_SCREENCAPTURE_ERROR; + return screencap(pData, mon); } case RP_IPC_TO_GUEST_SAVESTATE: { diff --git a/od-win32/win32_scaler.cpp b/od-win32/win32_scaler.cpp index e87b1426..0f3aa35f 100644 --- a/od-win32/win32_scaler.cpp +++ b/od-win32/win32_scaler.cpp @@ -788,6 +788,7 @@ uae_u8 *getfilterbuffer(int monid, int *widthp, int *heightp, int *pitch, int *d struct vidbuf_description *avidinfo = &adisplays[monid].gfxvidinfo; struct vidbuffer *vb = avidinfo->outbuffer; struct uae_filter *usedfilter = mon->usedfilter; + int w, h; *widthp = 0; *heightp = 0; @@ -799,10 +800,16 @@ uae_u8 *getfilterbuffer(int monid, int *widthp, int *heightp, int *pitch, int *d return NULL; } } - *widthp = vb->outwidth; - *heightp = vb->outheight; + w = vb->outwidth; + h = vb->outheight; + if (!monid) { + // if native screen: do not include vertical blank + h = get_vertical_visible_height(); + } if (pitch) *pitch = vb->rowbytes; + *widthp = w; + *heightp = h; *depth = vb->pixbytes * 8; return vb->bufmem; #if 0