androidsurfaceviewhere-apiaidlsurfaceholder

How to pass SurfaceHolder via AIDL?


I have 2 separate Android app (apk).

App 1 creates SurfaceView inside it and should provide AIDL methods for other apps to obtain an instance of SurfaceHolder for such SurfaceView. So the other apps will be able to draw on that view, displayed inside app number 1.

I was able to transfer Surface itself via aidl easily, since it implements Parcelable interface.

// IMainService.aidl
package com.commonsware.cwac.preso.demo.service;
import android.view.Surface;

interface IMainService {
    Surface getSurf();
}

But 3-rd party sdk need SurfaceHolder to draw on. So the question is - how can I create SurfaceHolder for a given Surface instance, or how can I transfer SurfaceHolder via AIDL. Is there any examples of how I can implement Parcelable for SurfaceHolder?

My use-case (if its matter): App 1 starts as a Service and draw UI on Presentation Screen. And I need a way to get another apps display Navigation Data via Nokia Here Mobile SDK inside app 1. I need SurfaceHolder in order to use this api.

Any help will be appreciated.


Solution

  • After a while, finally create a solution that works well with Here OffscreenRender API.

    At one app I create SurfaceHolder and this app provide AIDL (see at the post above). With this AIDL I was able to correctly send Surface object and then, on app 2 side, make SurfaceHolder from it.

    public class MySurfaceHolder implements SurfaceHolder {
    
    private Surface surface;
    private Rect rect;
    
    MySurfaceHolder(Surface surface, Rect rect) {
        this.surface = surface;
        this.rect = rect;
    }
    
    ///....
    
    @Override
    public Canvas lockCanvas() {
        return surface.lockCanvas(this.rect);
    }
    
    @Override
    public Canvas lockCanvas(Rect rect) {
        return surface.lockCanvas(rect);
    }
    
    @Override
    public void unlockCanvasAndPost(Canvas canvas) {
        surface.unlockCanvasAndPost(canvas);
    }
    
    @Override
    public Rect getSurfaceFrame() {
        return rect;
    }
    
    @Override
    public Surface getSurface() {
        return surface;
    }
    }
    

    Basically, its my own SurfaceHolder, which get initialized by my own, instead of system. This approach need extend AIDL to be able to request Rect sizes, as well.

    Hope that will be helpful for someone.