INLINE void render_quad(sdl_info *sdl, texture_info *texture, render_primitive *prim, int x, int y) { SDL_Texture *texture_id; SDL_Rect target_rect; target_rect.x = x; target_rect.y = y; target_rect.w = round_nearest(prim->bounds.x1 - prim->bounds.x0); target_rect.h = round_nearest(prim->bounds.y1 - prim->bounds.y0); if (texture) { texture_id = texture->texture_id; texture->copyinfo->time -= osd_ticks(); #if 0 if ((PRIMFLAG_GET_SCREENTEX(prim->flags)) && video_config.filter) { SDL_SetTextureScaleMode(texture->texture_id, DRAW2_SCALEMODE_BEST); } else { SDL_SetTextureScaleMode(texture->texture_id, DRAW2_SCALEMODE_NEAREST); } #endif SDL_SetTextureBlendMode(texture_id, texture->sdl_blendmode); set_coloralphamode(texture_id, &prim->color); SDL_RenderCopy(sdl->sdl_renderer, texture_id, NULL, &target_rect); texture->copyinfo->time += osd_ticks(); texture->copyinfo->pixel_count += MAX(STAT_PIXEL_THRESHOLD , (texture->rawwidth * texture->rawheight)); if (sdl->last_blit_pixels) { texture->copyinfo->time += (sdl->last_blit_time * (INT64) (texture->rawwidth * texture->rawheight)) / (INT64) sdl->last_blit_pixels; } texture->copyinfo->samples++; texture->copyinfo->perf = ( texture->copyinfo->pixel_count * (osd_ticks_per_second()/1000)) / texture->copyinfo->time; } else { UINT32 sr = (UINT32)(255.0f * prim->color.r); UINT32 sg = (UINT32)(255.0f * prim->color.g); UINT32 sb = (UINT32)(255.0f * prim->color.b); UINT32 sa = (UINT32)(255.0f * prim->color.a); SDL_SetRenderDrawBlendMode(sdl->sdl_renderer, map_blendmode(PRIMFLAG_GET_BLENDMODE(prim->flags))); SDL_SetRenderDrawColor(sdl->sdl_renderer, sr, sg, sb, sa); SDL_RenderFillRect(sdl->sdl_renderer, &target_rect); } }
void renderer_sdl2::render_quad(texture_info *texture, const render_primitive &prim, const int x, const int y) { SDL_Rect target_rect; target_rect.x = x; target_rect.y = y; target_rect.w = round_nearest(prim.bounds.x1 - prim.bounds.x0); target_rect.h = round_nearest(prim.bounds.y1 - prim.bounds.y0); if (texture) { copy_info_t *copyinfo = texture->m_copyinfo; copyinfo->time -= osd_ticks(); texture->render_quad(prim, x, y); copyinfo->time += osd_ticks(); copyinfo->pixel_count += std::max(STAT_PIXEL_THRESHOLD , (texture->raw_width() * texture->raw_height())); if (m_last_blit_pixels) { copyinfo->time += (m_last_blit_time * (INT64) (texture->raw_width() * texture->raw_height())) / (INT64) m_last_blit_pixels; } copyinfo->samples++; copyinfo->perf = ( texture->m_copyinfo->pixel_count * (osd_ticks_per_second()/1000)) / texture->m_copyinfo->time; } else { UINT32 sr = (UINT32)(255.0f * prim.color.r); UINT32 sg = (UINT32)(255.0f * prim.color.g); UINT32 sb = (UINT32)(255.0f * prim.color.b); UINT32 sa = (UINT32)(255.0f * prim.color.a); SDL_SetRenderDrawBlendMode(m_sdl_renderer, map_blendmode(PRIMFLAG_GET_BLENDMODE(prim.flags))); SDL_SetRenderDrawColor(m_sdl_renderer, sr, sg, sb, sa); SDL_RenderFillRect(m_sdl_renderer, &target_rect); } }
texture_info::texture_info(renderer_sdl2 *renderer, const render_texinfo &texsource, const quad_setup_data &setup, UINT32 flags) { // fill in the core data m_renderer = renderer; m_hash = texture_compute_hash(texsource, flags); m_flags = flags; m_texinfo = texsource; m_texinfo.seqid = -1; // force set data m_is_rotated = false; m_setup = setup; m_sdl_blendmode = map_blendmode(PRIMFLAG_GET_BLENDMODE(flags)); m_pitch = 0; switch (PRIMFLAG_GET_TEXFORMAT(flags)) { case TEXFORMAT_ARGB32: m_format = SDL_TEXFORMAT_ARGB32; break; case TEXFORMAT_RGB32: m_format = texsource.palette ? SDL_TEXFORMAT_RGB32_PALETTED : SDL_TEXFORMAT_RGB32; break; case TEXFORMAT_PALETTE16: m_format = SDL_TEXFORMAT_PALETTE16; break; case TEXFORMAT_PALETTEA16: m_format = SDL_TEXFORMAT_PALETTE16A; break; case TEXFORMAT_YUY16: m_format = texsource.palette ? SDL_TEXFORMAT_YUY16_PALETTED : SDL_TEXFORMAT_YUY16; break; default: osd_printf_error("Unknown textureformat %d\n", PRIMFLAG_GET_TEXFORMAT(flags)); } if (setup.rotwidth != m_texinfo.width || setup.rotheight != m_texinfo.height || setup.dudx < 0 || setup.dvdy < 0 || (PRIMFLAG_GET_TEXORIENT(flags) != 0)) m_is_rotated = true; else m_is_rotated = false; //m_sdl_access = SDL_TEXTUREACCESS_STATIC; m_sdl_access = SDL_TEXTUREACCESS_STREAMING; // Watch out for 0x0 textures ... if (!m_setup.rotwidth || !m_setup.rotheight) osd_printf_warning("Trying to create texture with zero dim\n"); // set copy_info m_copyinfo = compute_size_type(); m_texture_id = SDL_CreateTexture(m_renderer->m_sdl_renderer, m_copyinfo->dst_fmt, m_sdl_access, m_setup.rotwidth, m_setup.rotheight); if (!m_texture_id) osd_printf_error("Error creating texture: %d x %d, pixelformat %s error: %s\n", m_setup.rotwidth, m_setup.rotheight, m_copyinfo->dstname, SDL_GetError()); if (m_sdl_access == SDL_TEXTUREACCESS_STATIC) { if (m_copyinfo->blitter->m_is_passthrough) m_pixels = nullptr; else m_pixels = malloc(m_setup.rotwidth * m_setup.rotheight * m_copyinfo->blitter->m_dest_bpp); } m_last_access = osd_ticks(); }
int renderer_sdl2::draw(int update) { texture_info *texture=nullptr; float vofs, hofs; int blit_pixels = 0; if (video_config.novideo) { return 0; } auto win = assert_window(); osd_dim wdim = win->get_size(); if (has_flags(FI_CHANGED) || (wdim.width() != m_width) || (wdim.height() != m_height)) { destroy_all_textures(); m_width = wdim.width(); m_height = wdim.height(); SDL_RenderSetViewport(m_sdl_renderer, nullptr); m_blittimer = 3; clear_flags(FI_CHANGED); } //SDL_SelectRenderer(window().sdl_window); if (m_blittimer > 0) { /* SDL Underlays need alpha = 0 ! */ SDL_SetRenderDrawBlendMode(m_sdl_renderer, SDL_BLENDMODE_NONE); //SDL_SetRenderDrawColor(0,0,0,255); SDL_SetRenderDrawColor(m_sdl_renderer, 0,0,0,0); SDL_RenderFillRect(m_sdl_renderer, nullptr); m_blittimer--; } // compute centering parameters vofs = hofs = 0.0f; if (video_config.centerv || video_config.centerh) { int ch, cw; ch = wdim.height(); cw = wdim.width(); if (video_config.centerv) { vofs = (ch - m_blit_dim.height()) / 2.0f; } if (video_config.centerh) { hofs = (cw - m_blit_dim.width()) / 2.0f; } } m_last_hofs = hofs; m_last_vofs = vofs; win->m_primlist->acquire_lock(); // now draw for (render_primitive &prim : *win->m_primlist) { Uint8 sr, sg, sb, sa; switch (prim.type) { case render_primitive::LINE: sr = (int)(255.0f * prim.color.r); sg = (int)(255.0f * prim.color.g); sb = (int)(255.0f * prim.color.b); sa = (int)(255.0f * prim.color.a); SDL_SetRenderDrawBlendMode(m_sdl_renderer, map_blendmode(PRIMFLAG_GET_BLENDMODE(prim.flags))); SDL_SetRenderDrawColor(m_sdl_renderer, sr, sg, sb, sa); SDL_RenderDrawLine(m_sdl_renderer, prim.bounds.x0 + hofs, prim.bounds.y0 + vofs, prim.bounds.x1 + hofs, prim.bounds.y1 + vofs); break; case render_primitive::QUAD: texture = texture_update(prim); if (texture) blit_pixels += (texture->raw_height() * texture->raw_width()); render_quad(texture, prim, round_nearest(hofs + prim.bounds.x0), round_nearest(vofs + prim.bounds.y0)); break; default: throw emu_fatalerror("Unexpected render_primitive type\n"); } } win->m_primlist->release_lock(); m_last_blit_pixels = blit_pixels; m_last_blit_time = -osd_ticks(); SDL_RenderPresent(m_sdl_renderer); m_last_blit_time += osd_ticks(); return 0; }
static texture_info *texture_create(sdl_window_info *window, const render_texinfo *texsource, quad_setup_data *setup, UINT32 flags) { sdl_info *sdl = (sdl_info *) window->dxdata; texture_info *texture; // allocate a new texture texture = (texture_info *) osd_malloc(sizeof(*texture)); memset(texture, 0, sizeof(*texture)); // fill in the core data texture->hash = texture_compute_hash(texsource, flags); texture->flags = flags; texture->texinfo = *texsource; texture->texinfo.seqid = -1; // force set data texture->is_rotated = FALSE; texture->setup = *setup; texture->sdl_blendmode = map_blendmode(PRIMFLAG_GET_BLENDMODE(flags)); switch (PRIMFLAG_GET_TEXFORMAT(flags)) { case TEXFORMAT_ARGB32: texture->format = SDL_TEXFORMAT_ARGB32; break; case TEXFORMAT_RGB32: texture->format = texsource->palette ? SDL_TEXFORMAT_RGB32_PALETTED : SDL_TEXFORMAT_RGB32; break; case TEXFORMAT_PALETTE16: texture->format = SDL_TEXFORMAT_PALETTE16; break; case TEXFORMAT_PALETTEA16: texture->format = SDL_TEXFORMAT_PALETTE16A; break; case TEXFORMAT_YUY16: texture->format = texsource->palette ? SDL_TEXFORMAT_YUY16_PALETTED : SDL_TEXFORMAT_YUY16; break; default: mame_printf_error("Unknown textureformat %d\n", PRIMFLAG_GET_TEXFORMAT(flags)); } texture->rawwidth = texsource->width; texture->rawheight = texsource->height; if (setup->rotwidth != texture->rawwidth || setup->rotheight != texture->rawheight || setup->dudx < 0 ) texture->is_rotated = TRUE; else texture->is_rotated = FALSE; //texture->sdl_access = SDL_TEXTUREACCESS_STATIC; texture->sdl_access = SDL_TEXTUREACCESS_STREAMING; // Watch out for 0x0 textures ... if (!texture->setup.rotwidth || !texture->setup.rotheight) mame_printf_warning("Trying to create texture with zero dim\n"); // compute the size texture->copyinfo = texture_compute_size_type(sdl->sdl_renderer, texsource, texture, flags); texture->texture_id = SDL_CreateTexture(sdl->sdl_renderer, texture->copyinfo->dst_fmt, texture->sdl_access, texture->setup.rotwidth, texture->setup.rotheight); if (!texture->texture_id) mame_printf_error("Error creating texture: %d x %d, pixelformat %s error: %s\n", texture->setup.rotwidth, texture->setup.rotheight, texture->copyinfo->dstname, SDL_GetError()); if ( (texture->copyinfo->func != NULL) && (texture->sdl_access == SDL_TEXTUREACCESS_STATIC)) { texture->pixels = osd_malloc_array(texture->setup.rotwidth * texture->setup.rotheight * texture->copyinfo->dst_bpp); texture->pixels_own=TRUE; } /* add us to the texture list */ texture->next = sdl->texlist; sdl->texlist = texture; texture->last_access = osd_ticks(); return texture; }
static int draw13_window_draw(sdl_window_info *window, UINT32 dc, int update) { sdl_info *sdl = (sdl_info *) window->dxdata; render_primitive *prim; texture_info *texture=NULL; float vofs, hofs; int blit_pixels = 0; if (video_config.novideo) { return 0; } if (sdl->resize_pending) { SDL_SetWindowSize(window->sdl_window, sdl->resize_width, sdl->resize_height); SDL_GetWindowSize(window->sdl_window, &window->width, &window->height); sdl->resize_pending = 0; SDL_RenderSetViewport(sdl->sdl_renderer, NULL); } //SDL_SelectRenderer(window->sdl_window); if (sdl->blittimer > 0) { /* SDL Underlays need alpha = 0 ! */ SDL_SetRenderDrawBlendMode(sdl->sdl_renderer, SDL_BLENDMODE_NONE); //SDL_SetRenderDrawColor(0,0,0,255); SDL_SetRenderDrawColor(sdl->sdl_renderer, 0,0,0,0); SDL_RenderFillRect(sdl->sdl_renderer, NULL); sdl->blittimer--; } // compute centering parameters vofs = hofs = 0.0f; if (video_config.centerv || video_config.centerh) { int ch, cw; if ((window->fullscreen) && (!video_config.switchres)) { ch = window->monitor->center_height; cw = window->monitor->center_width; } else { ch = window->height; cw = window->width; } if (video_config.centerv) { vofs = (ch - window->blitheight) / 2.0f; } if (video_config.centerh) { hofs = (cw - window->blitwidth) / 2.0f; } } sdl->last_hofs = hofs; sdl->last_vofs = vofs; window->primlist->acquire_lock(); // now draw for (prim = window->primlist->first(); prim != NULL; prim = prim->next()) { Uint8 sr, sg, sb, sa; switch (prim->type) { case render_primitive::LINE: sr = (int)(255.0f * prim->color.r); sg = (int)(255.0f * prim->color.g); sb = (int)(255.0f * prim->color.b); sa = (int)(255.0f * prim->color.a); SDL_SetRenderDrawBlendMode(sdl->sdl_renderer, map_blendmode(PRIMFLAG_GET_BLENDMODE(prim->flags))); SDL_SetRenderDrawColor(sdl->sdl_renderer, sr, sg, sb, sa); SDL_RenderDrawLine(sdl->sdl_renderer, prim->bounds.x0 + hofs, prim->bounds.y0 + vofs, prim->bounds.x1 + hofs, prim->bounds.y1 + vofs); break; case render_primitive::QUAD: texture = texture_update(window, prim); if (texture) blit_pixels += (texture->rawheight * texture->rawwidth); render_quad(sdl, texture, prim, round_nearest(hofs + prim->bounds.x0), round_nearest(vofs + prim->bounds.y0)); break; default: throw emu_fatalerror("Unexpected render_primitive type\n"); } } window->primlist->release_lock(); sdl->last_blit_pixels = blit_pixels; sdl->last_blit_time = -osd_ticks(); SDL_RenderPresent(sdl->sdl_renderer); sdl->last_blit_time += osd_ticks(); return 0; }