static picture_pool_t *Pool(vout_display_t *vd, unsigned count) { vout_display_sys_t *sys = vd->sys; if (!sys->pool) { if (!sys->picture) { picture_resource_t rsc; memset(&rsc, 0, sizeof(rsc)); rsc.p[0].p_pixels = sys->video_ptr; rsc.p[0].i_lines = sys->var_info.yres; rsc.p[0].i_pitch = sys->line_length; sys->picture = picture_NewFromResource(&vd->fmt, &rsc); if (!sys->picture) return NULL; } if (sys->is_hw_accel) sys->pool = picture_pool_New(1, &sys->picture); else sys->pool = picture_pool_NewFromFormat(&vd->fmt, count); } return sys->pool; }
picture_pool_t *picture_pool_NewFromFormat(const video_format_t *fmt, int picture_count) { // picture_t *picture[picture_count]; picture_t **picture = (picture_t **)calloc(picture_count, sizeof(picture_t *)); // sunqueen modify for (int i = 0; i < picture_count; i++) { picture[i] = picture_NewFromFormat(fmt); if (!picture[i]) goto error; } picture_pool_t *pool = picture_pool_New(picture_count, picture); if (!pool) goto error; free(picture); // sunqueen add return pool; error: for (int i = 0; i < picture_count; i++) { if (!picture[i]) break; picture_Release(picture[i]); } free(picture); // sunqueen add return NULL; }
/** * Return a direct buffer */ static picture_pool_t *Pool (vout_display_t *vd, unsigned requested_count) { vout_display_sys_t *sys = vd->sys; (void)requested_count; if (sys->pool) return sys->pool; vout_display_place_t place; vout_display_PlacePicture (&place, &vd->source, vd->cfg, false); /* */ const uint32_t values[] = { place.x, place.y, place.width, place.height }; xcb_configure_window (sys->conn, sys->window, XCB_CONFIG_WINDOW_X | XCB_CONFIG_WINDOW_Y | XCB_CONFIG_WINDOW_WIDTH | XCB_CONFIG_WINDOW_HEIGHT, values); picture_t *pic = picture_NewFromFormat (&vd->fmt); if (!pic) return NULL; assert (pic->i_planes == 1); picture_resource_t res = { .p = { [0] = { .i_lines = pic->p->i_lines, .i_pitch = pic->p->i_pitch, }, }, }; picture_Release (pic); unsigned count; picture_t *pic_array[MAX_PICTURES]; const size_t size = res.p->i_pitch * res.p->i_lines; for (count = 0; count < MAX_PICTURES; count++) { xcb_shm_seg_t seg = (sys->seg_base != 0) ? (sys->seg_base + count) : 0; if (XCB_picture_Alloc (vd, &res, size, sys->conn, seg)) break; pic_array[count] = XCB_picture_NewFromResource (&vd->fmt, &res, sys->conn); if (unlikely(pic_array[count] == NULL)) break; } xcb_flush (sys->conn); if (count == 0) return NULL; sys->pool = picture_pool_New (count, pic_array); if (unlikely(sys->pool == NULL)) while (count > 0) picture_Release(pic_array[--count]); return sys->pool; }
static picture_t *Get(vout_display_t *vd) { vout_display_sys_t *sys = vd->sys; if (!sys->pool) { if (!sys->picture) { picture_resource_t rsc; memset(&rsc, 0, sizeof(rsc)); rsc.p[0].p_pixels = sys->video_ptr; rsc.p[0].i_lines = sys->var_info.yres; if (sys->var_info.xres_virtual) rsc.p[0].i_pitch = sys->var_info.xres_virtual * sys->bytes_per_pixel; else rsc.p[0].i_pitch = sys->var_info.xres * sys->bytes_per_pixel; sys->picture = picture_NewFromResource(&vd->fmt, &rsc); if (!sys->picture) return NULL; } if (sys->is_hw_accel) sys->pool = picture_pool_New(1, &sys->picture); else sys->pool = picture_pool_NewFromFormat(&vd->fmt, 1); if (!sys->pool) return NULL; } return picture_pool_Get(sys->pool); }
/** * Return a direct buffer */ static picture_pool_t *Pool (vout_display_t *vd, unsigned requested_count) { vout_display_sys_t *p_sys = vd->sys; (void)requested_count; if (!p_sys->pool) { vout_display_place_t place; vout_display_PlacePicture (&place, &vd->source, vd->cfg, false); /* */ const uint32_t values[] = { place.x, place.y, place.width, place.height }; xcb_configure_window (p_sys->conn, p_sys->window, XCB_CONFIG_WINDOW_X | XCB_CONFIG_WINDOW_Y | XCB_CONFIG_WINDOW_WIDTH | XCB_CONFIG_WINDOW_HEIGHT, values); picture_t *pic = picture_NewFromFormat (&vd->fmt); if (!pic) return NULL; assert (pic->i_planes == 1); memset (p_sys->resource, 0, sizeof(p_sys->resource)); unsigned count; picture_t *pic_array[MAX_PICTURES]; for (count = 0; count < MAX_PICTURES; count++) { picture_resource_t *res = &p_sys->resource[count]; res->p->i_lines = pic->p->i_lines; res->p->i_pitch = pic->p->i_pitch; if (PictureResourceAlloc (vd, res, res->p->i_pitch * res->p->i_lines, p_sys->conn, p_sys->shm)) break; pic_array[count] = picture_NewFromResource (&vd->fmt, res); if (!pic_array[count]) { PictureResourceFree (res, p_sys->conn); memset (res, 0, sizeof(*res)); break; } } picture_Release (pic); if (count == 0) return NULL; p_sys->pool = picture_pool_New (count, pic_array); /* TODO release picture resources if NULL */ xcb_flush (p_sys->conn); } return p_sys->pool; }
static picture_pool_t *Pool(vout_display_t *vd, unsigned count) { vout_display_sys_t *sys = vd->sys; if (sys->pool) return sys->pool; if (count > sys->count) count = sys->count; picture_t *pictures[count]; for (unsigned i = 0; i < count; i++) { picture_sys_t *picsys = malloc(sizeof (*picsys)); if (unlikely(picsys == NULL)) { count = i; break; } picsys->sys = sys; picsys->id = NULL; picture_resource_t rsc = { .p_sys = picsys }; for (unsigned i = 0; i < PICTURE_PLANE_MAX; i++) { /* vmem-lock is responsible for the allocation */ rsc.p[i].p_pixels = NULL; rsc.p[i].i_lines = sys->lines[i]; rsc.p[i].i_pitch = sys->pitches[i]; } pictures[i] = picture_NewFromResource(&vd->fmt, &rsc); if (!pictures[i]) { free(rsc.p_sys); count = i; break; } } /* */ sys->pool = picture_pool_New(count, pictures); if (!sys->pool) { for (unsigned i = 0; i < count; i++) picture_Release(pictures[i]); } picture_pool_Enum(sys->pool, Lock, sys); return sys->pool; }
/** * Return a direct buffer */ static picture_t *Get(vout_display_t *vd) { vout_display_sys_t *sys = vd->sys; if (!sys->pool) { picture_resource_t rsc; memset(&rsc, 0, sizeof(rsc)); if (sys->overlay) { SDL_Overlay *ol = sys->overlay; for (int i = 0; i < ol->planes; i++) { rsc.p[i].p_pixels = ol->pixels[ i > 0 && sys->is_uv_swapped ? (3-i) : i]; rsc.p[i].i_pitch = ol->pitches[i > 0 && sys->is_uv_swapped ? (3-i) : i]; rsc.p[i].i_lines = ol->h; if (ol->format == SDL_YV12_OVERLAY || ol->format == SDL_IYUV_OVERLAY) rsc.p[i].i_lines /= 2; } } else { const int x = sys->place.x; const int y = sys->place.y; SDL_Surface *sf = sys->display; SDL_FillRect(sf, NULL, 0); assert(x >= 0 && y >= 0); rsc.p[0].p_pixels = (uint8_t*)sf->pixels + y * sf->pitch + x * ((sf->format->BitsPerPixel + 7) / 8); rsc.p[0].i_pitch = sf->pitch; rsc.p[0].i_lines = vd->fmt.i_height; } picture_t *picture = picture_NewFromResource(&vd->fmt, &rsc);; if (!picture) return NULL; sys->pool = picture_pool_New(1, &picture); if (!sys->pool) return NULL; } return picture_pool_Get(sys->pool); }
/** * Return a pool of direct buffers */ static picture_pool_t *Pool(vout_display_t *vd, unsigned count) { vout_display_sys_t *sys = vd->sys; VLC_UNUSED(count); if (!sys->pool) { picture_resource_t rsc; memset(&rsc, 0, sizeof(rsc)); rsc.p[0].p_pixels = aa_image(sys->aa_context); rsc.p[0].i_pitch = aa_imgwidth(sys->aa_context); rsc.p[0].i_lines = aa_imgheight(sys->aa_context); picture_t *p_picture = picture_NewFromResource(&vd->fmt, &rsc); if (!p_picture) return NULL; sys->pool = picture_pool_New(1, &p_picture); } return sys->pool; }
picture_pool_t *picture_pool_Reserve(picture_pool_t *master, unsigned count) { picture_t *picture[count ? count : 1]; unsigned i; for (i = 0; i < count; i++) { picture[i] = picture_pool_Get(master); if (picture[i] == NULL) goto error; } picture_pool_t *pool = picture_pool_New(count, picture); if (!pool) goto error; return pool; error: while (i > 0) picture_Release(picture[--i]); return NULL; }
picture_pool_t *picture_pool_NewFromFormat(const video_format_t *fmt, unsigned count) { picture_t *picture[count ? count : 1]; unsigned i; for (i = 0; i < count; i++) { picture[i] = picture_NewFromFormat(fmt); if (picture[i] == NULL) goto error; } picture_pool_t *pool = picture_pool_New(count, picture); if (!pool) goto error; return pool; error: while (i > 0) picture_Release(picture[--i]); return NULL; }
picture_pool_t *picture_pool_NewFromFormat(const video_format_t *fmt, int picture_count) { picture_t *picture[picture_count]; for (int i = 0; i < picture_count; i++) { picture[i] = picture_NewFromFormat(fmt); if (!picture[i]) goto error; } picture_pool_t *pool = picture_pool_New(picture_count, picture); if (!pool) goto error; return pool; error: for (int i = 0; i < picture_count; i++) { if (!picture[i]) break; picture_Release(picture[i]); } return NULL; }
static int Init(vout_display_t *vd, video_format_t *fmt) { vout_display_sys_t *sys = vd->sys; /* */ RECT *display = &sys->sys.rect_display; display->left = 0; display->top = 0; display->right = GetSystemMetrics(SM_CXSCREEN);; display->bottom = GetSystemMetrics(SM_CYSCREEN);; /* Initialize an offscreen bitmap for direct buffer operations. */ /* */ HDC window_dc = GetDC(sys->sys.hvideownd); /* */ sys->i_depth = GetDeviceCaps(window_dc, PLANES) * GetDeviceCaps(window_dc, BITSPIXEL); /* */ msg_Dbg(vd, "GDI depth is %i", sys->i_depth); switch (sys->i_depth) { case 8: fmt->i_chroma = VLC_CODEC_RGB8; break; case 15: fmt->i_chroma = VLC_CODEC_RGB15; fmt->i_rmask = 0x7c00; fmt->i_gmask = 0x03e0; fmt->i_bmask = 0x001f; break; case 16: fmt->i_chroma = VLC_CODEC_RGB16; fmt->i_rmask = 0xf800; fmt->i_gmask = 0x07e0; fmt->i_bmask = 0x001f; break; case 24: fmt->i_chroma = VLC_CODEC_RGB24; fmt->i_rmask = 0x00ff0000; fmt->i_gmask = 0x0000ff00; fmt->i_bmask = 0x000000ff; break; case 32: fmt->i_chroma = VLC_CODEC_RGB32; fmt->i_rmask = 0x00ff0000; fmt->i_gmask = 0x0000ff00; fmt->i_bmask = 0x000000ff; break; default: msg_Err(vd, "screen depth %i not supported", sys->i_depth); return VLC_EGENERIC; } void *p_pic_buffer; int i_pic_pitch; /* Initialize offscreen bitmap */ BITMAPINFO *bi = &sys->bitmapinfo; memset(bi, 0, sizeof(BITMAPINFO) + 3 * sizeof(RGBQUAD)); if (sys->i_depth > 8) { ((DWORD*)bi->bmiColors)[0] = fmt->i_rmask; ((DWORD*)bi->bmiColors)[1] = fmt->i_gmask; ((DWORD*)bi->bmiColors)[2] = fmt->i_bmask;; } BITMAPINFOHEADER *bih = &sys->bitmapinfo.bmiHeader; bih->biSize = sizeof(BITMAPINFOHEADER); bih->biSizeImage = 0; bih->biPlanes = 1; bih->biCompression = (sys->i_depth == 15 || sys->i_depth == 16) ? BI_BITFIELDS : BI_RGB; bih->biBitCount = sys->i_depth; bih->biWidth = fmt->i_width; bih->biHeight = -fmt->i_height; bih->biClrImportant = 0; bih->biClrUsed = 0; bih->biXPelsPerMeter = 0; bih->biYPelsPerMeter = 0; i_pic_pitch = bih->biBitCount * bih->biWidth / 8; sys->off_bitmap = CreateDIBSection(window_dc, (BITMAPINFO *)bih, DIB_RGB_COLORS, &p_pic_buffer, NULL, 0); sys->off_dc = CreateCompatibleDC(window_dc); SelectObject(sys->off_dc, sys->off_bitmap); ReleaseDC(sys->sys.hvideownd, window_dc); if (!sys->sys.b_windowless) EventThreadUpdateTitle(sys->sys.event, VOUT_TITLE " (WinGDI output)"); /* */ picture_resource_t rsc; memset(&rsc, 0, sizeof(rsc)); rsc.p[0].p_pixels = p_pic_buffer; rsc.p[0].i_lines = fmt->i_height; rsc.p[0].i_pitch = i_pic_pitch;; picture_t *picture = picture_NewFromResource(fmt, &rsc); if (picture != NULL) sys->sys.pool = picture_pool_New(1, &picture); else sys->sys.pool = NULL; UpdateRects(vd, true); return VLC_SUCCESS; }