hwc: Add support for plane alpha

HWC 1.2 API passes down the plane alpha and the blending
operation to apply. Pass this information to the MDP.

Change-Id: I7fbd17345d9157aa654e4b1031ac3e26adf87f37
This commit is contained in:
Naseer Ahmed
2013-03-18 20:14:05 -04:00
committed by Gerrit - the friendly Code Review server
parent e36a9c2f1a
commit 522ce66a3e
7 changed files with 87 additions and 14 deletions

View File

@@ -751,7 +751,7 @@ static int hwc_device_open(const struct hw_module_t* module, const char* name,
//Setup HWC methods
dev->device.common.tag = HARDWARE_DEVICE_TAG;
dev->device.common.version = HWC_DEVICE_API_VERSION_1_1;
dev->device.common.version = HWC_DEVICE_API_VERSION_1_2;
dev->device.common.module = const_cast<hw_module_t*>(module);
dev->device.common.close = hwc_device_close;
dev->device.prepare = hwc_prepare;

View File

@@ -171,7 +171,10 @@ bool FBUpdateLowRes::configure(hwc_context_t *ctx, hwc_display_contents_1 *list,
orient = ovutils::OVERLAY_TRANSFORM_0;
transform = 0;
ovutils::PipeArgs parg(mdpFlags, info, zOrder, isFg,
static_cast<ovutils::eRotFlags>(rotFlags));
static_cast<ovutils::eRotFlags>(rotFlags),
ovutils::DEFAULT_PLANE_ALPHA,
(ovutils::eBlending)
getBlending(layer->blending));
ret = true;
if(configMdp(ctx->mOverlay, parg, orient, sourceCrop, displayFrame,
NULL, mDest) < 0) {
@@ -268,11 +271,16 @@ bool FBUpdateHighRes::configure(hwc_context_t *ctx,
ovutils::eZorder zOrder = static_cast<ovutils::eZorder>(fbZorder);
//XXX: FB layer plane alpha is currently sent as zero from
//surfaceflinger
ovutils::PipeArgs pargL(mdpFlagsL,
info,
zOrder,
ovutils::IS_FG_OFF,
ovutils::ROT_FLAGS_NONE);
ovutils::ROT_FLAGS_NONE,
ovutils::DEFAULT_PLANE_ALPHA,
(ovutils::eBlending)
getBlending(layer->blending));
ov.setSource(pargL, destL);
ovutils::eMdpFlags mdpFlagsR = mdpFlagsL;
@@ -281,7 +289,10 @@ bool FBUpdateHighRes::configure(hwc_context_t *ctx,
info,
zOrder,
ovutils::IS_FG_OFF,
ovutils::ROT_FLAGS_NONE);
ovutils::ROT_FLAGS_NONE,
ovutils::DEFAULT_PLANE_ALPHA,
(ovutils::eBlending)
getBlending(layer->blending));
ov.setSource(pargR, destR);
hwc_rect_t sourceCrop = layer->sourceCrop;

View File

@@ -545,6 +545,18 @@ bool isSecureModePolicy(int mdpVersion) {
return false;
}
int getBlending(int blending) {
switch(blending) {
case HWC_BLENDING_NONE:
return overlay::utils::OVERLAY_BLENDING_OPAQUE;
case HWC_BLENDING_PREMULT:
return overlay::utils::OVERLAY_BLENDING_PREMULT;
case HWC_BLENDING_COVERAGE :
default:
return overlay::utils::OVERLAY_BLENDING_COVERAGE;
}
}
//Crops source buffer against destination and FB boundaries
void calculate_crop_rects(hwc_rect_t& crop, hwc_rect_t& dst,
const hwc_rect_t& scissor, int orient) {
@@ -1035,7 +1047,10 @@ int configureLowRes(hwc_context_t *ctx, hwc_layer_1_t *layer,
//For the mdp, since either we are pre-rotating or MDP does flips
orient = OVERLAY_TRANSFORM_0;
transform = 0;
PipeArgs parg(mdpFlags, whf, z, isFg, static_cast<eRotFlags>(rotFlags));
PipeArgs parg(mdpFlags, whf, z, isFg,
static_cast<eRotFlags>(rotFlags), layer->planeAlpha,
(ovutils::eBlending) getBlending(layer->blending));
if(configMdp(ctx->mOverlay, parg, orient, crop, dst, metadata, dest) < 0) {
ALOGE("%s: commit failed for low res panel", __FUNCTION__);
return -1;
@@ -1164,7 +1179,9 @@ int configureHighRes(hwc_context_t *ctx, hwc_layer_1_t *layer,
//configure left mixer
if(lDest != OV_INVALID) {
PipeArgs pargL(mdpFlagsL, whf, z, isFg,
static_cast<eRotFlags>(rotFlags));
static_cast<eRotFlags>(rotFlags), layer->planeAlpha,
(ovutils::eBlending) getBlending(layer->blending));
if(configMdp(ctx->mOverlay, pargL, orient,
tmp_cropL, tmp_dstL, metadata, lDest) < 0) {
ALOGE("%s: commit failed for left mixer config", __FUNCTION__);
@@ -1175,7 +1192,9 @@ int configureHighRes(hwc_context_t *ctx, hwc_layer_1_t *layer,
//configure right mixer
if(rDest != OV_INVALID) {
PipeArgs pargR(mdpFlagsR, whf, z, isFg,
static_cast<eRotFlags>(rotFlags));
static_cast<eRotFlags>(rotFlags),
layer->planeAlpha,
(ovutils::eBlending) getBlending(layer->blending));
tmp_dstR.right = tmp_dstR.right - lSplit;
tmp_dstR.left = tmp_dstR.left - lSplit;
if(configMdp(ctx->mOverlay, pargR, orient,

View File

@@ -170,6 +170,7 @@ bool isExternalActive(hwc_context_t* ctx);
bool needsScaling(hwc_context_t* ctx, hwc_layer_1_t const* layer, const int& dpy);
bool isAlphaPresent(hwc_layer_1_t const* layer);
int hwc_vsync_control(hwc_context_t* ctx, int dpy, int enable);
int getBlending(int blending);
//Helper function to dump logs
void dumpsys_log(android::String8& buf, const char* fmt, ...);
@@ -275,8 +276,7 @@ void init_uevent_thread(hwc_context_t* ctx);
void init_vsync_thread(hwc_context_t* ctx);
inline void getLayerResolution(const hwc_layer_1_t* layer,
int& width, int& height)
{
int& width, int& height) {
hwc_rect_t displayFrame = layer->displayFrame;
width = displayFrame.right - displayFrame.left;
height = displayFrame.bottom - displayFrame.top;

View File

@@ -94,13 +94,14 @@ void MdpCtrl::setSource(const utils::PipeArgs& args) {
setSrcWhf(args.whf);
//TODO These are hardcoded. Can be moved out of setSource.
mOVInfo.alpha = 0xff;
mOVInfo.transp_mask = 0xffffffff;
//TODO These calls should ideally be a part of setPipeParams API
setFlags(args.mdpFlags);
setZ(args.zorder);
setIsFg(args.isFg);
setPlaneAlpha(args.planeAlpha);
setBlending(args.blending);
}
void MdpCtrl::setCrop(const utils::Dim& d) {

View File

@@ -101,6 +101,11 @@ private:
void setIsFg(utils::eIsFg isFg);
/* return a copy of src whf*/
utils::Whf getSrcWhf() const;
/* set plane alpha */
void setPlaneAlpha(int planeAlpha);
/* set blending method */
void setBlending(overlay::utils::eBlending blending);
/* set src whf */
void setSrcWhf(const utils::Whf& whf);
/* set src/dst rect dim */
@@ -241,6 +246,24 @@ inline void MdpCtrl::setDownscale(int dscale) {
mDownscale = dscale;
}
inline void MdpCtrl::setPlaneAlpha(int planeAlpha) {
mOVInfo.alpha = planeAlpha;
}
inline void MdpCtrl::setBlending(overlay::utils::eBlending blending) {
switch((int) blending) {
case utils::OVERLAY_BLENDING_OPAQUE:
mOVInfo.blend_op = BLEND_OP_OPAQUE;
break;
case utils::OVERLAY_BLENDING_PREMULT:
mOVInfo.blend_op = BLEND_OP_PREMULTIPLIED;
break;
case utils::OVERLAY_BLENDING_COVERAGE:
default:
mOVInfo.blend_op = BLEND_OP_COVERAGE;
}
}
inline bool MdpCtrl::ovChanged() const {
#ifdef USES_POST_PROCESSING
// Some pp params are stored as pointer address,

View File

@@ -212,6 +212,8 @@ struct Whf {
enum { MAX_PATH_LEN = 256 };
enum { DEFAULT_PLANE_ALPHA = 0xFF };
/**
* Rotator flags: not to be confused with orientation flags.
* Usually, you want to open the rotator to make sure it is
@@ -329,21 +331,36 @@ enum eTransform {
OVERLAY_TRANSFORM_INV = 0x80
};
enum eBlending {
OVERLAY_BLENDING_UNDEFINED = 0x0,
/* No blending */
OVERLAY_BLENDING_OPAQUE,
/* src.rgb + dst.rgb*(1-src_alpha) */
OVERLAY_BLENDING_PREMULT,
/* src.rgb * src_alpha + dst.rgb (1 - src_alpha) */
OVERLAY_BLENDING_COVERAGE,
};
// Used to consolidate pipe params
struct PipeArgs {
PipeArgs() : mdpFlags(OV_MDP_FLAGS_NONE),
zorder(Z_SYSTEM_ALLOC),
isFg(IS_FG_OFF),
rotFlags(ROT_FLAGS_NONE){
rotFlags(ROT_FLAGS_NONE),
planeAlpha(DEFAULT_PLANE_ALPHA),
blending(OVERLAY_BLENDING_COVERAGE){
}
PipeArgs(eMdpFlags f, Whf _whf,
eZorder z, eIsFg fg, eRotFlags r) :
eZorder z, eIsFg fg, eRotFlags r,
int pA = DEFAULT_PLANE_ALPHA, eBlending b = OVERLAY_BLENDING_COVERAGE) :
mdpFlags(f),
whf(_whf),
zorder(z),
isFg(fg),
rotFlags(r) {
rotFlags(r),
planeAlpha(pA),
blending(b){
}
eMdpFlags mdpFlags; // for mdp_overlay flags
@@ -351,6 +368,8 @@ struct PipeArgs {
eZorder zorder; // stage number
eIsFg isFg; // control alpha & transp
eRotFlags rotFlags;
int planeAlpha;
eBlending blending;
};
// Cannot use HW_OVERLAY_MAGNIFICATION_LIMIT, since at the time