I add my program two RichEdit which the one displays binary contents and the another shows the index of the byte. I hope these two edit always anchor on the same position while/after scrolling.
A possible way is to handle the main RichEdit's WM_VSCROLL and WM_MOUSEWHEEL message and pass the message and parameters to the second RichEdit. I've tried this but I found that the two edits aligned not very well. And the other disadvantage is the both RichEdits' scroll bar needs to be enabled, if I only enable one, the another can't receive WM_MOUSEWHEEL message, but I hope one scroll bar displayed only.
The second way I've tried is using a timer and synchronize with LINESCROLL regularly by the time (< 10ms is better). This works well most of the time, but sometimes still have the unaligned issue.
Is there a better solution to handle this kind of demand?
//---------------------------------------------------------------------------
void __fastcall TBinaryEdit::Timer1Timer(TObject *Sender)
{
int srcLine = 0;
int trgLine = 0;
if (Sender == Timer1) {
srcLine = GetRichEditLineNo(MainEdit);
trgLine = GetRichEditLineNo(IndexEdit);
if (srcLine != trgLine) {
SendMessage(IndexEdit->Handle, EM_LINESCROLL, 0, srcLine - trgLine);
}
}
}
//---------------------------------------------------------------------------
int TBinaryEdit::GetRichEditLineNo(TRichEdit* RE)
{
int line;
int wordpos;
TRect rt;
POINTL pt;
SendMessage(RE->Handle, EM_GETRECT, 0, LPARAM(&rt));
pt.x = RE->Left + rt.left;
pt.y = RE->Top + rt.top;
wordpos = SendMessage(RE->Handle, EM_CHARFROMPOS, 0, LPARAM(&pt));
line = SendMessage(RE->Handle, EM_LINEFROMCHAR, wordpos, 0);
return line;
}
Thanks for your help. I've found a simple solution for my short-term need.
As I mentioned before, the second RichEdit's scroll bar should be enabled for receiving WM_MOUSEWHEEL message, but I don't like both edit have scroll bar displayed. For this reason, I use EM_LINESCROLL instead to replace the mouse wheel message. I write a sub class derive the TRichEdit and overwrite its WM_MOUSEWHEEL handler, then pass EM_LINESCROLL message with the mouse wheel's delta value to both RichEdits.
int zDelta = GET_WHEEL_DELTA_WPARAM(Message.WParam);
int scroll = zDelta == -120 ? 1 : -1;
SendMessage(MainEdit->Handle, EM_LINESCROLL, 0, scroll);
SendMessage(IndexEdit->Handle, EM_LINESCROLL, 0, scroll);
This makes the text vertical offset in RichEdits be aligned. But I think there must be better solution, I will keep research for improvement.