Android用C++surface表示RGBデータ作成


次のAndroid 4.4プラットフォームでは、RGBデータを画面に直接表示するためのテストを行います.もちろん、YUVを直接表示するには、関数を書いて変換しても直接表示できます.
ファイルからRGBのRGBデータを取得するとここからダウンロードできます. http://kc.cc/WeVp
#include <cutils/memory.h>

#include <unistd.h>
#include <utils/Log.h>

#include <binder/IPCThreadState.h>
#include <binder/ProcessState.h>
#include <binder/IServiceManager.h>

#include <gui/Surface.h>
#include <gui/SurfaceComposerClient.h>
#include <gui/ISurfaceComposer.h>
#include <ui/DisplayInfo.h>
#include <ui/Rect.h>
#include <ui/Region.h>
#include <android/native_window.h>
#include <SkGraphics.h>
#include <SkBitmap.h>
#include <SkCanvas.h>
#include <SkDevice.h>
#include <SkStream.h>
#include <SkImageDecoder.h>

#include <hardware/hwcomposer_defs.h>
using namespace android;

static inline SkBitmap::Config convertPixelFormat(PixelFormat format) {
    /* note: if PIXEL_FORMAT_RGBX_8888 means that all alpha bytes are 0xFF, then
        we can map to SkBitmap::kARGB_8888_Config, and optionally call
        bitmap.setIsOpaque(true) on the resulting SkBitmap (as an accelerator)
    */
    switch (format) {
    case PIXEL_FORMAT_RGBX_8888:    return SkBitmap::kARGB_8888_Config;
    case PIXEL_FORMAT_RGBA_8888:    return SkBitmap::kARGB_8888_Config;
    case PIXEL_FORMAT_RGB_565:      return SkBitmap::kRGB_565_Config;
    default:                        return SkBitmap::kNo_Config;
    }
}

int main(int argc, char** argv)
{
    // set up the thread-pool
    sp<ProcessState> proc(ProcessState::self());
    ProcessState::self()->startThreadPool();

    // create a client to surfaceflinger
    sp<SurfaceComposerClient> client = new SurfaceComposerClient();
    //DisplayoutBuffer display;
    //client->getDisplayoutBuffer(client->getBuiltInDisplay(HWC_DISPLAY_PRIMARY), &display);
	sp<IBinder> dtoken(SurfaceComposerClient::getBuiltInDisplay(
            ISurfaceComposer::eDisplayIdMain));
	DisplayInfo dinfo;
	//          
    status_t status = SurfaceComposerClient::getDisplayInfo(dtoken, &dinfo);
	printf("w=%d,h=%d,xdpi=%f,ydpi=%f,fps=%f,ds=%f
", dinfo.w, dinfo.h, dinfo.xdpi, dinfo.ydpi, dinfo.fps, dinfo.density); if (status) return -1; sp<SurfaceControl> surfaceControl = client->createSurface(String8("testsurface"), dinfo.w, dinfo.h, PIXEL_FORMAT_RGB_565, 0); /**************************** ******************************************************/ SurfaceComposerClient::openGlobalTransaction(); surfaceControl->setLayer(100000);// Z surfaceControl->setPosition(0, 0);// (0,0) SurfaceComposerClient::closeGlobalTransaction(); surfaceControl->show();// , sp<Surface> surface = surfaceControl->getSurface(); ANativeWindow_Buffer outBuffer; //Surface::SurfaceoutBuffer outBuffer; surface->lock(&outBuffer,NULL);// surface ssize_t bpr = outBuffer.stride * bytesPerPixel(outBuffer.format); android_memset16((uint16_t*)outBuffer.bits, 0xF800, bpr*outBuffer.height);// surface RGB surface->unlockAndPost(); sleep(3); // RGB :http://kc.cc/WeVp /**************************** ******************************************************/ SurfaceComposerClient::openGlobalTransaction(); surfaceControl->setSize(480, 272); surfaceControl->setPosition(100, 100); SurfaceComposerClient::closeGlobalTransaction(); surfaceControl->show();// , FILE *fp = fopen("/tmp/rgb565.rgb","rb");// RGB565 480*272 if(fp != NULL){ unsigned char *rgb565Data = new unsigned char[480*272*2]; memset(rgb565Data,0x00,480*272*2); fread(rgb565Data,1,480*272*2,fp); surface->lock(&outBuffer,NULL); //bpr = outBuffer.stride * bytesPerPixel(outBuffer.format); //android_memset16((uint16_t*)outBuffer.bits, 0x04E0, bpr*outBuffer.height); memcpy(outBuffer.bits,rgb565Data,480*272*2); delete[] rgb565Data; surface->unlockAndPost(); } fclose(fp); sleep(3); // skia /******************************* ***************************************************/ SurfaceComposerClient::openGlobalTransaction(); surfaceControl->setSize(320, 420); surfaceControl->setPosition(100, 100); SurfaceComposerClient::closeGlobalTransaction(); surfaceControl->show();// SkPaint paint; paint.setColor(SK_ColorBLUE); Rect rect(0, 0, 320, 240); Region dirtyRegion(rect); surface->lock(&outBuffer, &rect); bpr = outBuffer.stride * bytesPerPixel(outBuffer.format); // printf("w=%d,h=%d,bpr=%d,fmt=%d,bits=%p
", outBuffer.w, outBuffer.h, bpr, outBuffer.format, outBuffer.bits); SkBitmap bitmap; bitmap.setConfig(convertPixelFormat(outBuffer.format), 320, 240, bpr); bitmap.setPixels(outBuffer.bits); SkCanvas canvas; SkRegion clipReg; const Rect b(dirtyRegion.getBounds()); clipReg.setRect(b.left, b.top, b.right, b.bottom); canvas.clipRegion(clipReg); canvas.drawARGB(0, 0xFF, 0x00, 0xFF); canvas.drawCircle(200, 200, 100, paint); bitmap.notifyPixelsChanged(); surface->unlockAndPost(); sleep(3); /**********************************************************************************/ SkFILEStream stream("/sdcard/test.jpg"); SkImageDecoder* codec = SkImageDecoder::Factory(&stream); if(codec){ SkBitmap bmp; stream.rewind(); codec->decode(&stream, &bmp, SkBitmap::kRGB_565_Config, SkImageDecoder::kDecodePixels_Mode); surface->lock(&outBuffer,NULL); bpr = outBuffer.stride * bytesPerPixel(outBuffer.format); bitmap.setConfig(convertPixelFormat(outBuffer.format), 320, 240, bpr); bitmap.setPixels(outBuffer.bits); //dev = new SkDevice(bitmap); //canvas.setDevice(dev); canvas.drawBitmap(bmp, SkIntToScalar(200), SkIntToScalar(300)); surface->unlockAndPost(); sleep(3); //delete dev; } IPCThreadState::self()->joinThreadPool(); IPCThreadState::self()->stopProcess(); return 0; }
Android.mk
LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)

LOCAL_SRC_FILES:= \
	testsurface.cpp

LOCAL_C_INCLUDES := \
	external/skia/include/core

LOCAL_SHARED_LIBRARIES := \
	libcutils \
	libutils \
	libbinder \
    libui \
    libgui \
    libskia

LOCAL_MODULE:= testsurface

LOCAL_MODULE_TAGS := tests

include $(BUILD_EXECUTABLE)
コードの変更http://blog.csdn.net/lxl123/article/details/21465841 彼のコードはAndroid 4.4でコンパイルされています.