其他分享
首页 > 其他分享> > 手工局部二值化,MFC, BMP

手工局部二值化,MFC, BMP

作者:互联网

拿知乎上的一张图练练手,光照是斜对角,全局二值化阈值20,一个角太白;改为全局80,另一个角太黑。

就把图分成4x4,16个小方块,用一个阈值矩阵手工搞,虽说是滥竽充数,好歹也弄出来了。

 

 

 

程序段:

void CXDTS1View::OnTestTest1()
{
    // TODO: Add your command handler code here
    CXDTDoc* pDoc = GetDocument();
    ASSERT_VALID(pDoc);
    if (!pDoc)
        return;

    unsigned char* pData;
    int            DataLen;

    
    //pData = (unsigned char*)pDoc->m_Data;
    DataLen = pDoc->m_DataLen;
    if (DataLen == 0) return;

    pData = new unsigned char[DataLen];
    
    memcpy(pData, (void*)pDoc->m_Data, DataLen);


    //if (DataLen > 10000) DataLen = 10000;

    BITMAPFILEHEADER hdr;
    LPBITMAPINFOHEADER lpbi;
    BITMAPINFOHEADER  bmpInfo;//信息头  

    memcpy(&hdr, pData, 14);
    memcpy(&bmpInfo, pData + 14, 40);


    unsigned char* p = NULL;
    unsigned char* pBmpdata = NULL;
    unsigned char* pBmpdata2 = NULL;
    p = (unsigned char*)pData + 14;
    pBmpdata = (unsigned char*)(pData + hdr.bfOffBits);
    pBmpdata2 = (unsigned char*)(pData + hdr.bfOffBits);
    lpbi = (LPBITMAPINFOHEADER)(p);
    /*PRINT("%d-%d-%d", hdr.bfType, hdr.bfSize, hdr.bfOffBits);
    PRINT("%d-%d-%d", lpbi->biSize, lpbi->biWidth, lpbi->biHeight);
    PRINT("%d-%d-%d", bmpInfo.biSize, bmpInfo.biWidth, bmpInfo.biHeight);*/

    int bfWidth, bfHeight;
    int biBitCount;
    int bytesPerLine;
    int skip;
    int imageSize;

    //DBI 数据信息
    bfWidth = lpbi->biWidth;
    bfHeight = lpbi->biHeight;
    biBitCount = lpbi->biBitCount;

    
    //内存数据映射
    bytesPerLine = ((bfWidth * biBitCount + 31) >> 5) << 2;//bfWidth *3+skip
    skip = 4 - ((bfWidth * biBitCount) >> 3) & 3;
    imageSize = bytesPerLine * bfHeight;

    PRINT("BMP W:%d-H:%d-b:%d  MEM: BpL:%d-Skip:%d-Size:%d", 
        bfWidth, bfHeight, biBitCount,
        bytesPerLine, skip, imageSize);


    CMainFrame* pMainFrame = (CMainFrame*)((CXDTApp*)AfxGetApp())->m_pMainWnd;
    CPropertiesWnd* pwndProperties = &(pMainFrame->m_wndProperties);

    CString str = pwndProperties->m_pSize->GetSubItem(0)->FormatProperty();
    int  door;
    door = atoi(str.GetBuffer());
    

    int R, G, B, Gray;
    
    //door = 80;
    
    int tdoor[4][4] =
    {
        50, 60, 70, 80,
        40, 50, 60, 70,
        30, 40, 50, 60,
        20, 30, 40, 50 
    };
    
    //处理内存数据
    for (int i = 0; i < bfHeight; i++) //高度是反的
    {
        for (int j = 0; j < bytesPerLine; j+=3)  //宽度 转换为 行(列数) 
        {
                
            B=pBmpdata[i * bytesPerLine + j] ;
            G=pBmpdata[i * bytesPerLine + j+1];
            R=pBmpdata[i * bytesPerLine + j+2];

            Gray = (R * 19595 + G * 38469 + B * 7472) >> 16;

            door = tdoor[i * 4 / bfHeight][j * 4 / bytesPerLine];

            if (Gray > door) Gray = 255;
            else  Gray = 0;

            pBmpdata[i * bytesPerLine + j] = Gray;
            pBmpdata[i * bytesPerLine + j+1] = Gray;
            pBmpdata[i * bytesPerLine + j+2] = Gray;
            
        }
    }
    
    
    //pDoc->UpdateAllViews(NULL);
    ShowBMP(pData, DataLen);
    
    delete pData;

}

 

标签:MFC,bytesPerLine,int,pData,unsigned,char,BMP,DataLen,二值化
来源: https://www.cnblogs.com/xgz21/p/16522155.html