qcom/display: Fix aspect ratio calculation for UI on HDMI

- Changed the aspect ratio of UI on HDMI based on the aspect
  ratio of the primary resolution.
- Remove the default values for action safe region.

Change-Id: I596611f8b01e6e1c1007ad7e6c323ea0ea710ec9
CRs-fixed: 323358
(cherry picked from commit b3c2e7f9d68db550f280ed60e37e7f4ee2a73058)

Conflicts:

	liboverlay/overlayLib.h
This commit is contained in:
Arun Kumar K.R 2012-01-17 21:23:58 -08:00 committed by Andrew Sutherland
parent 38e11bf7d4
commit 297e73b6a9
3 changed files with 126 additions and 190 deletions

View File

@ -54,15 +54,6 @@
#define FB_DEBUG 0
#if defined(HDMI_DUAL_DISPLAY)
#define AS_1080_RATIO_H (4.25/100) // Default Action Safe vertical limit for 1080p
#define AS_1080_RATIO_W (4.25/100) // Default Action Safe horizontal limit for 1080p
#define AS_720_RATIO_H (6.0/100) // Default Action Safe vertical limit for 720p
#define AS_720_RATIO_W (4.25/100) // Default Action Safe horizontal limit for 720p
#define AS_480_RATIO_H (8.0/100) // Default Action Safe vertical limit for 480p
#define AS_480_RATIO_W (5.0/100) // Default Action Safe horizontal limit for 480p
#define HEIGHT_1080P 1080
#define HEIGHT_720P 720
#define HEIGHT_480P 480
#define EVEN_OUT(x) if (x & 0x0001) {x--;}
using overlay::Overlay;
/** min of int a, b */
@ -220,6 +211,48 @@ static int closeHDMIChannel(private_module_t* m)
return 0;
}
static void getSecondaryDisplayDestinationInfo(private_module_t* m, overlay_rect&
rect, int& orientation)
{
Overlay* pTemp = m->pobjOverlay;
int width = pTemp->getFBWidth();
int height = pTemp->getFBHeight();
int fbwidth = m->info.xres, fbheight = m->info.yres;
rect.x = 0; rect.y = 0;
rect.w = width; rect.h = height;
int rot = m->orientation;
switch(rot) {
// ROT_0
case 0:
// ROT_180
case HAL_TRANSFORM_ROT_180:
pTemp->getAspectRatioPosition(fbwidth, fbheight,
&rect);
if(rot == HAL_TRANSFORM_ROT_180)
orientation = HAL_TRANSFORM_ROT_180;
else
orientation = 0;
break;
// ROT_90
case HAL_TRANSFORM_ROT_90:
// ROT_270
case HAL_TRANSFORM_ROT_270:
//Calculate the Aspectratio for the UI
//in the landscape mode
//Width and height will be swapped as there
//is rotation
pTemp->getAspectRatioPosition(fbheight, fbwidth,
&rect);
if(rot == HAL_TRANSFORM_ROT_90)
orientation = HAL_TRANSFORM_ROT_270;
else if(rot == HAL_TRANSFORM_ROT_270)
orientation = HAL_TRANSFORM_ROT_90;
break;
}
return;
}
static void *hdmi_ui_loop(void *ptr)
{
private_module_t* m = reinterpret_cast<private_module_t*>(
@ -233,8 +266,6 @@ static void *hdmi_ui_loop(void *ptr)
pthread_mutex_unlock(&m->overlayLock);
return NULL;
}
float asWidthRatio = m->actionsafeWidthRatio/100.0f;
float asHeightRatio = m->actionsafeHeightRatio/100.0f;
bool waitForVsync = true;
int flags = WAIT_FOR_VSYNC;
if (m->pobjOverlay) {
@ -266,101 +297,25 @@ static void *hdmi_ui_loop(void *ptr)
}
if (pTemp->isChannelUP()) {
int width = pTemp->getFBWidth();
int height = pTemp->getFBHeight();
int aswidth = width, asheight = height;
int asX = 0, asY = 0; // Action safe x, y co-ordinates
int fbwidth = m->info.xres, fbheight = m->info.yres;
float defaultASWidthRatio = 0.0f, defaultASHeightRatio = 0.0f;
// TODO: disable OverScan for now
if(!m->trueMirrorSupport) {
if(HEIGHT_1080P == height) {
defaultASHeightRatio = AS_1080_RATIO_H;
defaultASWidthRatio = AS_1080_RATIO_W;
} else if(HEIGHT_720P == height) {
defaultASHeightRatio = AS_720_RATIO_H;
defaultASWidthRatio = AS_720_RATIO_W;
} else if(HEIGHT_480P == height) {
defaultASHeightRatio = AS_480_RATIO_H;
defaultASWidthRatio = AS_480_RATIO_W;
}
if(asWidthRatio <= 0.0f)
asWidthRatio = defaultASWidthRatio;
if(asHeightRatio <= 0.0f)
asHeightRatio = defaultASHeightRatio;
}
aswidth = (int)((float)width - (float)(width * asWidthRatio));
asheight = (int)((float)height - (float)(height * asHeightRatio));
asX = (width - aswidth) / 2;
asY = (height - asheight) / 2;
int rot = m->orientation;
if (fbwidth < fbheight) {
switch(rot) {
// ROT_0
case 0:
// ROT_180
case HAL_TRANSFORM_ROT_180: {
aswidth = (asheight * fbwidth) / fbheight;
asX = (width - aswidth) / 2;
if(rot == HAL_TRANSFORM_ROT_180)
rot = OVERLAY_TRANSFORM_ROT_180;
else
rot = 0;
}
break;
// ROT_90
case HAL_TRANSFORM_ROT_90:
rot = OVERLAY_TRANSFORM_ROT_270;
break;
// ROT_270
case HAL_TRANSFORM_ROT_270:
rot = OVERLAY_TRANSFORM_ROT_90;
break;
}
}
else if (fbwidth > fbheight) {
switch(rot) {
// ROT_0
case 0:
rot = 0;
break;
// ROT_180
case HAL_TRANSFORM_ROT_180:
rot = OVERLAY_TRANSFORM_ROT_180;
break;
// ROT_90
case HAL_TRANSFORM_ROT_90:
// ROT_270
case HAL_TRANSFORM_ROT_270: {
//Swap width and height
int t = fbwidth;
fbwidth = fbheight;
fbheight = t;
aswidth = (asheight * fbwidth) / fbheight;
asX = (width - aswidth) / 2;
if(rot == HAL_TRANSFORM_ROT_90)
rot = OVERLAY_TRANSFORM_ROT_270;
else
rot = OVERLAY_TRANSFORM_ROT_90;
}
break;
}
}
overlay_rect destRect;
int rot = 0;
int currOrientation = 0;
getSecondaryDisplayDestinationInfo(m, destRect, rot);
pTemp->getOrientation(currOrientation);
if(rot != currOrientation) {
pTemp->setTransform(rot);
}
EVEN_OUT(asX);
EVEN_OUT(asY);
EVEN_OUT(aswidth);
EVEN_OUT(asheight);
EVEN_OUT(destRect.x);
EVEN_OUT(destRect.y);
EVEN_OUT(destRect.w);
EVEN_OUT(destRect.h);
int currentX = 0, currentY = 0;
uint32_t currentW = width, currentH = height;
uint32_t currentW = 0, currentH = 0;
if (pTemp->getPosition(currentX, currentY, currentW, currentH)) {
if ((currentX != asX) || (currentY != asY) || (currentW != aswidth)
|| (currentH != asheight)) {
pTemp->setPosition(asX, asY, aswidth, asheight);
if ((currentX != destRect.x) || (currentY != destRect.y) ||
(currentW != destRect.w) || (currentH != destRect.h)) {
pTemp->setPosition(destRect.x, destRect.y, destRect.w,
destRect.h);
}
}
if (m->trueMirrorSupport) {

View File

@ -471,16 +471,16 @@ bool Overlay::setDeviceOrientation(int orientation) {
bool Overlay::setPosition(int x, int y, uint32_t w, uint32_t h) {
bool ret = false;
overlay_rect rect;
overlay_rect inrect;
overlay_rect secDest;
overlay_rect priDest;
int currX, currY;
uint32_t currW, currH;
// Set even destination co-ordinates
EVEN_OUT(x); EVEN_OUT(y);
EVEN_OUT(w); EVEN_OUT(h);
objOvCtrlChannel[VG0_PIPE].getPosition(currX, currY, currW, currH);
inrect.x = x, inrect.y = y;
inrect.w = w, inrect.h = h;
priDest.x = x, priDest.y = y;
priDest.w = w, priDest.h = h;
if(x != currX || y != currY || w != currW || h != currH) {
switch (mState) {
case OV_UI_MIRROR_TV:
@ -490,27 +490,30 @@ bool Overlay::setPosition(int x, int y, uint32_t w, uint32_t h) {
break;
case OV_2D_VIDEO_ON_TV:
if (FrameBufferInfo::getInstance()->canSupportTrueMirroring()) {
objOvCtrlChannel[VG1_PIPE].getAspectRatioPosition(mCroppedSrcWidth,
mCroppedSrcHeight, mDevOrientation, &inrect, &rect);
objOvCtrlChannel[VG1_PIPE].getAspectRatioPosition(
mCroppedSrcWidth, mCroppedSrcHeight, mDevOrientation,
&priDest, &secDest);
} else {
objOvCtrlChannel[VG1_PIPE].getAspectRatioPosition(mCroppedSrcWidth,
mCroppedSrcHeight, &rect);
objOvCtrlChannel[VG1_PIPE].getAspectRatioPosition(
mCroppedSrcWidth, mCroppedSrcHeight, &secDest);
}
setChannelPosition(rect.x, rect.y, rect.w, rect.h, VG1_PIPE);
setChannelPosition(secDest.x, secDest.y, secDest.w, secDest.h,
VG1_PIPE);
return setChannelPosition(x, y, w, h, VG0_PIPE);
break;
case OV_3D_VIDEO_3D_PANEL:
for (int i = 0; i < NUM_CHANNELS; i++) {
if (sHDMIAsPrimary)
objOvCtrlChannel[i].getPositionS3D(i, mS3DFormat, &rect);
objOvCtrlChannel[i].getPositionS3D(i, mS3DFormat, &secDest);
else {
if (!objOvCtrlChannel[i].useVirtualFB()) {
LOGE("%s: failed virtual fb for channel %d", __FUNCTION__, i);
return false;
}
objOvCtrlChannel[i].getPositionS3D(i, 0x1, &rect);
objOvCtrlChannel[i].getPositionS3D(i, 0x1, &secDest);
}
if(!setChannelPosition(rect.x, rect.y, rect.w, rect.h, i)) {
if(!setChannelPosition(secDest.x, secDest.y, secDest.w,
secDest.h, i)) {
LOGE("%s: failed for channel %d", __FUNCTION__, i);
return false;
}
@ -519,11 +522,13 @@ bool Overlay::setPosition(int x, int y, uint32_t w, uint32_t h) {
case OV_3D_VIDEO_2D_TV:
case OV_3D_VIDEO_3D_TV:
for (int i = 0; i < NUM_CHANNELS; i++) {
ret = objOvCtrlChannel[i].getPositionS3D(i, mS3DFormat, &rect);
ret = objOvCtrlChannel[i].getPositionS3D(i, mS3DFormat,
&secDest);
if (!ret)
ret = setChannelPosition(x, y, w, h, i);
else
ret = setChannelPosition(rect.x, rect.y, rect.w, rect.h, i);
ret = setChannelPosition(secDest.x, secDest.y, secDest.w,
secDest.h, i);
if (!ret) {
LOGE("%s: failed for channel %d", __FUNCTION__, i);
return ret;
@ -615,6 +620,10 @@ bool Overlay::updateOverlaySource(const overlay_buffer_info& info, int orientati
return ret;
}
bool Overlay::getAspectRatioPosition(int w, int h, overlay_rect *rect, int channel) {
return objOvCtrlChannel[channel].getAspectRatioPosition(w, h, rect);
}
int Overlay::getS3DFormat(int format) {
// The S3D is part of the HAL_PIXEL_FORMAT_YV12 value. Add
// an explicit check for the format
@ -754,7 +763,6 @@ bool Overlay::setCrop(uint32_t x, uint32_t y, uint32_t w, uint32_t h) {
inRect.x = x; inRect.y = y; inRect.w = w; inRect.h = h;
mCroppedSrcWidth = w;
mCroppedSrcHeight = h;
switch (mState) {
case OV_UI_MIRROR_TV:
case OV_2D_VIDEO_ON_PANEL:
@ -957,6 +965,15 @@ bool OverlayControlChannel::getAspectRatioPosition(int w, int h, overlay_rect *r
}
if (width > fbWidth) width = fbWidth;
if (height > fbHeight) height = fbHeight;
char value[PROPERTY_VALUE_MAX];
property_get("hw.actionsafe.width", value, "0");
float asWidth = atof(value);
property_get("hw.actionsafe.height", value, "0");
float asHeight = atof(value);
width = width * (1.0f - asWidth / 100.0f);
height = height * (1.0f - asHeight / 100.0f);
x = (fbWidth - width) / 2;
y = (fbHeight - height) / 2;
rect->x = x;
@ -968,7 +985,7 @@ bool OverlayControlChannel::getAspectRatioPosition(int w, int h, overlay_rect *r
// This function gets the destination position for Seconday display
// based on the aspect ratio of the primary
// based on the position and aspect ratio of the primary
bool OverlayControlChannel::getAspectRatioPosition(int w, int h, int orientation,
overlay_rect *inRect, overlay_rect *outRect) {
float priWidth = FrameBufferInfo::getInstance()->getWidth();
@ -981,73 +998,51 @@ bool OverlayControlChannel::getAspectRatioPosition(int w, int h, int orientation
float yRatio = 1.0;
int xPos = 0;
int yPos = 0;
int tmp = 0;
float actualWidth = fbWidth;
if(priWidth < priHeight) {
switch(orientation) {
case MDP_ROT_NOP:
actualWidth = (fbHeight * priWidth) / priHeight;
xPos = (fbWidth - actualWidth) / 2;
break;
case MDP_ROT_180:
actualWidth = (fbHeight * priWidth) / priHeight;
xPos = (fbWidth - actualWidth) / 2;
overlay_rect rect;
switch(orientation) {
case MDP_ROT_NOP:
case MDP_ROT_180:
getAspectRatioPosition((int)priWidth, (int)priHeight, &rect);
xPos = rect.x;
yPos = rect.y;
fbWidth = rect.w;
fbHeight = rect.h;
actualWidth = fbWidth;
if(orientation == MDP_ROT_180) {
inRect->x = priWidth - (inRect->x + inRect->w);
inRect->y = priHeight - (inRect->y + inRect->h);
break;
case MDP_ROT_90:
}
break;
case MDP_ROT_90:
case MDP_ROT_270:
// Swap width/height for primary
swapWidthHeight(priWidth, priHeight);
//Swap the destination width/height
swapWidthHeight(inRect->w, inRect->h);
getAspectRatioPosition((int)priWidth, (int)priHeight, &rect);
xPos = rect.x;
yPos = rect.y;
fbWidth = rect.w;
actualWidth = fbWidth;
fbHeight = rect.h;
if(orientation == MDP_ROT_90) {
tmp = inRect->y;
inRect->y = priWidth - (inRect->x + inRect->w);
inRect->x = tmp;
// Swap width/height for primary
swapWidthHeight(priWidth, priHeight);
//Swap the destination width/height
swapWidthHeight(inRect->w, inRect->h);
break;
case MDP_ROT_270:
}
else if(orientation == MDP_ROT_270) {
tmp = inRect->x;
inRect->x = priHeight - (inRect->y + inRect->h);
inRect->y = tmp;
// Swap width/height for primary
swapWidthHeight(priWidth, priHeight);
//Swap the destination width/height
swapWidthHeight(inRect->w, inRect->h);
break;
default:
LOGE("In %s: Portrait: Unknown Orientation", __FUNCTION__);
break;
}
} else {
switch(orientation) {
case MDP_ROT_NOP:
break;
case MDP_ROT_180:
inRect->x = priWidth - (inRect->x + inRect->w);
inRect->y = priHeight - (inRect->y + inRect->h);
break;
case MDP_ROT_90:
case MDP_ROT_270:
// Swap width/height for primary
swapWidthHeight(priWidth, priHeight);
//Swap the destination width/height
swapWidthHeight(inRect->w, inRect->h);
actualWidth = ( fbHeight * priWidth) / priHeight;
xPos = (fbWidth - actualWidth) / 2;
if(orientation == MDP_ROT_90) {
tmp = inRect->y;
inRect->y = priWidth - (inRect->x + inRect->w);
inRect->x = tmp;
}
else if(orientation == MDP_ROT_270) {
tmp = inRect->x;
inRect->x = priHeight - (inRect->y + inRect->h);
inRect->y = tmp;
}
break;
default:
LOGE("In %s: Landscape: Unknown Orientation", __FUNCTION__);
break;
}
}
break;
default:
LOGE("In %s: Unknown Orientation", __FUNCTION__);
break;
}
//Calculate the position...
xRatio = inRect->x/priWidth;
@ -1055,12 +1050,12 @@ bool OverlayControlChannel::getAspectRatioPosition(int w, int h, int orientation
wRatio = inRect->w/priWidth;
hRatio = inRect->h/priHeight;
outRect->x = (xRatio * fbWidth) + xPos;
outRect->y = yRatio * fbHeight;
outRect->x = (xRatio * actualWidth) + xPos;
outRect->y = (yRatio * fbHeight) + yPos;
outRect->w = (wRatio * actualWidth);
outRect->h = hRatio * fbHeight;
LOGE("Calculated AS Position for HDMI: X= %d, y = %d w = %d h = %d",
LOGD("Calculated AS Position for HDMI: X= %d, y = %d w = %d h = %d",
outRect->x, outRect->y,outRect->w, outRect->h);
return true;
}

View File

@ -137,20 +137,6 @@ struct overlay_buffer_info {
bool secure;
};
/* values for copybit_set_parameter(OVERLAY_TRANSFORM) */
enum {
/* flip source image horizontally */
OVERLAY_TRANSFORM_FLIP_H = HAL_TRANSFORM_FLIP_H,
/* flip source image vertically */
OVERLAY_TRANSFORM_FLIP_V = HAL_TRANSFORM_FLIP_V,
/* rotate source image 90 degrees */
OVERLAY_TRANSFORM_ROT_90 = HAL_TRANSFORM_ROT_90,
/* rotate source image 180 degrees */
OVERLAY_TRANSFORM_ROT_180 = HAL_TRANSFORM_ROT_180,
/* rotate source image 270 degrees */
OVERLAY_TRANSFORM_ROT_270 = HAL_TRANSFORM_ROT_270
};
using android::Mutex;
namespace overlay {
//Utility Class to query the framebuffer info
@ -435,13 +421,13 @@ public:
bool queueBuffer(buffer_handle_t buffer);
bool setSource(const overlay_buffer_info& info, int orientation, int hdmiConnected,
int flags, int numBuffers = 2);
bool getAspectRatioPosition(int w, int h, overlay_rect *rect, int channel = 0);
bool setCrop(uint32_t x, uint32_t y, uint32_t w, uint32_t h);
bool updateOverlayFlags(int flags);
void setVisualParam(int8_t paramType, float paramValue);
bool waitForHdmiVsync(int channel);
int getChannelStatus() const { return (mChannelUP ? OVERLAY_CHANNEL_UP: OVERLAY_CHANNEL_DOWN); }
void closeExternalChannel();
private:
bool setChannelPosition(int x, int y, uint32_t w, uint32_t h, int channel = 0);
bool setChannelCrop(uint32_t x, uint32_t y, uint32_t w, uint32_t h, int channel);