2 * @file GhostTextBuffer.h
4 * @brief Declaration of CGhostTextBuffer (subclasses CCrystalTextBuffer to handle ghost lines)
7 #ifndef __GHOSTTEXTBUFFER_H__
8 #define __GHOSTTEXTBUFFER_H__
11 #include "ccrystaltextbuffer.h"
14 /////////////////////////////////////////////////////////////////////////////
17 We use the current ccrystalEditor flags
19 This flag must be cleared and set in GhostTextBuffer.cpp
20 and MergeDoc.cpp (Rescan) only.
22 GetLineColors (in MergeEditView) reads it to choose the line color.
27 LF_GHOST = 0x00400000L,
33 /////////////////////////////////////////////////////////////////////////////
34 // CCrystalTextBuffer command target
37 Features offered with this class :
39 <li> apparent/real line conversion
40 <li> insertText/deleteText working with ghost lines
41 <li> AddUndoRecord/Undo/Redo working with ghost lines
42 <li> insertGhostLine function
45 class EDITPADC_CLASS CGhostTextBuffer : public CCrystalTextBuffer
48 DECLARE_DYNCREATE (CGhostTextBuffer)
52 // Nested class declarations
56 int m_nLength, m_nMax;
57 int m_nEolChars; // # of eolchars
59 DWORD m_dwRevisionNumber;
61 int FullLength() const { return m_nLength+m_nEolChars; }
62 int Length() const { return m_nLength; }
66 memset (this, 0, sizeof (SLineInfo));
73 UNDO_BEGINGROUP = 0x0100
77 Support For Descriptions On Undo/Redo Actions
79 We need a structure to remember richer information position
80 and the number of real lines inserted/deleted (to set ghost lines during undo)
82 This flags are parameters of AddUndoRecord ; so AddUndoRecord
83 is not the virtual version of CCrystalTextBuffer::AddUndoRecord
85 The text is duplicated (already in CCrystalTextBuffer::SUndoRecord),
86 and it is not useful. If someone finds a clean way to correct this...
92 // Undo records store file line numbers, not screen line numbers
93 // File line numbers do not count ghost lines
94 // (ghost lines are lines with no text and no EOL chars, which are
95 // used by WinMerge as left-only or right-only placeholders)
96 // All the stored line number needed are real !
98 CPoint m_ptStartPos, m_ptEndPos; // Block of text participating
99 int m_ptStartPos_nGhost, m_ptEndPos_nGhost;
101 // Redo records store file line numbers, not screen line numbers
102 // they store the file number of the previous real line
103 // and (apparentLine - ComputeApparentLine(previousRealLine))
105 CPoint m_redo_ptStartPos, m_redo_ptEndPos; // Block of text participating
106 int m_redo_ptStartPos_nGhost, m_redo_ptEndPos_nGhost;
108 int m_nRealLinesCreated; // number of lines created during insertion
109 // (= total of real lines after - total before)
110 int m_nRealLinesInDeletedBlock; // number of real lines in the deleted block
111 // (<> total of real lines after - total before
112 // as first/end line may be just truncated, not removed)
113 int m_nAction; // For information only: action type
114 CDWordArray *m_paSavedRevisonNumbers;
118 // Since in most cases we have 1 character here,
119 // we should invent a better way. Note: 2 * sizeof(WORD) <= sizeof(TCHAR*)
121 // Here we will use the following trick: on Win32 platforms high-order word
122 // of any pointer will be != 0. So we can store 1 character strings without
123 // allocating memory.
128 TCHAR *m_pszText; // For cases when we have > 1 character strings
130 TCHAR m_szText[2]; // For single-character strings
135 SUndoRecord () // default constructor
137 memset (this, 0, sizeof (SUndoRecord));
139 SUndoRecord (const SUndoRecord & src) // copy constructor
141 memset (this, 0, sizeof (SUndoRecord));
144 SUndoRecord & operator=(const SUndoRecord & src) // copy assignment
146 m_dwFlags = src.m_dwFlags;
147 m_ptStartPos = src.m_ptStartPos;
148 m_ptStartPos_nGhost = src.m_ptStartPos_nGhost;
149 m_ptEndPos = src.m_ptEndPos;
150 m_ptEndPos_nGhost = src.m_ptEndPos_nGhost;
151 m_nAction = src.m_nAction;
152 m_redo_ptStartPos = src.m_redo_ptStartPos;
153 m_redo_ptStartPos_nGhost = src.m_redo_ptStartPos_nGhost;
154 m_redo_ptEndPos = src.m_redo_ptEndPos;
155 m_redo_ptEndPos_nGhost = src.m_redo_ptEndPos_nGhost;
156 m_nRealLinesCreated = src.m_nRealLinesCreated;
157 m_nRealLinesInDeletedBlock = src.m_nRealLinesInDeletedBlock;
158 SetText(src.GetText());
159 INT_PTR size = src.m_paSavedRevisonNumbers->GetSize();
160 m_paSavedRevisonNumbers = new CDWordArray();
161 m_paSavedRevisonNumbers->SetSize(size);
163 for (i = 0; i < size; i++)
164 (*m_paSavedRevisonNumbers)[i] = (*src.m_paSavedRevisonNumbers)[i];
167 ~SUndoRecord () // destructor
170 if (m_paSavedRevisonNumbers)
171 delete m_paSavedRevisonNumbers;
174 void SetText (LPCTSTR pszText);
177 LPCTSTR GetText () const
179 // see the m_szText/m_pszText definition about the use of HIWORD
180 if (HIWORD ((DWORD) m_pszText) != 0)
190 We need another array with our richer structure.
192 We share the positions with the CCrystalTextBuffer object.
193 We share m_bUndoGroup, its utility is to check we opened the UndoBeginGroup.
194 We share m_nUndoBufSize which is the max buffer size.
196 CArray < SUndoRecord, SUndoRecord & >m_aUndoBuf;
198 This one must be duplicated because the flag UNDO_BEGINGROUP needs to be set in both
199 CGhostTextBuffer::m_aUndoBuf and CCrystalTextBuffer::m_aUndoBuf CArrays
201 BOOL m_bUndoBeginGroup;
203 // [JRT] Support For Descriptions On Undo/Redo Actions
204 virtual void AddUndoRecord (BOOL bInsert, const CPoint & ptStartPos, const CPoint & ptEndPos,
205 LPCTSTR pszText, int nRealLinesChanged, int nActionType = CE_ACTION_UNKNOWN, CDWordArray *paSavedRevisonNumbers = NULL);
208 // A RealityBlock is a block of lines with no ghost lines
209 struct RealityBlock { int nStartReal; int nStartApparent; int nCount; };
210 // The array of reality blocks is kept in order
211 CArray < RealityBlock, RealityBlock& > m_RealityBlocks;
217 BOOL InternalInsertGhostLine (CCrystalTextView * pSource, int nLine);
218 BOOL InternalDeleteGhostLine (CCrystalTextView * pSource, int nLine, int nCount);
220 // Construction/destruction code
222 virtual BOOL InitNew (int nCrlfStyle = CRLF_STYLE_DOS);
225 This should work in base code as ghost lines are real empty lines
226 but maybe it doesn't (if there is an assert to check there is an EOL,
227 or if it adds the default EOL)
229 virtual void GetTextWithoutEmptys (int nStartLine, int nStartChar, int nEndLine, int nEndChar, CString &text, int nCrlfStyle =CRLF_STYLE_AUTOMATIC );
232 // Text modification functions
233 virtual BOOL InsertText (CCrystalTextView * pSource, int nLine, int nPos, LPCTSTR pszText, int &nEndLine, int &nEndChar, int nAction = CE_ACTION_UNKNOWN, BOOL bHistory =TRUE);
234 virtual BOOL DeleteText (CCrystalTextView * pSource, int nStartLine, int nStartPos, int nEndLine, int nEndPos, int nAction = CE_ACTION_UNKNOWN, BOOL bHistory =TRUE);
235 BOOL InsertGhostLine (CCrystalTextView * pSource, int nLine);
238 virtual BOOL Undo (CCrystalTextView * pSource, CPoint & ptCursorPos);
239 virtual BOOL Redo (CCrystalTextView * pSource, CPoint & ptCursorPos);
242 virtual void BeginUndoGroup (BOOL bMergeWithPrevious = FALSE);
243 virtual void FlushUndoGroup (CCrystalTextView * pSource);
247 Code for mapping between file line numbers (real line numbers)
248 and screen line numbers (apparent line numbers).
250 This is needed to handle ghost lines (ones with no text or EOL chars)
251 which WinMerge uses for left-only or right-only lines.
253 int ApparentLastRealLine() const;
254 int ComputeRealLine(int nApparentLine) const;
255 int ComputeApparentLine(int nRealLine) const;
256 /** richer position information yApparent = apparent(yReal) - yGhost */
257 int ComputeRealLineAndGhostAdjustment(int nApparentLine, int& decToReal) const;
258 /** richer position information yApparent = apparent(yReal) - yGhost */
259 int ComputeApparentLine(int nRealLine, int decToReal) const;
261 /** for loading file */
262 void FinishLoading();
263 /** for saving file */
264 void RemoveAllGhostLines();
268 void RecomputeRealityMapping();
270 Code to set EOL, if the status ghost/real of the line changes
272 We should call a CCrystalTextBuffer function to add the correct EOL
273 (if CCrystalTextBuffer keeps the default EOL for the file)
275 void RecomputeEOL(CCrystalTextView * pSource, int nStartLine, int nEndLine);
276 /** For debugging purpose */
277 void checkFlagsFromReality(BOOL bFlag) const;
280 virtual void OnNotifyLineHasBeenEdited(int nLine);
285 // ClassWizard generated virtual function overrides
286 //{{AFX_VIRTUAL(CCrystalTextBuffer)
289 // Generated message map functions
290 //{{AFX_MSG(CCrystalTextBuffer)
293 DECLARE_MESSAGE_MAP ()
296 /////////////////////////////////////////////////////////////////////////////
298 //{{AFX_INSERT_LOCATION}}
299 // Microsoft Developer Studio will insert additional declarations immediately before the previous line.
302 #endif //__GHOSTTEXTBUFFER_H__