Introduction
This article explains how to draw gradient colors in your Windows application. This article requires some basic knowledge of MFC classes and GUI. The code below is very easy and well-commented - I have commented out every sentence that I thought it might be helpful to comment it out. All the idea is to get RGB values of two colors, and then draw and fill rectangles using these colors and all 256 colors that lie between them to create a gradient image like ones we see in Setup and Installation programs.
I am still a beginner programmer but if you have any comments or suggestions related to this article then I would be glad to hearing from you. Also, if you have any questions, you can contact me at mohgdeisat@hotmail.com.
Gradient.h
#if !defined(AFX_GRADIENT1_H__39634012_8104_4550_A02B_65C0C7553A60__INCLUDED_)
#define AFX_GRADIENT1_H__39634012_8104_4550_A02B_65C0C7553A60__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif
class CGradient
{
public:
CGradient(CSize=CSize(800,600));
virtual ~CGradient();
void PrepareVertical(CDC *pDC,UINT RTop,
UINT GTop,UINT BTOP,UINT RBot,UINT GBot,UINT BBot);
void PrepareHorizontal(CDC *pDC,UINT RRight,
UINT GRight,UINT BRight,UINT RLeft,UINT GLeft,UINT BLeft);
CSize GetDimensions();
void SetDimensions(CSize Size);
void Draw(CDC *pDC, int xDest,int yDest,int xSrc,
int ySrc, int Width, int Height,DWORD Rop);
protected:
CDC *m_dcMem;
CSize m_Size;
};
#endif
And the class implementation goes here:
#include "stdafx.h"
#include "Gradient.h"
#include "Gradient1.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
CGradient::CGradient(CSize Size)
{
m_Size=Size;
m_dcMem=NULL;
}
CGradient::~CGradient()
{
if(m_dcMem!=NULL)
delete m_dcMem;
}
CSize CGradient::GetDimensions()
{
return m_Size;
}
void CGradient::SetDimensions(CSize Size)
{
m_Size=Size;
}
void CGradient::PrepareVertical(CDC *pDC,UINT RTop,
UINT GTop,UINT BTop,UINT RBot,UINT GBot,UINT BBot)
{
if(m_dcMem!=NULL)
{
delete m_dcMem;
}
CBitmap Bitmap;
m_dcMem=new CDC;
m_dcMem->CreateCompatibleDC(pDC);
m_dcMem->SetMapMode(MM_TEXT);
Bitmap.CreateCompatibleBitmap(pDC,m_Size.cx,m_Size.cy);
m_dcMem->SelectObject(&Bitmap);
double rStep,gStep,bStep;
double rCount,gCount,bCount;
double RectHeight=m_Size.cy/256.0;
const int NUM_COLORS=256;
rCount=RTop;
gCount=GTop;
bCount=BTop;
rStep=-((double)RTop-RBot)/NUM_COLORS;
gStep=-((double)GTop-GBot)/NUM_COLORS;
bStep=-((double)BTop-BBot)/NUM_COLORS;
for(int ColorCount=0;ColorCount<NUM_COLORS;ColorCount++)
{
m_dcMem->FillRect(CRect(0,ColorCount*RectHeight,
m_Size.cx,(ColorCount+1)*RectHeight),
&CBrush(RGB(rCount,gCount,bCount)));
rCount+=rStep;
gCount+=gStep;
bCount+=bStep;
}
}
void CGradient::PrepareHorizontal(CDC *pDC,UINT RLeft,
UINT GLeft,UINT BLeft,UINT RRight,UINT GRight,UINT BRight)
{
if(m_dcMem!=NULL)
{
delete m_dcMem;
}
CBitmap Bitmap;
m_dcMem=new CDC;
m_dcMem->CreateCompatibleDC(pDC);
m_dcMem->SetMapMode(MM_TEXT);
Bitmap.CreateCompatibleBitmap(pDC,m_Size.cx,m_Size.cy);
m_dcMem->SelectObject(&Bitmap);
double rStep,gStep,bStep;
double rCount,gCount,bCount;
double RectWidth=m_Size.cx/256.0;
const int NUM_COLORS=256;
rCount=RRight;
gCount=GRight;
bCount=BRight;
rStep=-((double)RRight-RLeft)/NUM_COLORS;
gStep=-((double)GRight-GLeft)/NUM_COLORS;
bStep=-((double)BRight-BLeft)/NUM_COLORS;
for(int ColorCount=0;ColorCount<NUM_COLORS;ColorCount++)
{
m_dcMem->FillRect(CRect(ColorCount*RectWidth,
0,(ColorCount+1)*RectWidth,m_Size.cy),
&CBrush(RGB(rCount,gCount,bCount)));
rCount+=rStep;
gCount+=gStep;
bCount+=bStep;
}
}
void CGradient::Draw(CDC *pDC, int xDest,int yDest,
int xSrc, int ySrc, int Width, int Height,DWORD Rop)
{
pDC->BitBlt(xDest,yDest,Width,Height,m_dcMem,xSrc,ySrc,Rop);
}