Click here to Skip to main content
15,867,686 members
Articles / Desktop Programming / MFC

Column based selection in rich edit control.

Rate me:
Please Sign up or sign in to vote.
5.00/5 (12 votes)
22 May 2012CPL3 min read 41.8K   2.7K   32   7
Column based selection in rich edit control.

 

Introduction 

This project will help you to understand about column based selection and how to implement Column Based selection in your project.  I had been searching this type of article or help but didn't find which imposed me to create such type of application.  I hope they will be beneficial who want to implement column based selection feature in their editor. 

Below I have shown some pictures those depict column based selection feature in other application. 

 Image 1

 Column based selection in Visual Studio..  

 Image 2

 Column based selection in my application's rich edit control.  

 In most of the application column based selection can be achived by "pressing Alt + drag the mouse" . The way is same in my application also.  

 

Background     

The strategy was simple  

1. First create a new a bitmap from the viewable part of edit control. But process this bitmap in such a way that text color will be white and backgorund (except text area)  color will be blue.

2. After processing keep this bitmap in a DC(device context). In my case this is m_processedDC.  

3. Now calculate user selected area and store 2 points in 2 member variable. 2 points means starting point and ending point. Ending point has to be continuously updated by mouse move message.

4. After user selected Rectangle calculation, copy only selected rectangle from m_processedDC to destination DC, in my case which is rich edit control's DC (device context), by BitBlt() method. 

5. Now user will see that some area his been selected . 

Code  explanation

Some important areas of code I going to explain below, 

1. I have implemented this in CColBasedRichEdit class which is inherited from MFC's CRichEditCtrl . 

2. Create a memory DC which is compatible with the application's current screen and create a bitmap which is compatible with the RichEdit control's device.  

C++
m_processedDC = ::CreateCompatibleDC(NULL);
HBITMAP bmpREdit = ::CreateCompatibleBitmap(*pDC, rcClient.Width(), rcClient.Height() );
::SelectObject(m_processedDC, bmpREdit);

3. Create a solid brush with current highlight color of system and fill destination DC's background with currently created brush .

C++
COLORREF clrHilite = ::GetSysColor(COLOR_HIGHLIGHT);
HBRUSH brHilite = CreateSolidBrush( clrHilite);
::FillRect(m_processedDC, CRect(0, 0, rcClient.Width(), rcClient.Height()), brHilite);

4. Create a bitmap with the specified width and height but its contents is undefined (as NULL)

C++
CHBITMAP hMemBmp = CreateBitmap(rcClient.Width(), rcClient.Height(), 1, 1/*BitsPerPixel*/, NULL);

 here 4th parameter ask to assign number of bits per pixel and we have assigned "1", so the resulted Bitmap will be a Black & White bitmap.  Now keep new bitmap in m_hSelectionDC DC.

5. Copy RichEdit's DC to 'm_hSelectionDC

C++
BitBlt(m_hSelectionDC, 0, 0, rcClient.Width(), rcClient.Height(), *pDC, 0, 0, SRCCOPY);

important thing is 'm_hSelectionDC' has Black & White pixel , so if u paint 'm_hSelectionDC' some where to test then u will see that a Black & Whilte image of rich edit control. Purpose of making Black&Whilte image is if RichEdit ctrl has different color character(text).

6. Now important part.  Here we can see the magic of 'MERGEPAINT'.

C++
BitBlt(m_processedDC, 0,0, rcClient.Width(), rcClient.Height(),  m_hSelectionDC , 0, 0, MERGEPAINT );

First Inverte the pixel of source DC.
Second Merge the color of 'm_processedDC' with 'm_hSelectionDC' (pixel by pixel)
Do u remember that pixel of 'm_processedDC' is the hilight color pixel of current system.

7. Now at this point we have got/prepared our m_processedDC<code>  and it is ready to use. 

8. In the mouse move message I calculate starting point and ending point of user selection.  

C++
// Adjust end line position
CPoint ptTemp =  PosFromChar( CharFromPos( point ) );
ptTemp.x = ptTemp.x + m_FontWidth - 2;
ptTemp.y = ptTemp.y + m_FontHeight - 2;
//m_colSelEndPt = ptTemp;
		
if(( ptTemp.x > (m_colSelEndPt.x + 4)) || ( ptTemp.x < (m_colSelEndPt.x - 4)  ) 
|| ( ptTemp.y > (m_colSelEndPt.y + 4)) || ( ptTemp.y < (m_colSelEndPt.y - 4)) )
{
m_colSelEndPt = ptTemp;

Invalidate();
UpdateWindow();  } 
 

9. To copy the selected area/text I have used MSDN's clipboard concept which actually allocate global memory/shared memory , 

C++
hClipboardData = (HGLOBAL)GlobalAlloc(GMEM_DDESHARE, sizeText);
pszClipText = (LPTSTR)GlobalLock((HGLOBAL)hClipboardData);
SetClipboardData(CF_UNICODETEXT/*CF_TEXT*/, hClipboardData);

 

How to use 

Download the zip file, which is a VC project (I have used Visual Studio 2005 ), and compile and run.

Select text by pressing ALT key + mouse drag and release both (mouse press and ALT key).

Now click "Copy Selection" button and go to your editor and paste it.

Points of Interest

The interesting thing is appearance/looking of  my application/implementation , however, is better  than some application, like - Edit Plus.

I have used Rich edit control of MFC but if anyone grab the basic concept then it can be implemented with any Programming language.    

License

This article, along with any associated source code and files, is licensed under The Common Public License Version 1.0 (CPL)


Written By
Enosis Solution, Dhaka
Bangladesh Bangladesh
Liveing in Dhaka.
Working at Enosis Solution.
Studied B.Sc. in Computer Science from Bangalore University.

Comments and Discussions

 
QuestionSuggestions on how to implement in .NET Pin
Kalkidas23-Mar-16 3:58
Kalkidas23-Mar-16 3:58 
Bugi have create the RichEditCtrl dynamic while it crashed ...... Pin
alannx15-Aug-12 21:09
alannx15-Aug-12 21:09 
GeneralRe: i have create the RichEditCtrl dynamic while it crashed ...... Pin
Mahfuzur Rahman.17-Aug-12 0:08
Mahfuzur Rahman.17-Aug-12 0:08 
QuestionGood job Pin
alannx15-Aug-12 21:02
alannx15-Aug-12 21:02 
AnswerRe: Good job Pin
Mahfuzur Rahman.17-Aug-12 0:06
Mahfuzur Rahman.17-Aug-12 0:06 
GeneralMy vote of 5 Pin
magicpapacy28-May-12 17:57
magicpapacy28-May-12 17:57 
Good Article, but I think you should get system default color first,not only use highlight white
GeneralMy vote of 5 Pin
Mukit, Ataul23-May-12 20:23
Mukit, Ataul23-May-12 20:23 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.