使用CBitmap和BITMAP [英] Working with CBitmap and BITMAP

查看:79
本文介绍了使用CBitmap和BITMAP的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用一些过滤器创建我的图像处理项目: Laplace & Sobel ,所以我创建了一个 SDI 应用程序,我没有上传我的项目,因为我正在使用Xtreme ToolkitPro v15.0.1" &您还应该安装它,以便能够编译&了解.

我创建了一个名为: CFilters
的类

I''m Creating my project of Image processing with some filters: Laplace & Sobel, so I created an SDI app, "I didn''t uploaded my project, because I am using Xtreme ToolkitPro v15.0.1" & you should have it installed too to be able to compile & understand.

I''ve created a class named: CFilters

class CFilters
{
public:
   CFilters();
   ~CFilters();

   static void Laplace(BITMAP* pBitMap);
   static void Sobel(BITMAP* pBitMap);
}



&当我从主菜单中点击Laplace Filter Sobel 时,我想要一个当前加载的&实例.显示的CBitmap已创建& BITMAP数据将传递到适当的过滤器静态函数CFilters::Laplace(BITMAP* pBitMap);CFilters::Sobel(BITMAP* pBitMap);,因此将修改pBitMap->bmBits.我可以显示过滤后的位图;

我做不到!

请帮助我;



& When I click the Laplace Filter or the Sobel one from the main menu, I would like an Instance of the currently loaded & shown CBitmap is created & the BITMAP data is passed to the appropriate filter static function CFilters::Laplace(BITMAP* pBitMap); or CFilters::Sobel(BITMAP* pBitMap); so the pBitMap->bmBits will be modified & I can show the filtered Bitmap;

I''m unable to do that!

Help me please;

推荐答案

我认为,您不应该直接在位图上进行图像处理.从文件加载,在屏幕上显示并保存到文件时,应使用位图.您的滤镜应该可以处理像素,无论它们是哪种格式.

我建议您的过滤器在BYTEfloat数组或RGBQUAD数组上工作.

这篇文章包含有用的代码和使用位图的链接:
CBitmap :: CreateBitmap:怎么做!? [ ^ ]

