[Android]libpng的编译与使用

库地址

https://github.com/julienr/libpng-android

设置NDK环境变量

将NDK目录加入PATH变量:
C:\Users\xx\AppData\Local\Android\Sdk\ndk\20.0.5594570\

静态库

修改Android.mk文件

#LOCAL_SHARED_LIBRARIES := -lz
LOCAL_EXPORT_LDLIBS := -lz
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/.

#include $(BUILD_SHARED_LIBRARY)
include $(BUILD_STATIC_LIBRARY)

动态库

修改Android.mk文件

#LOCAL_SHARED_LIBRARIES := -lz
#LOCAL_EXPORT_LDLIBS := -lz
LOCAL_LDLIBS := -lz 
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/.

include $(BUILD_SHARED_LIBRARY)
#include $(BUILD_STATIC_LIBRARY)

编译命令

ndk-build NDK_PROJECT_PATH=./

libpng库使用

从内存中读取png图片数据,解码为RGBA格式的raw数据
glPngReader.h

//
// Created by Jinzhu on 2019/9/7.
//

#ifndef OPENGLES_GLPNGREADER_H
#define OPENGLES_GLPNGREADER_H


#ifdef __cplusplus
extern "C" {
#endif

#include 
#include 
#include 
#include 

struct glPngReader {
    uint8_t *m_raw_data;
    size_t m_raw_size;
    size_t m_raw_offset;

    int m_width;
    int m_height;
    int m_color_type;
    int m_pixel_depth;

    int m_status;

    uint8_t *m_pixel_data;
};

void glPngReader_Create(struct glPngReader *pngReader, uint8_t *raw_data, size_t raw_size);
void glPngReader_Destory(struct glPngReader *pngReader);

uint8_t *glPngReader_GetPixelData(struct glPngReader *pngReader);

int glPngReader_GetWidth(struct glPngReader *pngReader);
int glPngReader_GetHeight(struct glPngReader *pngReader);


#ifdef __cplusplus
};
#endif


#endif //OPENGLES_GLPNGREADER_H

glPngReader.c

//
// Created by Jinzhu on 2019/9/7.
//


#include 

#ifdef __cplusplus
extern "C" {
#endif

#include "glPngReader.h"
#include 
#include 
#include 
#include 
#include 


#define LOG_TAG "PNGREADER-LIB"
#define ALOGE(...) __android_log_print(ANDROID_LOG_ERROR, LOG_TAG, __VA_ARGS__)


void glPngReader_ReadCallback(png_structp png_ptr, png_bytep data, png_size_t length) {
    struct glPngReader *pThis = (struct glPngReader *) png_get_io_ptr(png_ptr);
    if (pThis != NULL) {
        if (pThis->m_raw_offset + length <= pThis->m_raw_size) {
            memcpy(data, pThis->m_raw_data + pThis->m_raw_offset, length);
            pThis->m_raw_offset += length;
        } else {
            ALOGE("the length is illegal.");
        }
    }
}

void glPngReader_ReadImage(struct glPngReader *pngReader) {
    png_structp png_ptr = png_create_read_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL);
    if (png_ptr == NULL) {
        ALOGE("load libpng error,png_ptr = NULL.");
        pngReader->m_status = 0;
        return;
    }
    png_infop info_ptr = png_create_info_struct(png_ptr);
    if (info_ptr == NULL) {
        png_destroy_read_struct(&png_ptr, NULL, NULL);
        ALOGE("load libpng error,info_ptr = NULL.");
        pngReader->m_status = 0;
        return;
    }


    if (setjmp(png_jmpbuf(png_ptr))) {
        png_destroy_read_struct(&png_ptr, &info_ptr, NULL);
        ALOGE("libpng process error.");
        pngReader->m_status = 0;
        return;
    }


    png_set_read_fn(png_ptr, pngReader, glPngReader_ReadCallback);
    png_read_png(png_ptr, info_ptr, PNG_TRANSFORM_EXPAND, NULL);

    pngReader->m_width = info_ptr->width;
    pngReader->m_height = info_ptr->height;
    pngReader->m_color_type = info_ptr->color_type;
    pngReader->m_pixel_depth = info_ptr->pixel_depth;

    if ((pngReader->m_color_type != PNG_COLOR_TYPE_RGB &&
         pngReader->m_color_type != PNG_COLOR_TYPE_RGB_ALPHA)
        && pngReader->m_pixel_depth == 8) {
        ALOGE("image format error.");
        pngReader->m_status = 0;
        png_destroy_read_struct(&png_ptr, &info_ptr, NULL);
        return;
    }

    if (pngReader->m_pixel_data != NULL) {
        free(pngReader->m_pixel_data);
        pngReader->m_pixel_data = NULL;
    }
    pngReader->m_pixel_data = (uint8_t *) malloc(pngReader->m_width * pngReader->m_height * 4);

    png_bytep *row_pointers = png_get_rows(png_ptr, info_ptr);

    if (pngReader->m_color_type == PNG_COLOR_TYPE_RGB) {
        int pos = 0;
        for (int row = 0; row < pngReader->m_height; ++row) {
            for (int col = 0; col < (3 * pngReader->m_width); col += 3) {
                pngReader->m_pixel_data[pos++] = row_pointers[row][col + 0];//RED
                pngReader->m_pixel_data[pos++] = row_pointers[row][col + 1];//GREEN
                pngReader->m_pixel_data[pos++] = row_pointers[row][col + 2];//BLUE
                pngReader->m_pixel_data[pos++] = 255;//ALPHA
            }
        }
        pngReader->m_status = 1;
    } else if (pngReader->m_color_type == PNG_COLOR_TYPE_RGB_ALPHA) {
        int pos = 0;
        for (int row = 0; row < pngReader->m_height; ++row) {
            for (int col = 0; col < (4 * pngReader->m_width); col += 4) {
                pngReader->m_pixel_data[pos++] = row_pointers[row][col + 0];//RED
                pngReader->m_pixel_data[pos++] = row_pointers[row][col + 1];//GREEN
                pngReader->m_pixel_data[pos++] = row_pointers[row][col + 2];//BLUE
                pngReader->m_pixel_data[pos++] = row_pointers[row][col + 3];//ALPHA
            }
        }
        pngReader->m_status = 1;
    } else {
        pngReader->m_status = 0;
    }
    png_destroy_read_struct(&png_ptr, &info_ptr, NULL);
}

void glPngReader_Create(struct glPngReader *pngReader, uint8_t *raw_data, size_t raw_size) {
    pngReader->m_raw_data = raw_data;
    pngReader->m_raw_size = raw_size;
    pngReader->m_raw_offset = 0;

    pngReader->m_width = 0;
    pngReader->m_height = 0;
    pngReader->m_color_type = PNG_TRANSFORM_STRIP_ALPHA;
    pngReader->m_pixel_depth = 8;

    pngReader->m_status = 0;
    pngReader->m_pixel_data = NULL;

    glPngReader_ReadImage(pngReader);
}

void glPngReader_Destory(struct glPngReader *pngReader) {
    if (pngReader->m_pixel_data != NULL) {
        free(pngReader->m_pixel_data);
        pngReader->m_pixel_data = NULL;
    }
}

uint8_t *glPngReader_GetPixelData(struct glPngReader *pngReader) { return pngReader->m_pixel_data; }

int glPngReader_GetWidth(struct glPngReader *pngReader) { return pngReader->m_width; }

int glPngReader_GetHeight(struct glPngReader *pngReader) { return pngReader->m_height; }

#ifdef __cplusplus
};
#endif

你可能感兴趣的:(Android)