diff options
7 files changed, 157 insertions, 199 deletions
diff --git a/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayCodecFFmpeg.cpp b/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayCodecFFmpeg.cpp index 18939379c4..7f8d54b804 100644 --- a/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayCodecFFmpeg.cpp +++ b/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayCodecFFmpeg.cpp @@ -264,31 +264,30 @@ CDVDOverlay* CDVDOverlayCodecFFmpeg::GetOverlay() CDVDOverlayImage* overlay = new CDVDOverlayImage(); overlay->iPTSStartTime = m_StartTime; - overlay->iPTSStopTime = m_StopTime; - overlay->replace = true; + overlay->iPTSStopTime = m_StopTime; + overlay->replace = true; overlay->linesize = rect.w; - overlay->data = std::vector<uint8_t>(rect.w * rect.h); - overlay->palette = std::vector<uint32_t>(rect.nb_colors); - overlay->palette_colors = rect.nb_colors; - overlay->x = rect.x; - overlay->y = rect.y; - overlay->width = rect.w; - overlay->height = rect.h; - overlay->bForced = rect.flags != 0; - - overlay->source_width = m_width; + overlay->pixels.resize(rect.w * rect.h); + overlay->palette.resize(rect.nb_colors); + overlay->x = rect.x; + overlay->y = rect.y; + overlay->width = rect.w; + overlay->height = rect.h; + overlay->bForced = rect.flags != 0; + overlay->source_width = m_width; overlay->source_height = m_height; uint8_t* s = rect.data[0]; - uint8_t* t = overlay->data.data(); - for(int i=0;i<rect.h;i++) + uint8_t* t = overlay->pixels.data(); + + for (int i = 0; i < rect.h; i++) { memcpy(t, s, rect.w); s += rect.linesize[0]; t += overlay->linesize; } - for(int i=0;i<rect.nb_colors;i++) + for (int i = 0; i < rect.nb_colors; i++) overlay->palette[i] = Endian_SwapLE32(((uint32_t *)rect.data[1])[i]); m_SubtitleIndex++; diff --git a/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayImage.h b/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayImage.h index b6ed038a46..3af66d858f 100644 --- a/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayImage.h +++ b/xbmc/cores/VideoPlayer/DVDCodecs/Overlay/DVDOverlayImage.h @@ -34,24 +34,23 @@ public: else { bpp = 4; - palette = {}; + palette.clear(); } - palette_colors = src.palette_colors; - linesize = sub_w * bpp; - x = sub_x; - y = sub_y; - width = sub_w; - height = sub_h; - source_width = src.source_width; - source_height = src.source_height; + linesize = sub_w * bpp; + x = sub_x; + y = sub_y; + width = sub_w; + height = sub_h; + source_width = src.source_width; + source_height = src.source_height; - data = std::vector<uint8_t>(sub_h * linesize); + pixels.resize(sub_h * linesize); uint8_t* s = src.data_at(sub_x, sub_y); - uint8_t* t = data.data(); + uint8_t* t = pixels.data(); - for(int row = 0;row < sub_h; ++row) + for (int row = 0; row < sub_h; ++row) { memcpy(t, s, linesize); s += src.linesize; @@ -70,20 +69,14 @@ public: uint8_t* data_at(int sub_x, int sub_y) const { - int bpp; - if (!palette.empty()) - bpp = 1; - else - bpp = 4; - return const_cast<uint8_t*>(&data[(sub_y - y) * linesize + (sub_x - x) * bpp]); + const int bpp = palette.empty() ? 4 : 1; + return const_cast<uint8_t*>(pixels.data() + ((sub_y - y) * linesize + (sub_x - x) * bpp)); } - std::vector<uint8_t> data; - int linesize{0}; - + std::vector<uint8_t> pixels; std::vector<uint32_t> palette; - int palette_colors{0}; + int linesize{0}; int x{0}; int y{0}; int width{0}; diff --git a/xbmc/cores/VideoPlayer/DVDInputStreams/DVDInputStreamBluray.cpp b/xbmc/cores/VideoPlayer/DVDInputStreams/DVDInputStreamBluray.cpp index 59e277ca84..95c8cac537 100644 --- a/xbmc/cores/VideoPlayer/DVDInputStreams/DVDInputStreamBluray.cpp +++ b/xbmc/cores/VideoPlayer/DVDInputStreams/DVDInputStreamBluray.cpp @@ -809,11 +809,9 @@ void CDVDInputStreamBluray::OverlayCallback(const BD_OVERLAY * const ov) return; } - if (ov->cmd == BD_OVERLAY_DRAW - || ov->cmd == BD_OVERLAY_WIPE) + if (ov->cmd == BD_OVERLAY_DRAW || ov->cmd == BD_OVERLAY_WIPE) OverlayClear(plane, ov->x, ov->y, ov->w, ov->h); - /* uncompress and draw bitmap */ if (ov->img && ov->cmd == BD_OVERLAY_DRAW) { @@ -821,34 +819,32 @@ void CDVDInputStreamBluray::OverlayCallback(const BD_OVERLAY * const ov) if (ov->palette) { - overlay->palette_colors = 256; - overlay->palette = std::vector<uint32_t>(overlay->palette_colors); + overlay->palette.resize(256); for(unsigned i = 0; i < 256; i++) overlay->palette[i] = build_rgba(ov->palette[i]); } + else + overlay->palette.clear(); const BD_PG_RLE_ELEM *rlep = ov->img; + size_t bytes = ov->w * ov->h; + overlay->pixels.resize(bytes); - unsigned pixels = ov->w * ov->h; - - std::vector<uint8_t> img(pixels); + for (size_t i = 0; i < bytes; i += rlep->len, rlep++) + memset(overlay->pixels.data() + i, rlep->color, rlep->len); - for (unsigned i = 0; i < pixels; i += rlep->len, rlep++) - memset(img.data() + i, rlep->color, rlep->len); - - overlay->data = img; overlay->linesize = ov->w; - overlay->x = ov->x; - overlay->y = ov->y; - overlay->height = ov->h; - overlay->width = ov->w; + overlay->x = ov->x; + overlay->y = ov->y; + overlay->height = ov->h; + overlay->width = ov->w; overlay->source_height = plane.h; - overlay->source_width = plane.w; + overlay->source_width = plane.w; plane.o.push_back(overlay); } - if(ov->cmd == BD_OVERLAY_FLUSH) + if (ov->cmd == BD_OVERLAY_FLUSH) OverlayFlush(ov->pts); #endif } @@ -884,19 +880,18 @@ void CDVDInputStreamBluray::OverlayCallbackARGB(const struct bd_argb_overlay_s * { SOverlay overlay(new CDVDOverlayImage(), [](CDVDOverlay* ov) { CDVDOverlay::Release(ov); }); - overlay->palette_colors = 0; - overlay->palette = {}; - + overlay->palette.clear(); size_t bytes = static_cast<size_t>(ov->stride * ov->h * 4); + overlay->pixels.resize(bytes); + memcpy(overlay->pixels.data(), ov->argb, bytes); - overlay->data = std::vector<uint8_t>(ov->argb, ov->argb + bytes); overlay->linesize = ov->stride * 4; - overlay->x = ov->x; - overlay->y = ov->y; - overlay->height = ov->h; - overlay->width = ov->w; + overlay->x = ov->x; + overlay->y = ov->y; + overlay->height = ov->h; + overlay->width = ov->w; overlay->source_height = plane.h; - overlay->source_width = plane.w; + overlay->source_width = plane.w; plane.o.push_back(overlay); } diff --git a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererDX.cpp b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererDX.cpp index ac008ede36..10337b928b 100644 --- a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererDX.cpp +++ b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererDX.cpp @@ -74,12 +74,13 @@ COverlayQuadsDX::COverlayQuadsDX(ASS_Image* images, float width, float height) float u, v; if (!LoadTexture(quads.size_x, quads.size_y, quads.size_x, DXGI_FORMAT_R8_UNORM, - quads.data.data(), &u, &v, &m_texture)) + quads.texture.data(), &u, &v, &m_texture)) { return; } - Vertex *vt = new Vertex[6 * quads.quad.size()], *vt_orig = vt; + Vertex* vt = new Vertex[6 * quads.quad.size()]; + Vertex* vt_orig = vt; SQuad* vs = quads.quad.data(); float scale_u = u / quads.size_x; @@ -198,32 +199,21 @@ COverlayImageDX::~COverlayImageDX() COverlayImageDX::COverlayImageDX(CDVDOverlayImage* o) { - std::vector<uint32_t> rgba; - int stride; - if (!o->palette.empty()) + if (o->palette.empty()) { - m_pma = !!USE_PREMULTIPLIED_ALPHA; - rgba = convert_rgba(o, m_pma); - stride = o->width * 4; + m_pma = false; + uint32_t* rgba = reinterpret_cast<uint32_t*>(o->pixels.data()); + Load(rgba, o->width, o->height, o->linesize); } else { - m_pma = false; - rgba = std::vector<uint32_t>(o->data.data(), o->data.data() + o->data.size()); - stride = o->linesize; + std::vector<uint32_t> rgba(o->width * o->height); + m_pma = !!USE_PREMULTIPLIED_ALPHA; + convert_rgba(o, m_pma, rgba); + Load(rgba.data(), o->width, o->height, o->width * 4); } - if (rgba.empty()) - { - CLog::Log(LOGERROR, "COverlayImageDX::COverlayImageDX - failed to convert overlay to rgb"); - return; - } - - Load(rgba.data(), o->width, o->height, stride); - if (reinterpret_cast<uint8_t*>(rgba.data()) != o->data.data()) - rgba.clear(); - - if(o->source_width && o->source_height) + if (o->source_width && o->source_height) { float center_x = (0.5f * o->width + o->x) / o->source_width; float center_y = (0.5f * o->height + o->y) / o->source_height; @@ -237,8 +227,8 @@ COverlayImageDX::COverlayImageDX(CDVDOverlayImage* o) } else { - m_align = ALIGN_VIDEO; - m_pos = POSITION_ABSOLUTE; + m_align = ALIGN_VIDEO; + m_pos = POSITION_ABSOLUTE; m_x = static_cast<float>(o->x); m_y = static_cast<float>(o->y); m_width = static_cast<float>(o->width); @@ -249,20 +239,17 @@ COverlayImageDX::COverlayImageDX(CDVDOverlayImage* o) COverlayImageDX::COverlayImageDX(CDVDOverlaySpu* o) { int min_x, max_x, min_y, max_y; - std::vector<uint32_t> rgba = convert_rgba(o, USE_PREMULTIPLIED_ALPHA, min_x, max_x, min_y, max_y); - if (rgba.empty()) - { - CLog::Log(LOGERROR, "COverlayImageDX::COverlayImageDX - failed to convert overlay to rgb"); - return; - } + std::vector<uint32_t> rgba(o->width * o->height); + + convert_rgba(o, USE_PREMULTIPLIED_ALPHA, min_x, max_x, min_y, max_y, rgba); Load(rgba.data() + min_x + min_y * o->width, max_x - min_x, max_y - min_y, o->width * 4); - m_align = ALIGN_VIDEO; - m_pos = POSITION_ABSOLUTE; - m_x = (float)(min_x + o->x); - m_y = (float)(min_y + o->y); - m_width = (float)(max_x - min_x); - m_height = (float)(max_y - min_y); + m_align = ALIGN_VIDEO; + m_pos = POSITION_ABSOLUTE; + m_x = static_cast<float>(min_x + o->x); + m_y = static_cast<float>(min_y + o->y); + m_width = static_cast<float>(max_x - min_x); + m_height = static_cast<float>(max_y - min_y); } void COverlayImageDX::Load(uint32_t* rgba, int width, int height, int stride) diff --git a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererGL.cpp b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererGL.cpp index f21834ab76..a1b83a9d1c 100644 --- a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererGL.cpp +++ b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererGL.cpp @@ -161,27 +161,6 @@ COverlayTextureGL::COverlayTextureGL(CDVDOverlayImage* o) { m_texture = 0; - std::vector<uint32_t> rgba; - int stride; - if (!o->palette.empty()) - { - m_pma = !!USE_PREMULTIPLIED_ALPHA; - rgba = convert_rgba(o, m_pma); - stride = o->width * 4; - } - else - { - m_pma = false; - rgba = std::vector<uint32_t>(o->data.data(), o->data.data() + o->data.size()); - stride = o->linesize; - } - - if (rgba.empty()) - { - CLog::Log(LOGERROR, "COverlayTextureGL::COverlayTextureGL - failed to convert overlay to rgb"); - return; - } - glGenTextures(1, &m_texture); glBindTexture(GL_TEXTURE_2D, m_texture); @@ -190,14 +169,23 @@ COverlayTextureGL::COverlayTextureGL(CDVDOverlayImage* o) glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); - LoadTexture(GL_TEXTURE_2D, o->width, o->height, stride, &m_u, &m_v, false, rgba.data()); - - if (reinterpret_cast<uint8_t*>(rgba.data()) != o->data.data()) - rgba.clear(); + if (o->palette.empty()) + { + m_pma = false; + uint32_t* rgba = reinterpret_cast<uint32_t*>(o->pixels.data()); + LoadTexture(GL_TEXTURE_2D, o->width, o->height, o->linesize, &m_u, &m_v, false, rgba); + } + else + { + std::vector<uint32_t> rgba(o->width * o->height); + m_pma = !!USE_PREMULTIPLIED_ALPHA; + convert_rgba(o, m_pma, rgba); + LoadTexture(GL_TEXTURE_2D, o->width, o->height, o->width * 4, &m_u, &m_v, false, rgba.data()); + } glBindTexture(GL_TEXTURE_2D, 0); - if(o->source_width && o->source_height) + if (o->source_width && o->source_height) { float center_x = (0.5f * o->width + o->x) / o->source_width; float center_y = (0.5f * o->height + o->y) / o->source_height; @@ -211,8 +199,8 @@ COverlayTextureGL::COverlayTextureGL(CDVDOverlayImage* o) } else { - m_align = ALIGN_VIDEO; - m_pos = POSITION_ABSOLUTE; + m_align = ALIGN_VIDEO; + m_pos = POSITION_ABSOLUTE; m_x = static_cast<float>(o->x); m_y = static_cast<float>(o->y); m_width = static_cast<float>(o->width); @@ -225,13 +213,9 @@ COverlayTextureGL::COverlayTextureGL(CDVDOverlaySpu* o) m_texture = 0; int min_x, max_x, min_y, max_y; - std::vector<uint32_t> rgba = convert_rgba(o, USE_PREMULTIPLIED_ALPHA, min_x, max_x, min_y, max_y); + std::vector<uint32_t> rgba(o->width * o->height); - if (rgba.empty()) - { - CLog::Log(LOGERROR, "COverlayTextureGL::COverlayTextureGL - failed to convert overlay to rgb"); - return; - } + convert_rgba(o, USE_PREMULTIPLIED_ALPHA, min_x, max_x, min_y, max_y, rgba); glGenTextures(1, &m_texture); glBindTexture(GL_TEXTURE_2D, m_texture); @@ -246,13 +230,13 @@ COverlayTextureGL::COverlayTextureGL(CDVDOverlaySpu* o) glBindTexture(GL_TEXTURE_2D, 0); - m_align = ALIGN_VIDEO; - m_pos = POSITION_ABSOLUTE; - m_x = (float)(min_x + o->x); - m_y = (float)(min_y + o->y); - m_width = (float)(max_x - min_x); - m_height = (float)(max_y - min_y); - m_pma = !!USE_PREMULTIPLIED_ALPHA; + m_align = ALIGN_VIDEO; + m_pos = POSITION_ABSOLUTE; + m_x = static_cast<float>(min_x + o->x); + m_y = static_cast<float>(min_y + o->y); + m_width = static_cast<float>(max_x - min_x); + m_height = static_cast<float>(max_y - min_y); + m_pma = !!USE_PREMULTIPLIED_ALPHA; } COverlayGlyphGL::COverlayGlyphGL(ASS_Image* images, float width, float height) @@ -273,7 +257,7 @@ COverlayGlyphGL::COverlayGlyphGL(ASS_Image* images, float width, float height) glBindTexture(GL_TEXTURE_2D, m_texture); LoadTexture(GL_TEXTURE_2D, quads.size_x, quads.size_y, quads.size_x, &m_u, &m_v, true, - quads.data.data()); + quads.texture.data()); float scale_u = m_u / quads.size_x; diff --git a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.cpp b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.cpp index 0c32e94b9e..a21800e067 100644 --- a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.cpp +++ b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.cpp @@ -16,7 +16,8 @@ #include "settings/SettingsComponent.h" #include "windowing/GraphicContext.h" -namespace OVERLAY { +namespace OVERLAY +{ static uint32_t build_rgba(int a, int r, int g, int b, bool mergealpha) { @@ -43,32 +44,31 @@ static uint32_t build_rgba(int yuv[3], int alpha, bool mergealpha) } #undef clamp -std::vector<uint32_t> convert_rgba(CDVDOverlayImage* o, bool mergealpha) +void convert_rgba(CDVDOverlayImage* o, bool mergealpha, std::vector<uint32_t>& rgba) { - std::vector<uint32_t> rgba(o->width * o->height); - uint32_t palette[256] = {}; - for(int i = 0; i < o->palette_colors; i++) + for (size_t i = 0; i < o->palette.size(); i++) palette[i] = build_rgba((o->palette[i] >> PIXEL_ASHIFT) & 0xff , (o->palette[i] >> PIXEL_RSHIFT) & 0xff , (o->palette[i] >> PIXEL_GSHIFT) & 0xff , (o->palette[i] >> PIXEL_BSHIFT) & 0xff , mergealpha); - for(int row = 0; row < o->height; row++) - for(int col = 0; col < o->width; col++) - rgba[row * o->width + col] = palette[ o->data[row * o->linesize + col] ]; - - return rgba; + for (int row = 0; row < o->height; row++) + for (int col = 0; col < o->width; col++) + rgba[row * o->width + col] = palette[o->pixels[row * o->linesize + col]]; } -std::vector<uint32_t> convert_rgba( - CDVDOverlaySpu* o, bool mergealpha, int& min_x, int& max_x, int& min_y, int& max_y) +void convert_rgba(CDVDOverlaySpu* o, + bool mergealpha, + int& min_x, + int& max_x, + int& min_y, + int& max_y, + std::vector<uint32_t>& rgba) { - std::vector<uint32_t> rgba(o->width * o->height); - uint32_t palette[8]; - for(int i = 0; i < 4; i++) + for (int i = 0; i < 4; i++) { palette[i] = build_rgba(o->color[i] , o->alpha[i] , mergealpha); palette[i+4] = build_rgba(o->highlight_color[i], o->highlight_alpha[i], mergealpha); @@ -159,21 +159,18 @@ std::vector<uint32_t> convert_rgba( max_y = max_x = 1; min_y = min_x = 0; } - - return rgba; } bool convert_quad(ASS_Image* images, SQuads& quads, int max_x) { ASS_Image* img; + int count = 0; if (!images) return false; // first calculate how many glyph we have and the total x length - int count{0}; - for(img = images; img; img = img->next) { // fully transparent or width or height is 0 -> not displayed @@ -217,21 +214,20 @@ bool convert_quad(ASS_Image* images, SQuads& quads, int max_x) quads.size_y += curr_y + 1; // allocate space for the glyph positions and texturedata - - quads.quad = std::vector<SQuad>(count); - quads.data = std::vector<uint8_t>(quads.size_x * quads.size_y); + quads.quad.resize(count); + quads.texture.resize(quads.size_x * quads.size_y); SQuad* v = quads.quad.data(); - uint8_t* data = quads.data.data(); + uint8_t* data = quads.texture.data(); int y = 0; curr_x = 0; curr_y = 0; - for(img = images; img; img = img->next) + for (img = images; img; img = img->next) { - if((img->color & 0xff) == 0xff || img->w == 0 || img->h == 0) + if ((img->color & 0xff) == 0xff || img->w == 0 || img->h == 0) continue; unsigned int color = img->color; @@ -240,9 +236,9 @@ bool convert_quad(ASS_Image* images, SQuads& quads, int max_x) if (curr_x + img->w >= quads.size_x) { curr_y += y + 1; - curr_x = 0; - y = 0; - data = quads.data.data() + curr_y * quads.size_x; + curr_x = 0; + y = 0; + data = quads.texture.data() + curr_y * quads.size_x; } unsigned int r = ((color >> 24) & 0xff); @@ -265,10 +261,8 @@ bool convert_quad(ASS_Image* images, SQuads& quads, int max_x) v++; - for(int i=0; i<img->h; i++) - memcpy(data + quads.size_x * i - , img->bitmap + img->stride * i - , img->w); + for (int i = 0; i < img->h; i++) + memcpy(data + quads.size_x * i, img->bitmap + img->stride * i, img->w); if (img->h > y) y = img->h; diff --git a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.h b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.h index 94438e6305..96db7397a6 100644 --- a/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.h +++ b/xbmc/cores/VideoPlayer/VideoRenderers/OverlayRendererUtil.h @@ -17,28 +17,34 @@ class CDVDOverlaySpu; class CDVDOverlaySSA; typedef struct ass_image ASS_Image; -namespace OVERLAY { - - struct SQuad - { - int u, v; - unsigned char r, g, b, a; - int x, y; - int w, h; - }; - - struct SQuads - { - int size_x{0}; - int size_y{0}; - std::vector<uint8_t> data; - std::vector<SQuad> quad; - }; - - std::vector<uint32_t> convert_rgba(CDVDOverlayImage* o, bool mergealpha); - std::vector<uint32_t> convert_rgba( - CDVDOverlaySpu* o, bool mergealpha, int& min_x, int& max_x, int& min_y, int& max_y); - bool convert_quad(ASS_Image* images, SQuads& quads, int max_x); - int GetStereoscopicDepth(); - -} +namespace OVERLAY +{ + +struct SQuad +{ + int u, v; + unsigned char r, g, b, a; + int x, y; + int w, h; +}; + +struct SQuads +{ + int size_x{0}; + int size_y{0}; + std::vector<uint8_t> texture; + std::vector<SQuad> quad; +}; + +void convert_rgba(CDVDOverlayImage* o, bool mergealpha, std::vector<uint32_t>& rgba); +void convert_rgba(CDVDOverlaySpu* o, + bool mergealpha, + int& min_x, + int& max_x, + int& min_y, + int& max_y, + std::vector<uint32_t>& rgba); +bool convert_quad(ASS_Image* images, SQuads& quads, int max_x); +int GetStereoscopicDepth(); + +} // namespace OVERLAY |