您还可以使用助手类来存储图像像素:
将2D数组传递给函数 [问题存储图像矩阵 [
In my opinion, you shouldn''t do image processing directly on bitmaps. You should use bitmaps when loading from a file, displaying on screen, and saving to a file. Your filters should work on the pixels, whatever format they are.

I suggest your filters work on BYTE or float array, or RGBQUAD arrays.

This post contains usefull code and links for using Bitmaps:
CBitmap::CreateBitmap: How to !?[^]

You can also use a helper class to store image pixels:
Passing 2D Arrays to functions[^]
This one is in C#, but you can easily conver it:
Problem storing image matrix[^]


除了一件事情,我已经意识到我项目的大约60%:当加载一些BMP图像时,应用程序崩溃了,这是我的代码来源:
ECAEDDoc.h
I''ve realized about 60% of my project except one thing: When loading some BMP images the app crashes, here is my code source:
ECAEDDoc.h
// ECAEDDoc.h : interface of the CECAEDDoc class
//
/////////////////////////////////////////////////////////////////////////////
#if !defined(AFX_ECAEDDOC_H__64E67B6C_E0ED_4F6D_8A70_2387DE188471__INCLUDED_)
#define AFX_ECAEDDOC_H__64E67B6C_E0ED_4F6D_8A70_2387DE188471__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

class CECAEDDoc : public CDocument
{
protected: // create from serialization only
	CECAEDDoc();
	DECLARE_DYNCREATE(CECAEDDoc)
// Attributes
public:
	CBitmap m_bmpIn;
	CBitmap m_bmpOut;
// Operations
public:
// Overrides
	// ClassWizard generated virtual function overrides
	//{{AFX_VIRTUAL(CECAEDDoc)
	public:
	virtual BOOL OnNewDocument();
	virtual void Serialize(CArchive& ar);
	virtual BOOL OnOpenDocument(LPCTSTR lpszPathName);
	//}}AFX_VIRTUAL
// Implementation
public:
	virtual ~CECAEDDoc();
#ifdef _DEBUG
	virtual void AssertValid() const;
	virtual void Dump(CDumpContext& dc) const;
#endif
protected:
// Generated message map functions
protected:
	//{{AFX_MSG(CECAEDDoc)
		// NOTE - the ClassWizard will add and remove member functions here.
		//    DO NOT EDIT what you see in these blocks of generated code !
	//}}AFX_MSG
	DECLARE_MESSAGE_MAP()
};
/////////////////////////////////////////////////////////////////////////////
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.
#endif // !defined(AFX_ECAEDDOC_H__64E67B6C_E0ED_4F6D_8A70_2387DE188471__INCLUDED_)



ECAEDDoc.cpp



ECAEDDoc.cpp

// ECAEDDoc.cpp : implementation of the CECAEDDoc class
//
#include "stdafx.h"
#include "ECAED.h"
#include "ECAEDDoc.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
// CECAEDDoc
IMPLEMENT_DYNCREATE(CECAEDDoc, CDocument)
BEGIN_MESSAGE_MAP(CECAEDDoc, CDocument)
	//{{AFX_MSG_MAP(CECAEDDoc)
		// NOTE - the ClassWizard will add and remove mapping macros here.
		//    DO NOT EDIT what you see in these blocks of generated code!
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CECAEDDoc construction/destruction
CECAEDDoc::CECAEDDoc()
{
	// TODO: add one-time construction code here
}
CECAEDDoc::~CECAEDDoc()
{
}
BOOL CECAEDDoc::OnNewDocument()
{
	if (!CDocument::OnNewDocument())
		return FALSE;
	// TODO: add reinitialization code here
	// (SDI documents will reuse this document)
	return TRUE;
}

/////////////////////////////////////////////////////////////////////////////
// CECAEDDoc serialization
void CECAEDDoc::Serialize(CArchive& ar)
{
	if (ar.IsStoring())
	{
		// TODO: add storing code here
	}
	else
	{
		// TODO: add loading code here
	}
}
/////////////////////////////////////////////////////////////////////////////
// CECAEDDoc diagnostics
#ifdef _DEBUG
void CECAEDDoc::AssertValid() const
{
	CDocument::AssertValid();
}
void CECAEDDoc::Dump(CDumpContext& dc) const
{
	CDocument::Dump(dc);
}
#endif //_DEBUG
/////////////////////////////////////////////////////////////////////////////
// CECAEDDoc commands
BOOL CECAEDDoc::OnOpenDocument(LPCTSTR lpszPathName) 
{
	if (!CDocument::OnOpenDocument(lpszPathName))
		return FALSE;
	
	// TODO: Add your specialized creation code here
	// Load the selected bitmap file
	HBITMAP hBitmap = (HBITMAP)::LoadImage(NULL, lpszPathName, IMAGE_BITMAP, 0, 0, LR_CREATEDIBSECTION | LR_LOADFROMFILE);
	
	// Do we have a valid handle for the loaded image?
	if (hBitmap)
	{
		// Delete the current bitmap
		m_bmpIn.DeleteObject();
		
		// Attach the currently loaded bitmap to the bitmap object
		m_bmpIn.Attach(hBitmap);
	}
	DIBSECTION ds;
	
	::GetObject(hBitmap, sizeof(DIBSECTION), &ds);
	BITMAPINFO bmi;
	LPBYTE pBits = (LPBYTE)ds.dsBm.bmBits;
	LPBYTE pBitsOut;
	HBITMAP hBitmapOut;
	// Initialize header to 0s.
	ZeroMemory(&bmi, sizeof(bmi));
	// Fill out the fields you care about.
	bmi.bmiHeader = ds.dsBmih;
	hBitmapOut = CreateDIBSection(GetDC(NULL), &bmi, DIB_RGB_COLORS, (LPVOID*)&pBitsOut, NULL, 0);
	if (!hBitmap || !pBitsOut)
		return NULL;
	
	// Do we have a valid handle for the created image?
	if (hBitmapOut)
	{
		// Delete the current bitmap
		m_bmpOut.DeleteObject();
		
		// Attach the currently loaded bitmap to the bitmap object
		m_bmpOut.Attach(hBitmapOut);
	}
	DIBSECTION dsOut;
	
	::GetObject(hBitmapOut, sizeof(DIBSECTION), &dsOut);
	
	::SetDIBits(GetDC(NULL), hBitmapOut, 0, dsOut.dsBm.bmHeight, pBits, &bmi, DIB_RGB_COLORS);
	
	int Mask[3][3] = {{-2, -1, -2},
					  {-1, 12, -1},
					  {-2, -1, -2}};
	int sumR;
	int sumG;
	int sumB;
	
	for (int y = 0; y < dsOut.dsBm.bmHeight; y ++)
		for (int x = 0; x < dsOut.dsBm.bmWidth; x ++)
		{
			sumR = 0;
			sumG = 0;
			sumB = 0;
			for (int i = 0; i < 3; i ++)
			{
				if ((y + i - 1) < 0 || (y + i - 1) > dsOut.dsBm.bmHeight)
						continue;
				for (int j = 0; j < 3; j ++)
				{
					if ((x + j - 1) < 0 || (x + j - 1) > dsOut.dsBm.bmWidth)
						continue;
					
					sumB += pBits[(y + i - 1) * ds.dsBm.bmWidthBytes + (x * ds.dsBm.bmBitsPixel / 8) + j - 1] * Mask[i][j] / 2;
					sumG += pBits[(y + i - 1) * ds.dsBm.bmWidthBytes + (x * ds.dsBm.bmBitsPixel / 8) + j - 1 + 1] * Mask[i][j] / 2;
					sumR += pBits[(y + i - 1) * ds.dsBm.bmWidthBytes + (x * ds.dsBm.bmBitsPixel / 8) + j - 1 + 2] * Mask[i][j] / 2;
				}
			}
			if (sumR < 0)
				sumR = 0;
			if (sumR > 255)
				sumR = 255;
			if (sumG < 0)
				sumG = 0;
			if (sumG > 255)
				sumG = 255;
			if (sumB < 0)
				sumB = 0;
			if (sumB > 255)
				sumB = 255;
			pBitsOut[y * dsOut.dsBm.bmWidthBytes + (x * dsOut.dsBm.bmBitsPixel / 8)] = sumB;
			pBitsOut[y * dsOut.dsBm.bmWidthBytes + (x * dsOut.dsBm.bmBitsPixel / 8) + 1] = sumG;
			pBitsOut[y * dsOut.dsBm.bmWidthBytes + (x * dsOut.dsBm.bmBitsPixel / 8) + 2] = sumR;
		}
		
		return TRUE;
}



这是该应用程序的屏幕截图:


我不知道如何解决它!?



and here is a screenshot of the app:


I don''t know how to fix it !?


1.编译应用程序的调试版本.

2.在调试器下运行您的应用.

3.崩溃时,选择重试".

4.调试器将向您显示崩溃的行.

5.查看该行中引用的变量.最有可能的是,它将是某种类型的指针,或者是超出范围的数组索引.

6.如果无法解决,请在此处再次发布.
1. Compile the Debug version of your app.

2. Run your app under the debugger.

3. When it crashes, choose "Retry".

4. The debugger will show you the line where it crashed.

5. Look at variables that are referenced in that line. Most likely, it will be a pointer of some kind, or an array index out of bounds.

6. Post again here if you can''t figure it out.


这篇关于使用CBitmap和BITMAP的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