⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 setscanner.cpp

📁 又VC++实现的基于TWAIN的扫描仪图像输入处理软件
💻 CPP
📖 第 1 页 / 共 5 页
字号:
		  else
		  {
            dwBytesInLine=(int)((nWidth*8)/8+j1) ;
		  }
	      dwBytesBMP=dwBytes=dwBytesInLine * nLength;

          dwBytesBMP= dwBytes= dwBytesInLine * nLength;
          dwBytesBMPH= dwBytesH=dwBytesBMP;
          dwBytesInLineH=dwBytesInLine;
         
		  break;
	 case 2:
		  nLength=length+y1;
          nWidth=(nWidth/8)*8;
         //计算的是存储文件空间大小
		  j2=nWidth/8;
		  j3=nWidth%8;
		  if(j3!=0)
		  {
			 j2=j2+1;
		  }
		  j1=4-j2%4;
		  j=(j2*8)%32;
		  if(j==0)
		  {
             dwBytesInLineH=(j2*8)/8;
		  }
		  else
		  {
            dwBytesInLineH=(j2*8)/8+j1;
		  }
		 dwBytesBMPH = dwBytesH = dwBytesInLineH * nLength;
        
         //计算的是读取数据时的空间大小,和灰度相同
          dwBytesInLine=dwBytesInLineH*8;
	      dwBytesBMP=dwBytes=dwBytesInLine * nLength;
          
		 break;
	}

    //写存储文件的信息头
    if( !PreviewBitmap.Open( pFileName, CFile::modeCreate| CFile::modeWrite , &e ) )
	{
	   #ifdef _DEBUG    
		 afxDump << "File could not be opened " << e.m_cause << "\n";
	   #endif
	}
    
	Bifh.biSize = sizeof(BITMAPINFOHEADER);
	Bifh.biWidth = (LONG) nWidth;
	Bifh.biPlanes = 1;
	switch(pScanner->m_nColor)
	{
	  case  16777216:
	    Bifh.biHeight    = (LONG)(nLength-y1);
		Bifh.biBitCount  = 24;
		Bifh.biSizeImage = dwBytesBMP-y1*dwBytesInLine;
		Bmpfh.bfType	 = 0x4d42;  
		Bmpfh.bfSize	 = 0x36+dwBytes-y1*dwBytesInLine;   
		Bmpfh.bfReserved1= 0; 
		Bmpfh.bfReserved2= 0;
		Bmpfh.bfOffBits	 = 0x36; 

        biBitCount=24;
		break;
	  case 256:
		Bifh.biHeight   = (LONG)(nLength-y1);
		Bifh.biBitCount = 8;
		Bifh.biSizeImage= dwBytesBMP-y1*dwBytesInLine;
		for (i=0;i<256;i++)
		{
		   BMPpalete[i].peBlue =0;
	 	   BMPpalete[i].peGreen=0;
		   BMPpalete[i].peRed  =0;
		   BMPpalete[i].peFlags=0;
		}
		for (i=0;i<256;i++)
		{
		   BMPpalete[i].peBlue =i;
		   BMPpalete[i].peGreen=i;
		   BMPpalete[i].peRed  =i;
		   BMPpalete[i].peFlags=0;
		}
		Bmpfh.bfType=0x4d42; 
		Bmpfh.bfSize=0x0436+4*256+dwBytes-y1*dwBytesInLine;   
		Bmpfh.bfReserved1=0; 
		Bmpfh.bfReserved2=0;
		Bmpfh.bfOffBits=0x0436; 

        biBitCount=8;
		break;
	case 2:
		Bifh.biHeight   = (LONG)(nLength-y1);
		Bifh.biBitCount = 1;
		Bifh.biSizeImage= dwBytesBMPH-y1*dwBytesInLineH;
		for (i=0;i<2;i++)
		{ 
		  BMPpalete[i].peBlue=0;
		  BMPpalete[i].peGreen=0;
		  BMPpalete[i].peRed=0;
		  BMPpalete[i].peFlags=0;
		}
		  BMPpalete[0].peBlue=0;
		  BMPpalete[0].peGreen=0;
		  BMPpalete[0].peRed=0;
		  BMPpalete[0].peFlags=0;
		  BMPpalete[1].peBlue=255;
		  BMPpalete[1].peGreen=255;
		  BMPpalete[1].peRed=255;
		  BMPpalete[1].peFlags=0;
					
		  Bmpfh.bfType= 0x4d42;  
		  Bmpfh.bfSize= 0x3e+2*4+dwBytesH-y1*dwBytesInLineH;   
		  Bmpfh.bfReserved1	= 0; 
		  Bmpfh.bfReserved2	= 0;
		  Bmpfh.bfOffBits	= 0x3e; 

          biBitCount=8;

          break;
	}
	
	Bifh.biCompression = 0;
	Bifh.biXPelsPerMeter = PerMeter;
	Bifh.biYPelsPerMeter = PerMeter;
	Bifh.biClrUsed = 0;
	Bifh.biClrImportant = 0;
			
	PreviewBitmap.Write(&Bmpfh,sizeof(BITMAPFILEHEADER));
	PreviewBitmap.Write(&Bifh,sizeof(BITMAPINFOHEADER));
	if(Bifh.biBitCount==8)
	{
		PreviewBitmap.Write(&BMPpalete[0],256*4);	
	}
	else if(Bifh.biBitCount==1)
	{
		PreviewBitmap.Write(&BMPpalete[0],2*4);
	}
	else
	{
		PreviewBitmap.Write(&BMPpalete[0],0*4);	  
	}
