mName("unnamed"),
mDebug(false),
mFormat(PIXEL_FORMAT_NONE),
- mOpaqueLayer(true),
mTransactionFlags(0),
mQueuedFrames(0),
mCurrentTransform(0),
uint32_t layerFlags = 0;
if (flags & ISurfaceComposerClient::eHidden)
- layerFlags = layer_state_t::eLayerHidden;
+ layerFlags |= layer_state_t::eLayerHidden;
+ if (flags & ISurfaceComposerClient::eOpaque)
+ layerFlags |= layer_state_t::eLayerOpaque;
if (flags & ISurfaceComposerClient::eNonPremultiplied)
mPremultipliedAlpha = false;
mSecure = (flags & ISurfaceComposerClient::eSecure) ? true : false;
mProtectedByApp = (flags & ISurfaceComposerClient::eProtectedByApp) ? true : false;
- mOpaqueLayer = (flags & ISurfaceComposerClient::eOpaque);
mCurrentOpacity = getOpacityForFormat(format);
mSurfaceFlingerConsumer->setDefaultBufferSize(w, h);
// this gives us only the "orientation" component of the transform
const State& s(getDrawingState());
- if (!isOpaque() || s.alpha != 0xFF) {
+ if (!isOpaque(s) || s.alpha != 0xFF) {
layer.setBlending(mPremultipliedAlpha ?
HWC_BLENDING_PREMULT :
HWC_BLENDING_COVERAGE);
texCoords[3] = vec2(right, 1.0f - top);
RenderEngine& engine(mFlinger->getRenderEngine());
- engine.setupLayerBlending(mPremultipliedAlpha, isOpaque(), s.alpha);
+ engine.setupLayerBlending(mPremultipliedAlpha, isOpaque(s), s.alpha);
engine.drawMesh(mMesh);
engine.disableBlending();
}
}
}
-bool Layer::isOpaque() const
+bool Layer::isOpaque(const Layer::State& s) const
{
// if we don't have a buffer yet, we're translucent regardless of the
// layer's opaque flag.
// if the layer has the opaque flag, then we're always opaque,
// otherwise we use the current buffer's format.
- return mOpaqueLayer || mCurrentOpacity;
+ return ((s.flags & layer_state_t::eLayerOpaque) != 0) || mCurrentOpacity;
}
bool Layer::isProtected() const
}
// Capture the old state of the layer for comparisons later
- const bool oldOpacity = isOpaque();
+ const State& s(getDrawingState());
+ const bool oldOpacity = isOpaque(s);
sp<GraphicBuffer> oldActiveBuffer = mActiveBuffer;
struct Reject : public SurfaceFlingerConsumer::BufferRejecter {
}
mCurrentOpacity = getOpacityForFormat(mActiveBuffer->format);
- if (oldOpacity != isOpaque()) {
+ if (oldOpacity != isOpaque(s)) {
recomputeVisibleRegions = true;
}
// FIXME: postedRegion should be dirty & bounds
- const Layer::State& s(getDrawingState());
Region dirtyRegion(Rect(s.active.w, s.active.h));
// transform the dirty region to window-manager space
s.layerStack, s.z, s.transform.tx(), s.transform.ty(), s.active.w, s.active.h,
s.active.crop.left, s.active.crop.top,
s.active.crop.right, s.active.crop.bottom,
- isOpaque(), contentDirty,
+ isOpaque(s), contentDirty,
s.alpha, s.flags,
s.transform[0][0], s.transform[0][1],
s.transform[1][0], s.transform[1][1],
// handle hidden surfaces by setting the visible region to empty
if (CC_LIKELY(layer->isVisible())) {
- const bool translucent = !layer->isOpaque();
+ const bool translucent = !layer->isOpaque(s);
Rect bounds(s.transform.transform(layer->computeBounds()));
visibleRegion.set(bounds);
if (!visibleRegion.isEmpty()) {
const Layer::State& state(layer->getDrawingState());
if ((cur->getHints() & HWC_HINT_CLEAR_FB)
&& i
- && layer->isOpaque() && (state.alpha == 0xFF)
+ && layer->isOpaque(state) && (state.alpha == 0xFF)
&& hasGlesComposition) {
// never clear the very first layer since we're
// guaranteed the FB is already cleared
if (layer->setTransparentRegionHint(s.transparentRegion))
flags |= eTraversalNeeded;
}
- if (what & layer_state_t::eVisibilityChanged) {
+ if ((what & layer_state_t::eVisibilityChanged) ||
+ (what & layer_state_t::eOpacityChanged)) {
+ // TODO: should we just use an eFlagsChanged for this?
if (layer->setFlags(s.flags, s.mask))
flags |= eTraversalNeeded;
}