我正致力于从网络流式传输视频。我在本机代码中解码视频/音频内容并获取视频的原始像素
我在java代码中创建一个位图,使用surfaceholder和canvas,并从本机代码更新每个位图的像素,然后将位图作为视频流传输。我的问题是,由于内存不足,视频会在几秒钟后崩溃。
我想知道是否有任何我需要确保不会崩溃应用程序并使用低内存。
这是我的代码。
public CanvasThread(SurfaceHolder surfaceHolder, Panel panel) {
_surfaceHolder = surfaceHolder;
_panel = panel; }
public void setRunning(boolean run) {
_run = run; }
@Override
public void run() {
Canvas c;
while (_run) {
c = null;
try {
c = _surfaceHolder.lockCanvas(null);
synchronized (_surfaceHolder) {
_panel.onDraw(c);
}
} finally {
if (c != null) {
_surfaceHolder.unlockCanvasAndPost(c);
}
}
public class Panel extends SurfaceView implements SurfaceHolder.Callback{
private CanvasThread canvasthread;
private static Bitmap mBitmap;
private static boolean ii=false;
public Panel(Context context, AttributeSet attrs) {
super(context, attrs);
getHolder().addCallback(this);
canvasthread = new CanvasThread(getHolder(), this);
setFocusable(true);
mBitmap=Bitmap.createBitmap(480, 320, Bitmap.Config.RGB_565);//bitmap created in constructor
}
public Panel(Context context) {
super(context);
getHolder().addCallback(this);
canvasthread = new CanvasThread(getHolder(), this);
setFocusable(true);
}
private static native void renderbitmap(Bitmap bitmap); //native function
@Override
public void onDraw(Canvas canvas) {
renderbitmap(mBitmap); //Update pixels from native code
canvas.drawBitmap(mBitmap, 0,0,null);//draw on canvas
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width,int height) { }
@Override
public void surfaceCreated(SurfaceHolder holder) {
canvasthread.setRunning(true);
canvasthread.start(); }
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
boolean retry = true;
canvasthread.setRunning(false);
while (retry) {
try {
canvasthread.join();
retry = false;
} catch (InterruptedException e) { }
}
答案 0 :(得分:1)
这可能不会因为你的内存量有限。仿真器可能大约为16MB。您不应将所有图像存储在内存中。你必须选择
答案 1 :(得分:1)
通过快速扫描代码,您的基本问题似乎是每次调用OnDraw
方法时都在创建新的位图。相反,请注释掉该行,并在启动时仅为mBitmap
创建一次位图。
答案 2 :(得分:1)
你可以查看Richard Quirk的glbuffer。我在视频播放器应用程序中使用它。
通常,您希望保留您正在接收的视频数据包,并且只在它们需要显示之前解码它们。将代码与glbuffer集成并绕过Java代码中的任何Bitmap分配应该很容易。
在本机代码和GL纹理存储器中存在的任何给定时间将存在一个解码帧,并且您将保留用于缓冲的若干编码数据包。