//************************************************************
//从SCSI接口中开始读数据到内存中,并且存储在文件中           //
//*************************************************************
   //定义一些变量		
   DWORD   dwBits;
   HGLOBAL hbuffer1;     //nReadInBytes
   HGLOBAL hbuffer2;     //pMem+y1
   //HGLOBAL hmem1;

   LPSTR lpBits3,lpStart3;
   LPSTR lpBits1,lpStart1;
   LPSTR lpBits2,lpStart2;
  
   CScanningProgress* pScanningProgress;
   CProgressCtrl *pProgressCtrl;

   int nPrePos;
   int nReadInBytes;
   int nReadInBytes1,nReadInBytes2;
   int nReadInBytes0;
   int number2=0;
   int n6=1;
   int nCount=0;
   int n1,n2,n3;
   int Row,BytesPerRow; 
   double number1;


   DWORD bytesout = 0;
   DWORD RowsWritten;
   DWORD BytesWritten;
  
   //计算需要的内存大小并且申请相应内存空间
   BytesPerRow = (biBitCount*Bifh.biWidth)/8; 
 
   Row=1044480/BytesPerRow;  
   RowsWritten=0;
   dwBits = dwBytesBMP;
   nReadInBytes=(1044480)/(biBitCount*Bifh.biWidth/8);
   nReadInBytes=nReadInBytes*(biBitCount*Bifh.biWidth/8);
   //进程条中进程进度
   number1=dwBits/50;
   nPrePos=0;	
   count=0;
   //分配存储空间 ,大小为dwBytes,即实际存储文件大小,存储最终数据文件 			
   hMem = GlobalAlloc(GHND, dwBytesH);
   lpBits3 = (LPSTR)GlobalLock(hMem);
   lpStart3 =lpBits3; 
   lpBits3=lpBits3+dwBytesBMPH-dwBytesInLineH;
 
   pScanningProgress = new CScanningProgress; 
   while(RowsWritten<(DWORD)(Bifh.biHeight))
   {
     //判断是否终止扫描过程,需要改改进,因为似乎不起作用
	 /*MSG Cancelmsg;
	 PeekMessage(&Cancelmsg,pScanningProgress->m_hWnd,WM_KEYFIRST,WM_KEYLAST,PM_REMOVE);
     if(Cancelmsg.message ==WM_KEYDOWN)
	 {
	   if(Cancelmsg.wParam == 'q' | Cancelmsg.wParam =='Q')
		{
	       LogMessage("XferCancel returned\n");
		   bytesout = 0;
		   count = 0;
           number2=0;
		   number1=0;
		   n6=1; 

	 	   GlobalUnlock(hmem1);
		   GlobalFree(hmem1);
		   GlobalUnlock(hbuffer1);
		   GlobalFree(hbuffer1);
		   GlobalUnlock(hbuffer2);
		   GlobalFree(hbuffer2);
		 
		   delete pScanningProgress;
		   pScanningProgress = NULL;
		}
	}*/
    
	//计算每次读入的数据块大小
    RowsWritten = bytesout/BytesPerRow;
	if (Row >=(int)(Bifh.biHeight - RowsWritten))
	{
	   BytesWritten = BytesPerRow * (Bifh.biHeight - RowsWritten);
	   Row = Bifh.biHeight- RowsWritten;
	}
    else
    {
       BytesWritten = BytesPerRow * Row;
       Row = Row;
	}

	if(count==0)    //第一次读数据到PHOTOSHOP缓冲区中
	{
       //建立进程条窗口
       pScanningProgress = new CScanningProgress;
	   pScanningProgress->Create(IDD_DIALOG_SCANNING_PROGRESS,NULL);
	    //设置进程条进度
	   pProgressCtrl = (CProgressCtrl *)pScanningProgress->GetDlgItem(IDC_PROGRESS1);
	   pProgressCtrl->SetRange(0,50);

	   //分配一个保护每次读入的数据块和其相应拼齐数据的内存块
	   hbuffer2 = GlobalAlloc(GHND, (Row+y1)*BytesPerRow);
	   lpStart2=(LPSTR)GlobalLock(hbuffer2);
	   lpBits2=lpStart2;
       //计算以64K数据为交换单元,需要从SCSI读入数据的次数
	   if((Row+y1)*BytesPerRow>nReadInBytes)
	   {
		 n1=((Row+y1)*BytesPerRow)/nReadInBytes;
		 nReadInBytes0=((Row+y1)*BytesPerRow)-n1*nReadInBytes;
	   }
	   else
	   {
		 n1=0;
		 nReadInBytes0=(Row+y1)*BytesPerRow;
		}
	}
	else //非第一次读数据到PHOTOSHOP缓冲区中
	{
	   if(Row*BytesPerRow>nReadInBytes)
	   {
		 n1=(Row*BytesPerRow)/nReadInBytes;
		 nReadInBytes0=(Row*BytesPerRow)-n1*nReadInBytes;
	   }
	   else
	   {
		  n1=0;
		  nReadInBytes0=Row*BytesPerRow;
		}	
	}
    
    //分配每次读入数据块大小的内存空间      
	hbuffer1 = GlobalAlloc(GHND, nReadInBytes*n1+nReadInBytes0);
	lpBits=(LPSTR)GlobalLock(hbuffer1);
	lpBits1=lpBits;
	lpStart1=lpBits;  
    //和下层约定传输的是象素点个数,而不是字节数
    if(pScanner->m_nColor==16777216)
	{
	   nReadInBytes1=nReadInBytes/3;
	   nReadInBytes2=nReadInBytes0/3;
	}
	else
	{
       nReadInBytes1=nReadInBytes;
	   nReadInBytes2=nReadInBytes0;
	}

     while(n1>0)
	{
      //调用函数从SCSI中读取nReadInBytes字节个数据到lpBits指定的缓冲区
      downRow=nReadInBytes/BytesPerRow;
	  SCSI_Read(lpBits,nReadInBytes,nReadInBytes1,downRow,0);

      //写数据到指定的缓冲区中,以便拼齐等图像数据处理
      n2=0;
	  lpBits1=lpStart1;
	  memcpy(lpBits2,lpBits1,nReadInBytes);
	  lpBits2=lpBits2+nReadInBytes;
      //进程条前进
	  number2=number2+nReadInBytes;
      if(number2>=(number1*n6))
	  {
		 pProgressCtrl->OffsetPos((int)(number2/(number1*n6)+0.5));
         nPrePos=nPrePos+1;
         n6++;
	  }
	  n1--;
	 }
    
    //写数据到指定的缓冲区中,以便拼齐等图像数据处理
	n2=0;
	lpBits1=lpStart1;
	if(nReadInBytes0!=0)
    { 
      //调用SCSI读函数,从SCSI接口中读取其余数据
	  downRow=nReadInBytes0/BytesPerRow;
      SCSI_Read(lpBits,nReadInBytes0,nReadInBytes2,downRow,0);
    
 	  memcpy(lpBits2,lpBits1,nReadInBytes0);
      lpBits2=lpBits2+nReadInBytes0;
      
      number2=number2+nReadInBytes0;
      if(number2>=(number1*n6))
	  {
		 pProgressCtrl->OffsetPos((int)(number2/(number1*n6)+0.5));
         nPrePos=nPrePos+1;
         n6++;
	  }

	}	

	GlobalUnlock(hbuffer1);
	GlobalFree(hbuffer1);
//  
	int n4;
	int a,b;
//向文件写数据作准备,包括对彩色图像数据拼齐拼色,奇偶拼色                
   if(pScanner->m_nColor==16777216) //彩色图像
   {
	  lp1=lpStart2;
	  lp2=lp1+x0*BytesPerRow;
	  lp3=lp1+y0*BytesPerRow;
	  lp4=lp1+y2*BytesPerRow;
	  lp5=lp2+y2*BytesPerRow;
	  lp6=lp3+y2*BytesPerRow;
      
	  for(n3=0;n3<Row;n3++)
	  {
		for(n2=0;n2<BytesPerRow/3;n2++)
		{
		  n4=n2%(pScanner->m_nDPI);
				//A1 扫描仪的拼色程序:B、G、R--> lp3、lp2、lp1 / lp6、lp5、lp4
				//A0 扫描仪的拼色程序:R、G、B--> lp1、lp2、lp3 / lp4、lp5、lp6
		  if(jiou[n4]==0)//表示是偶数点
		  {
		   *(lpBits3+3*n2+2)=*(unsigned char*)(lp1+3*n2);
		   *(lpBits3+3*n2+1)=*(unsigned char*)(lp2+3*n2+1);
		   *(lpBits3+3*n2)=*(unsigned char*)(lp3+3*n2+2);
		  }
		  else
		  {
            *(lpBits3+3*n2+2)=*(unsigned char*)(lp4+3*n2);
		    *(lpBits3+3*n2+1)=*(unsigned char*)(lp5+3*n2+1);
		    *(lpBits3+3*n2)=*(unsigned char*)(lp6+3*n2+2);
		  }
		}
              
	    lp1=lp1+BytesPerRow;
		lp2=lp2+BytesPerRow;
		lp3=lp3+BytesPerRow;
        lp4=lp4+BytesPerRow;
        lp5=lp5+BytesPerRow;
        lp6=lp6+BytesPerRow;
              
		lpBits3=lpBits3-dwBytesInLine;
	  }
	
	  n2=0;
	  lpBits2=lpStart2;
		
      memcpy(lpBits2,lp1,y1*BytesPerRow);
	  lpBits2=lpBits2+y1*BytesPerRow;
	  lp1=lp1+y1*BytesPerRow;
    }
   else//灰度图和黑白图
   {
     lp1=lpStart2;
	 lp2=lp1+y2*BytesPerRow;

     for(n3=0;n3<Row;n3++)
	 {
	   	for(n2=0;n2<BytesPerRow;n2++)
		{
		  //如果是灰度图像
           if(pScanner->m_nColor==256)
		   {
			  n4=n2%(2*pScanner->m_nDPI);
			  if(jiou[n4]==0)//表示是偶数点
			  {
				*(lpBits3+n2)=*(unsigned char*)(lp1+n2);
			  }
			  else
			  {
                *(lpBits3+n2)=*(unsigned char*)(lp2+n2);
			  }
		   }
		  else//如果是黑白图像,则需要每读入8个字节才能写入PHOTOSHOP中一次
		  {
            for(i=0;i<8;i++)
			 {
			   n4=n2%(2*pScanner->m_nDPI);
			   a=*(unsigned char*)(lp1+n2);
               b=*(unsigned char*)(lp2+n2);
              
			   if(a==255)
			   {
				 a=1;
			   }
			   else
			   {
				  a=0;
			   }
			   if(b==255)
			   {
				  b=1;
			   }
			   else
			   {
				  b=0;
			   }
               *(lpBits3+n2/8)=2*(*(unsigned char*)(lpBits3+n2/8));
               if(jiou[n4]==0)//表示是偶数点
			   {
				 *(lpBits3+n2/8)=*(unsigned char*)(lpBits3+n2/8)|a;
					       
			   }
			  else
			  {
                 *(lpBits3+n2/8)=*(unsigned char*)(lpBits3+n2/8)|b;
				  
			  }
			   n2++;
			}
            n2=n2-1;
		  }
		}
	     lpBits3=lpBits3-dwBytesInLineH;
         lp1=lp1+BytesPerRow;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -