ricmoo / QRCode

QR code generation library in C, optimized for low-power devices, such as Arduino.
Other
647 stars 204 forks source link

How to Store as a BMP? #5

Open maikebing opened 6 years ago

maikebing commented 6 years ago

I have some code!try save to a BMP! but can't scan! can you help me?


typedef struct tagBITMAPINFOHEADER {
    unsigned int  biSize;
    int   biWidth;
    int   biHeight;
    unsigned short   biPlanes;
    unsigned short   biBitCount;
    unsigned int  biCompression;
    unsigned int  biSizeImage;
    int   biXPelsPerMeter;
    int   biYPelsPerMeter;
    unsigned int  biClrUsed;
    unsigned int  biClrImportant;
} BITMAPINFOHEADER, *PBITMAPINFOHEADER;

typedef struct tagBITMAPFILEHEADER {
    unsigned short    bfType;
    unsigned int   bfSize;
    unsigned short    bfReserved1;
    unsigned short    bfReserved2;
    unsigned int   bfOffBits;
} BITMAPFILEHEADER, *PBITMAPFILEHEADER;

typedef struct tagRGBQUAD {
    unsigned char rgbBlue;
    unsigned char rgbGreen;
    unsigned char rgbRed;
    unsigned char rgbReserved;
}RGBQUAD;

typedef struct tagBITMAPINFO {
    BITMAPINFOHEADER    bmiHeader;
    RGBQUAD             bmiColors[1];
} BITMAPINFO, *PBITMAPINFO;
PBITMAPINFO BuildBitmapInfo(int biBitCount, int width, int height)
{
    PBITMAPINFO pInfo = 0;
    if (biBitCount == 1)
    {
        pInfo = (PBITMAPINFO)malloc(sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * 2);
        int i = 0;
        for ( ; i < 2 ; i ++)
        {
            pInfo->bmiColors[i].rgbBlue = (unsigned char)(i*255);
            pInfo->bmiColors[i].rgbRed  = (unsigned char)(i*255);
            pInfo->bmiColors[i].rgbGreen = (unsigned char)(i*255);
            pInfo->bmiColors[i].rgbReserved = 0;
        }
    }
    else
        if (biBitCount == 8)
        {
            pInfo = (PBITMAPINFO)malloc(sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * 256);
            int i = 0;
            for (; i < 256 ; i ++)
            {
                pInfo->bmiColors[i].rgbBlue = (unsigned char)i;
                pInfo->bmiColors[i].rgbRed =  (unsigned char)i;
                pInfo->bmiColors[i].rgbGreen = (unsigned char)i;
                pInfo->bmiColors[i].rgbReserved = 0;
            }
        }
        else if (biBitCount == 24)
        {
            pInfo = (PBITMAPINFO)malloc(sizeof(BITMAPINFOHEADER));
        }
        else
            return NULL;

        pInfo->bmiHeader.biSizeImage = (width*biBitCount+31)/32*4*height;
        pInfo->bmiHeader.biBitCount = biBitCount;
        pInfo->bmiHeader.biClrImportant = 0;
        pInfo->bmiHeader.biClrUsed = 0;
        pInfo->bmiHeader.biCompression = 0;
        pInfo->bmiHeader.biHeight = height;
        pInfo->bmiHeader.biWidth = width;
        pInfo->bmiHeader.biPlanes = 1;
        pInfo->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
        pInfo->bmiHeader.biXPelsPerMeter = 0;
        pInfo->bmiHeader.biYPelsPerMeter = 0;

        return pInfo;
}

PBITMAPFILEHEADER  BuildBitmapFileHeader(unsigned int bfSize,unsigned int bfOffBits)
{
    PBITMAPFILEHEADER pHeader = (PBITMAPFILEHEADER)malloc(sizeof(BITMAPFILEHEADER));
    pHeader->bfOffBits = bfOffBits;
    pHeader->bfReserved1 = 0;
    pHeader->bfReserved2 = 0;
    pHeader->bfSize = bfSize;
    pHeader->bfType = 'M'*0X100+'B';
    return pHeader;
}

