bool CEGLNativeTypeRaspberryPI::ProbeResolutions(std::vector<RESOLUTION_INFO> &resolutions) { #if defined(TARGET_RASPBERRY_PI) resolutions.clear(); if(!m_DllBcmHost) return false; m_fixedMode = false; /* read initial desktop resolution before probe resolutions. * probing will replace the desktop resolution when it finds the same one. * we raplace it because probing will generate more detailed * resolution flags we don't get with vc_tv_get_state. */ if(m_initDesktopRes) { TV_DISPLAY_STATE_T tv_state; // get current display settings state memset(&tv_state, 0, sizeof(TV_DISPLAY_STATE_T)); m_DllBcmHost->vc_tv_get_display_state(&tv_state); if ((tv_state.state & ( VC_HDMI_HDMI | VC_HDMI_DVI )) != 0) // hdtv { m_desktopRes.iScreen = 0; m_desktopRes.bFullScreen = true; m_desktopRes.iWidth = tv_state.display.hdmi.width; m_desktopRes.iHeight = tv_state.display.hdmi.height; m_desktopRes.iScreenWidth = tv_state.display.hdmi.width; m_desktopRes.iScreenHeight= tv_state.display.hdmi.height; m_desktopRes.dwFlags = MAKEFLAGS(tv_state.display.hdmi.group, tv_state.display.hdmi.mode, tv_state.display.hdmi.scan_mode); // Also add 3D flags if (tv_state.display.hdmi.format_3d == HDMI_3D_FORMAT_SBS_HALF) { m_desktopRes.dwFlags |= D3DPRESENTFLAG_MODE3DSBS; m_desktopRes.iWidth >>= 1; m_desktopRes.iScreenWidth >>= 1; } else if (tv_state.display.hdmi.format_3d == HDMI_3D_FORMAT_TB_HALF)
void CEGLNativeTypeRaspberryPI::GetSupportedModes(HDMI_RES_GROUP_T group, std::vector<RESOLUTION_INFO> &resolutions) { if(!m_DllBcmHost) return; //Supported HDMI CEA/DMT resolutions, preferred resolution will be returned int32_t num_modes = 0; HDMI_RES_GROUP_T prefer_group; uint32_t prefer_mode; int i; TV_SUPPORTED_MODE_NEW_T *supported_modes = NULL; // query the number of modes first int max_supported_modes = m_DllBcmHost->vc_tv_hdmi_get_supported_modes_new(group, NULL, 0, &prefer_group, &prefer_mode); if (max_supported_modes > 0) supported_modes = new TV_SUPPORTED_MODE_NEW_T[max_supported_modes]; if (supported_modes) { num_modes = m_DllBcmHost->vc_tv_hdmi_get_supported_modes_new(group, supported_modes, max_supported_modes, &prefer_group, &prefer_mode); CLog::Log(LOGDEBUG, "EGL get supported modes (%d) = %d, prefer_group=%x, prefer_mode=%x\n", group, num_modes, prefer_group, prefer_mode); } if (num_modes > 0 && prefer_group != HDMI_RES_GROUP_INVALID) { TV_SUPPORTED_MODE_NEW_T *tv = supported_modes; for (i=0; i < num_modes; i++, tv++) { RESOLUTION_INFO res; res.iScreen = 0; res.bFullScreen = true; res.dwFlags = MAKEFLAGS(group, tv->code, tv->scan_mode); res.fRefreshRate = (float)tv->frame_rate; res.iWidth = tv->width; res.iHeight = tv->height; res.iScreenWidth = tv->width; res.iScreenHeight = tv->height; res.fPixelRatio = get_display_aspect_ratio((HDMI_ASPECT_T)tv->aspect_ratio) / ((float)res.iScreenWidth / (float)res.iScreenHeight); res.iSubtitles = (int)(0.965 * res.iHeight); if (!m_desktopRes.dwFlags && prefer_group == group && prefer_mode == tv->code) m_desktopRes = res; AddUniqueResolution(res, resolutions); CLog::Log(LOGDEBUG, "EGL mode %d: %s (%.2f) %s%s:%x\n", i, res.strMode.c_str(), res.fPixelRatio, tv->native ? "N" : "", tv->scan_mode ? "I" : "", tv->code); if (tv->frame_rate == 24 || tv->frame_rate == 30 || tv->frame_rate == 48 || tv->frame_rate == 60 || tv->frame_rate == 72) { RESOLUTION_INFO res2 = res; res2.fRefreshRate = (float)tv->frame_rate * (1000.0f/1001.0f); AddUniqueResolution(res2, resolutions); } } } if (supported_modes) delete [] supported_modes; }
bool CEGLNativeTypeRaspberryPI::ProbeResolutions(std::vector<RESOLUTION_INFO> &resolutions) { #if defined(TARGET_RASPBERRY_PI) resolutions.clear(); if(!m_DllBcmHost) return false; /* read initial desktop resolution before probe resolutions. * probing will replace the desktop resolution when it finds the same one. * we raplace it because probing will generate more detailed * resolution flags we don't get with vc_tv_get_state. */ if(m_initDesktopRes) { TV_DISPLAY_STATE_T tv_state; // get current display settings state memset(&tv_state, 0, sizeof(TV_DISPLAY_STATE_T)); m_DllBcmHost->vc_tv_get_display_state(&tv_state); if ((tv_state.state & ( VC_HDMI_HDMI | VC_HDMI_DVI )) != 0) // hdtv { m_desktopRes.iScreen = 0; m_desktopRes.bFullScreen = true; m_desktopRes.iWidth = tv_state.display.hdmi.width; m_desktopRes.iHeight = tv_state.display.hdmi.height; m_desktopRes.iScreenWidth = tv_state.display.hdmi.width; m_desktopRes.iScreenHeight= tv_state.display.hdmi.height; m_desktopRes.dwFlags = MAKEFLAGS(tv_state.display.hdmi.group, tv_state.display.hdmi.mode, tv_state.display.hdmi.scan_mode); m_desktopRes.fPixelRatio = tv_state.display.hdmi.display_options.aspect == 0 ? 1.0f : get_display_aspect_ratio((HDMI_ASPECT_T)tv_state.display.hdmi.display_options.aspect) / ((float)m_desktopRes.iScreenWidth / (float)m_desktopRes.iScreenHeight); HDMI_PROPERTY_PARAM_T property; property.property = HDMI_PROPERTY_PIXEL_CLOCK_TYPE; vc_tv_hdmi_get_property(&property); m_desktopRes.fRefreshRate = property.param1 == HDMI_PIXEL_CLOCK_TYPE_NTSC ? tv_state.display.hdmi.frame_rate * (1000.0f/1001.0f) : tv_state.display.hdmi.frame_rate; } else if ((tv_state.state & ( VC_SDTV_NTSC | VC_SDTV_PAL )) != 0) // sdtv { m_desktopRes.iScreen = 0; m_desktopRes.bFullScreen = true; m_desktopRes.iWidth = tv_state.display.sdtv.width; m_desktopRes.iHeight = tv_state.display.sdtv.height; m_desktopRes.iScreenWidth = tv_state.display.sdtv.width; m_desktopRes.iScreenHeight= tv_state.display.sdtv.height; m_desktopRes.dwFlags = MAKEFLAGS(HDMI_RES_GROUP_INVALID, tv_state.display.sdtv.mode, 1); m_desktopRes.fRefreshRate = (float)tv_state.display.sdtv.frame_rate; m_desktopRes.fPixelRatio = tv_state.display.hdmi.display_options.aspect == 0 ? 1.0f : get_display_aspect_ratio((SDTV_ASPECT_T)tv_state.display.sdtv.display_options.aspect) / ((float)m_desktopRes.iScreenWidth / (float)m_desktopRes.iScreenHeight); } else if ((tv_state.state & VC_LCD_ATTACHED_DEFAULT) != 0) // lcd { m_desktopRes.iScreen = 0; m_desktopRes.bFullScreen = true; m_desktopRes.iWidth = tv_state.display.sdtv.width; m_desktopRes.iHeight = tv_state.display.sdtv.height; m_desktopRes.iScreenWidth = tv_state.display.sdtv.width; m_desktopRes.iScreenHeight= tv_state.display.sdtv.height; m_desktopRes.dwFlags = MAKEFLAGS(HDMI_RES_GROUP_INVALID, 0, 0); m_desktopRes.fRefreshRate = (float)tv_state.display.sdtv.frame_rate; m_desktopRes.fPixelRatio = tv_state.display.hdmi.display_options.aspect == 0 ? 1.0f : get_display_aspect_ratio((SDTV_ASPECT_T)tv_state.display.sdtv.display_options.aspect) / ((float)m_desktopRes.iScreenWidth / (float)m_desktopRes.iScreenHeight); } SetResolutionString(m_desktopRes); m_initDesktopRes = false; m_desktopRes.iSubtitles = (int)(0.965 * m_desktopRes.iHeight); CLog::Log(LOGDEBUG, "EGL initial desktop resolution %s (%.2f)\n", m_desktopRes.strMode.c_str(), m_desktopRes.fPixelRatio); } if(GETFLAGS_GROUP(m_desktopRes.dwFlags) && GETFLAGS_MODE(m_desktopRes.dwFlags)) { GetSupportedModes(HDMI_RES_GROUP_DMT, resolutions); GetSupportedModes(HDMI_RES_GROUP_CEA, resolutions); } { AddUniqueResolution(m_desktopRes, resolutions, true); CLog::Log(LOGDEBUG, "EGL probe resolution %s:%x\n", m_desktopRes.strMode.c_str(), m_desktopRes.dwFlags); } DLOG("CEGLNativeTypeRaspberryPI::ProbeResolutions\n"); return true; #else return false; #endif }
void CEGLNativeTypeRaspberryPI::GetSupportedModes(HDMI_RES_GROUP_T group, std::vector<RESOLUTION_INFO> &resolutions) { if(!m_DllBcmHost) return; //Supported HDMI CEA/DMT resolutions, preferred resolution will be returned int32_t num_modes = 0; HDMI_RES_GROUP_T prefer_group; uint32_t prefer_mode; int i; TV_SUPPORTED_MODE_NEW_T *supported_modes = NULL; // query the number of modes first int max_supported_modes = m_DllBcmHost->vc_tv_hdmi_get_supported_modes_new(group, NULL, 0, &prefer_group, &prefer_mode); if (max_supported_modes > 0) supported_modes = new TV_SUPPORTED_MODE_NEW_T[max_supported_modes]; if (supported_modes) { num_modes = m_DllBcmHost->vc_tv_hdmi_get_supported_modes_new(group, supported_modes, max_supported_modes, &prefer_group, &prefer_mode); CLog::Log(LOGDEBUG, "EGL get supported modes (%d) = %d, prefer_group=%x, prefer_mode=%x\n", group, num_modes, prefer_group, prefer_mode); } if (num_modes > 0 && prefer_group != HDMI_RES_GROUP_INVALID) { TV_SUPPORTED_MODE_NEW_T *tv = supported_modes; for (i=0; i < num_modes; i++, tv++) { RESOLUTION_INFO res; res.iScreen = 0; res.bFullScreen = true; res.dwFlags = MAKEFLAGS(group, tv->code, tv->scan_mode); res.fRefreshRate = (float)tv->frame_rate; res.iWidth = tv->width; res.iHeight = tv->height; res.iScreenWidth = tv->width; res.iScreenHeight = tv->height; res.fPixelRatio = get_display_aspect_ratio((HDMI_ASPECT_T)tv->aspect_ratio) / ((float)res.iScreenWidth / (float)res.iScreenHeight); int gui_width = res.iWidth; int gui_height = res.iHeight; ClampToGUIDisplayLimits(gui_width, gui_height); res.iWidth = gui_width; res.iHeight = gui_height; res.strMode = StringUtils::Format("%dx%d @ %.2f%s - Full Screen", res.iScreenWidth, res.iScreenHeight, res.fRefreshRate, res.dwFlags & D3DPRESENTFLAG_INTERLACED ? "i" : ""); CLog::Log(LOGDEBUG, "EGL mode %d: %s (%.2f) %s%s:%x\n", i, res.strMode.c_str(), res.fPixelRatio, tv->native ? "N" : "", tv->scan_mode ? "I" : "", tv->code); res.iSubtitles = (int)(0.965 * res.iHeight); AddUniqueResolution(res, resolutions); // Also add 3D versions of modes if (tv->struct_3d_mask & HDMI_3D_STRUCT_SIDE_BY_SIDE_HALF_HORIZONTAL) { RESOLUTION_INFO res2 = res; res2.dwFlags |= D3DPRESENTFLAG_MODE3DSBS; res2.fPixelRatio = get_display_aspect_ratio((HDMI_ASPECT_T)tv->aspect_ratio) / ((float)res2.iScreenWidth / (float)res2.iScreenHeight); res2.fPixelRatio *= 2.0f; res2.strMode = StringUtils::Format("%dx%d @ %.2f%s - Full Screen", res2.iScreenWidth, res2.iScreenHeight, res2.fRefreshRate, res2.dwFlags & D3DPRESENTFLAG_INTERLACED ? "i" : ""); CLog::Log(LOGDEBUG, "EGL mode %d: %s (%.2f) SBS\n", i, res2.strMode.c_str(), res2.fPixelRatio); res2.iSubtitles = (int)(0.965 * res2.iHeight); AddUniqueResolution(res2, resolutions); } if (tv->struct_3d_mask & HDMI_3D_STRUCT_TOP_AND_BOTTOM) { RESOLUTION_INFO res2 = res; res2.dwFlags |= D3DPRESENTFLAG_MODE3DTB; res2.fPixelRatio = get_display_aspect_ratio((HDMI_ASPECT_T)tv->aspect_ratio) / ((float)res2.iScreenWidth / (float)res2.iScreenHeight); res2.fPixelRatio *= 0.5f; res2.strMode = StringUtils::Format("%dx%d @ %.2f%s - Full Screen", res2.iScreenWidth, res2.iScreenHeight, res2.fRefreshRate, res2.dwFlags & D3DPRESENTFLAG_INTERLACED ? "i" : ""); CLog::Log(LOGDEBUG, "EGL mode %d: %s (%.2f) TAB\n", i, res2.strMode.c_str(), res2.fPixelRatio); res2.iSubtitles = (int)(0.965 * res2.iHeight); AddUniqueResolution(res2, resolutions); } } } if (supported_modes) delete [] supported_modes; }
bool CEGLNativeTypeRaspberryPI::ProbeResolutions(std::vector<RESOLUTION_INFO> &resolutions) { #if defined(TARGET_RASPBERRY_PI) resolutions.clear(); if(!m_DllBcmHost) return false; m_fixedMode = false; /* read initial desktop resolution before probe resolutions. * probing will replace the desktop resolution when it finds the same one. * we raplace it because probing will generate more detailed * resolution flags we don't get with vc_tv_get_state. */ if(m_initDesktopRes) { TV_DISPLAY_STATE_T tv_state; // get current display settings state memset(&tv_state, 0, sizeof(TV_DISPLAY_STATE_T)); m_DllBcmHost->vc_tv_get_display_state(&tv_state); if ((tv_state.state & ( VC_HDMI_HDMI | VC_HDMI_DVI )) != 0) // hdtv { m_desktopRes.iScreen = 0; m_desktopRes.bFullScreen = true; m_desktopRes.iWidth = tv_state.display.hdmi.width; m_desktopRes.iHeight = tv_state.display.hdmi.height; m_desktopRes.iScreenWidth = tv_state.display.hdmi.width; m_desktopRes.iScreenHeight= tv_state.display.hdmi.height; m_desktopRes.dwFlags = MAKEFLAGS(tv_state.display.hdmi.group, tv_state.display.hdmi.mode, tv_state.display.hdmi.scan_mode); m_desktopRes.fPixelRatio = get_display_aspect_ratio((HDMI_ASPECT_T)tv_state.display.hdmi.display_options.aspect) / ((float)m_desktopRes.iScreenWidth / (float)m_desktopRes.iScreenHeight); // Also add 3D flags if (tv_state.display.hdmi.format_3d == HDMI_3D_FORMAT_SBS_HALF) { m_desktopRes.dwFlags |= D3DPRESENTFLAG_MODE3DSBS; m_desktopRes.fPixelRatio *= 2.0; } else if (tv_state.display.hdmi.format_3d == HDMI_3D_FORMAT_TB_HALF) { m_desktopRes.dwFlags |= D3DPRESENTFLAG_MODE3DTB; m_desktopRes.fPixelRatio *= 0.5; } m_desktopRes.fRefreshRate = (float)tv_state.display.hdmi.frame_rate; } else // sdtv { m_desktopRes.iScreen = 0; m_desktopRes.bFullScreen = true; m_desktopRes.iWidth = tv_state.display.sdtv.width; m_desktopRes.iHeight = tv_state.display.sdtv.height; m_desktopRes.iScreenWidth = tv_state.display.sdtv.width; m_desktopRes.iScreenHeight= tv_state.display.sdtv.height; m_desktopRes.dwFlags = D3DPRESENTFLAG_INTERLACED; m_desktopRes.fRefreshRate = (float)tv_state.display.sdtv.frame_rate; m_desktopRes.fPixelRatio = get_display_aspect_ratio((SDTV_ASPECT_T)tv_state.display.sdtv.display_options.aspect) / ((float)m_desktopRes.iScreenWidth / (float)m_desktopRes.iScreenHeight); } m_desktopRes.strMode = StringUtils::Format("%dx%d", m_desktopRes.iScreenWidth, m_desktopRes.iScreenHeight); if((int)m_desktopRes.fRefreshRate > 1) { m_desktopRes.strMode = StringUtils::Format("%dx%d @ %.2f%s - Full Screen", m_desktopRes.iScreenWidth, m_desktopRes.iScreenHeight, m_desktopRes.fRefreshRate, m_desktopRes.dwFlags & D3DPRESENTFLAG_INTERLACED ? "i" : ""); } m_initDesktopRes = false; int gui_width = m_desktopRes.iWidth; int gui_height = m_desktopRes.iHeight; ClampToGUIDisplayLimits(gui_width, gui_height); m_desktopRes.iWidth = gui_width; m_desktopRes.iHeight = gui_height; m_desktopRes.iSubtitles = (int)(0.965 * m_desktopRes.iHeight); CLog::Log(LOGDEBUG, "EGL initial desktop resolution %s (%.2f)\n", m_desktopRes.strMode.c_str(), m_desktopRes.fPixelRatio); } GetSupportedModes(HDMI_RES_GROUP_CEA, resolutions); GetSupportedModes(HDMI_RES_GROUP_DMT, resolutions); if(resolutions.size() == 0) { RESOLUTION_INFO res; CLog::Log(LOGDEBUG, "EGL probe resolution %s:%x\n", m_desktopRes.strMode.c_str(), m_desktopRes.dwFlags); AddUniqueResolution(m_desktopRes, resolutions); } if(resolutions.size() < 2) m_fixedMode = true; DLOG("CEGLNativeTypeRaspberryPI::ProbeResolutions\n"); return true; #else return false; #endif }
void CEGLNativeTypeRaspberryPI::GetSupportedModes(HDMI_RES_GROUP_T group, std::vector<RESOLUTION_INFO> &resolutions) { if(!m_DllBcmHost) return; //Supported HDMI CEA/DMT resolutions, first one will be preferred resolution TV_SUPPORTED_MODE_T supported_modes[TV_MAX_SUPPORTED_MODES]; int32_t num_modes; HDMI_RES_GROUP_T prefer_group; uint32_t prefer_mode; int i; num_modes = m_DllBcmHost->vc_tv_hdmi_get_supported_modes(group, supported_modes, TV_MAX_SUPPORTED_MODES, &prefer_group, &prefer_mode); CLog::Log(LOGDEBUG, "EGL get supported modes (%d) = %d, prefer_group=%x, prefer_mode=%x\n", group, num_modes, prefer_group, prefer_mode); if (num_modes > 0 && prefer_group != HDMI_RES_GROUP_INVALID) { TV_SUPPORTED_MODE_T *tv = supported_modes; for (i=0; i < num_modes; i++, tv++) { // treat 3D modes as half-width SBS unsigned int width = (group == HDMI_RES_GROUP_CEA_3D) ? tv->width>>1 : tv->width; RESOLUTION_INFO res; CLog::Log(LOGDEBUG, "EGL mode %d: %dx%d@%d %s%s:%x\n", i, width, tv->height, tv->frame_rate, tv->native ? "N" : "", tv->scan_mode ? "I" : "", tv->code); res.iScreen = 0; res.bFullScreen = true; res.dwFlags = MAKEFLAGS(group, tv->code, tv->scan_mode, group==HDMI_RES_GROUP_CEA_3D); res.fRefreshRate = (float)tv->frame_rate; res.fPixelRatio = 1.0f; res.iWidth = width; res.iHeight = tv->height; res.iScreenWidth = width; res.iScreenHeight = tv->height; res.strMode.Format("%dx%d", width, tv->height); if((float)tv->frame_rate > 1) { res.strMode.Format("%dx%d @ %.2f%s - Full Screen", res.iScreenWidth, res.iScreenHeight, res.fRefreshRate, res.dwFlags & D3DPRESENTFLAG_INTERLACED ? "i" : ""); } int gui_width = res.iWidth; int gui_height = res.iHeight; ClampToGUIDisplayLimits(gui_width, gui_height); res.iWidth = gui_width; res.iHeight = gui_height; res.iSubtitles = (int)(0.965 * res.iHeight); resolutions.push_back(res); /* replace initial desktop resolution with probed hdmi resolution */ if(m_desktopRes.iWidth == res.iWidth && m_desktopRes.iHeight == res.iHeight && m_desktopRes.iScreenWidth == res.iScreenWidth && m_desktopRes.iScreenHeight == res.iScreenHeight && m_desktopRes.fRefreshRate == res.fRefreshRate) { m_desktopRes = res; CLog::Log(LOGDEBUG, "EGL desktop replacement resolution %dx%d@%d %s%s:%x\n", width, tv->height, tv->frame_rate, tv->native ? "N" : "", tv->scan_mode ? "I" : "", tv->code); } m_res.push_back(res); } }