Add support for creating a Surface from a a SurfaceTexture.

The Surface is already using SurfaceTexture internally and it is parcelable. This
is intended to replace and phase out ParcelSurfaceTexture in favor of creating a
new Surface.java object from an existing SurfaceTexture.

Change-Id: I8e2dd86614523da6abed6403e1d705a68fa19fdf
This commit is contained in:
Ted Bonkenburg 2011-07-15 15:10:10 -07:00
parent 97532391ed
commit bd050ab2af
2 changed files with 47 additions and 16 deletions

View File

@ -122,7 +122,10 @@ public:
uint32_t reserved[2];
};
explicit Surface(const sp<ISurfaceTexture>& st);
static status_t writeToParcel(const sp<Surface>& control, Parcel* parcel);
static sp<Surface> readFromParcel(const Parcel& data);
static bool isValid(const sp<Surface>& surface) {
return (surface != 0) && surface->isValid();
@ -147,14 +150,14 @@ private:
Surface& operator = (Surface& rhs);
Surface(const Surface& rhs);
Surface(const sp<SurfaceControl>& control);
explicit Surface(const sp<SurfaceControl>& control);
Surface(const Parcel& data, const sp<IBinder>& ref);
~Surface();
/*
* private stuff...
*/
void init();
void init(const sp<ISurfaceTexture>& surfaceTexture);
static void cleanCachedSurfacesLocked();

View File

@ -184,6 +184,7 @@ status_t SurfaceControl::writeSurfaceToParcel(
identity = control->mIdentity;
}
parcel->writeStrongBinder(sur!=0 ? sur->asBinder() : NULL);
parcel->writeStrongBinder(NULL); // NULL ISurfaceTexture in this case.
parcel->writeInt32(identity);
return NO_ERROR;
}
@ -192,7 +193,8 @@ sp<Surface> SurfaceControl::getSurface() const
{
Mutex::Autolock _l(mLock);
if (mSurfaceData == 0) {
mSurfaceData = new Surface(const_cast<SurfaceControl*>(this));
sp<SurfaceControl> surface_control(const_cast<SurfaceControl*>(this));
mSurfaceData = new Surface(surface_control);
}
return mSurfaceData;
}
@ -208,31 +210,58 @@ Surface::Surface(const sp<SurfaceControl>& surface)
mSurface(surface->mSurface),
mIdentity(surface->mIdentity)
{
init();
sp<ISurfaceTexture> st;
if (mSurface != NULL) {
st = mSurface->getSurfaceTexture();
}
init(st);
}
Surface::Surface(const Parcel& parcel, const sp<IBinder>& ref)
: SurfaceTextureClient()
{
mSurface = interface_cast<ISurface>(ref);
mSurface = interface_cast<ISurface>(ref);
sp<IBinder> st_binder(parcel.readStrongBinder());
sp<ISurfaceTexture> st;
if (st_binder != NULL) {
st = interface_cast<ISurfaceTexture>(st_binder);
} else if (mSurface != NULL) {
st = mSurface->getSurfaceTexture();
}
mIdentity = parcel.readInt32();
init();
init(st);
}
Surface::Surface(const sp<ISurfaceTexture>& st)
: SurfaceTextureClient(),
mSurface(NULL),
mIdentity(0)
{
init(st);
}
status_t Surface::writeToParcel(
const sp<Surface>& surface, Parcel* parcel)
{
sp<ISurface> sur;
sp<ISurfaceTexture> st;
uint32_t identity = 0;
if (Surface::isValid(surface)) {
sur = surface->mSurface;
st = surface->getISurfaceTexture();
identity = surface->mIdentity;
} else if (surface != 0 && surface->mSurface != 0) {
LOGW("Parceling invalid surface with non-NULL ISurface as NULL: "
"mSurface = %p, mIdentity = %d",
surface->mSurface.get(), surface->mIdentity);
} else if (surface != 0 &&
(surface->mSurface != NULL ||
surface->getISurfaceTexture() != NULL)) {
LOGE("Parceling invalid surface with non-NULL ISurface/ISurfaceTexture as NULL: "
"mSurface = %p, surfaceTexture = %p, mIdentity = %d, ",
surface->mSurface.get(), surface->getISurfaceTexture().get(),
surface->mIdentity);
}
parcel->writeStrongBinder(sur!=0 ? sur->asBinder() : NULL);
parcel->writeStrongBinder(sur != NULL ? sur->asBinder() : NULL);
parcel->writeStrongBinder(st != NULL ? st->asBinder() : NULL);
parcel->writeInt32(identity);
return NO_ERROR;
@ -249,8 +278,8 @@ sp<Surface> Surface::readFromParcel(const Parcel& data) {
surface = new Surface(data, binder);
sCachedSurfaces.add(binder, surface);
}
if (surface->mSurface == 0) {
surface = 0;
if (surface->mSurface == NULL && surface->getISurfaceTexture() == NULL) {
surface = 0;
}
cleanCachedSurfacesLocked();
return surface;
@ -267,10 +296,9 @@ void Surface::cleanCachedSurfacesLocked() {
}
}
void Surface::init()
void Surface::init(const sp<ISurfaceTexture>& surfaceTexture)
{
if (mSurface != NULL) {
sp<ISurfaceTexture> surfaceTexture(mSurface->getSurfaceTexture());
if (mSurface != NULL || surfaceTexture != NULL) {
LOGE_IF(surfaceTexture==0, "got a NULL ISurfaceTexture from ISurface");
if (surfaceTexture != NULL) {
setISurfaceTexture(surfaceTexture);