int SaveDIB(PBITMAPINFO pInfo,unsigned char * pData,char * FileName)
{
    FILE *file = fopen(FileName,"wb");
    if(file == 0)
        return 0;

    PBITMAPFILEHEADER   pFileHeader;

    unsigned int    FileLen =0,bfOffBits =0;
    if( pInfo->bmiHeader.biBitCount==1 )
    {
        FileLen=(pInfo->bmiHeader.biWidth+31)/32*4 * pInfo->bmiHeader.biHeight;
        bfOffBits=0x3E;
    }
    else if( pInfo->bmiHeader.biBitCount==8 )
    {
        FileLen=(pInfo->bmiHeader.biWidth+3) /4 *4 * pInfo->bmiHeader.biHeight;
        bfOffBits=0x436;
    }
    else if( pInfo->bmiHeader.biBitCount==24 )
    {
        FileLen=(pInfo->bmiHeader.biWidth*3+3)/4*4 * pInfo->bmiHeader.biHeight;
        bfOffBits=sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER);//0x36;
    }
    printf("FileLen = %d  bfOffBits = %d",FileLen,bfOffBits);
    pFileHeader=BuildBitmapFileHeader(FileLen,bfOffBits);

    fwrite(&(pFileHeader->bfType),1,2,file);
    fwrite(&(pFileHeader->bfSize),1,4,file);
    fwrite(&(pFileHeader->bfReserved1),1,2,file);
    fwrite(&(pFileHeader->bfReserved2),1,2,file);
    fwrite(&(pFileHeader->bfOffBits ),1,4,file);
    //fwrite(pFileHeader,1,14,file);

    if( pInfo->bmiHeader.biBitCount==1 )
    {
        fwrite(pInfo,1,0x30,file);

    }

    if( pInfo->bmiHeader.biBitCount==8 )
    {
        fwrite(pInfo,1,0x428,file);

    }
    if( pInfo->bmiHeader.biBitCount==24 )
    {
        fwrite(pInfo,1,sizeof(BITMAPINFOHEADER),file);

    }
    fwrite(pData,1,pInfo->bmiHeader.biSizeImage,file);//dW*h

    fclose(file);

    if( pFileHeader )
        free(pFileHeader);

    pFileHeader = 0;
    return 1;
}
ricmoo commented 6 years ago

I don't see any QR code generation in your example...

maikebing commented 6 years ago
BOOL WriteBMP(char*text)
{
    QRCode qrcode;
    unsigned char buffer[1024];
    int  buffsize = qrcode_getBufferSize(3);
    uint8_t *qrcodeBytes= malloc(buffsize);
    bzero(qrcodeBytes, buffsize);
    qrcode_initText(&qrcode, qrcodeBytes, 3, ECC_LOW, text);
    HW_BIN2BMPStore(qrcodeBytes,(unsigned char*) &buffer);
    PBITMAPINFO pinf = BuildBitmapInfo(1, qrcode.size, qrcode.size);
    SaveDIB(pinf, (unsigned char*)&buffer,"/TEMP.BMP");
    free(pinf);
    free(qrcodeBytes);
    return TRUE;
}
maikebing commented 6 years ago

void HW_BIN2BMPStore( unsigned char * pbByteBinImage,unsigned char * buf)
{
    //int iCX = 112;
    int iCY = 20;
    int i = 0;
    for(; i<iCY; i++)
    {
        int j = 0;
        //printf("%d\n",i); 
        for (; j<14; j++)
        {
            //printf("j=%d\n",j);
            unsigned char  t=1;
            int n = 0;
            for (; n<8; n++)
            {
                //printf("n=%d\n",n);
                unsigned char  d = pbByteBinImage[i*14+j] & t;
                //printf("d=%d\n",d);
                if (d)
                {

                    buf[(iCY-1-i)*16+j] |= 1<<(7-n);
                    //printf("%d\n",buf[(iCY-1-i)*16+j]);
                }
                t *= 2;
            }
        }
    }
}
maikebing commented 6 years ago

I want to show some of the data to the QRcode picture file, can you write an example? With the pure C language, the code I wrote above always has a problem, and maybe I don't understand something.

lailuboy commented 3 months ago

I implemented saving a QR code as a BMP file using C language