1.°¡»ó À§Ä¡

°¡.°¡»ó À§Ä¡·Î À̵¿

ÅØ½ºÆ® ÆíÁý±â³ª ¿öµå ÇÁ·Î¼¼¼­³ª ±ÛÀÚ°¡ ÀÖ´Â °÷À¸·Î¸¸ ij·µÀÌ À̵¿ÇÒ ¼ö ÀÖÀ¸¸ç ±ÛÀÚ°¡ ¾ø´Â ºó °ø°£Àº ´ëÀÀµÇ´Â ¸Þ¸ð¸® À§Ä¡°¡ ¾øÀ¸¹Ç·Î À̵¿ÇÒ ¼ö ¾ø´Ù. °¡»ó À§Ä¡¶õ ±ÛÀÚ°¡ Á¸ÀçÇÏÁö ¾Ê´Â À§Ä¡¸¦ ¸»Çϴµ¥ ÀÌ À§Ä¡·Îµµ À̵¿ÇÏ´Â ±â´ÉÀº ±×·¡ÇÈ ¹®ÀÚ·Î µµÇ¥¸¦ ±×¸± ¶§³ª ¾µ¸¸ÇÏÁö º°·Î ½Ç¿ëÀûÀÌÁö ¸øÇÑ´Ù. ÀÌ·± ±â´ÉÀº ¾Æ¿¹ ¾ø¾îµµ »ó°üÀÌ ¾øÁö¸¸ ¿­¸ðµå¸¦ À§Çؼ­´Â ¹Ýµå½Ã Áö¿øÇØ¾ß ÇÑ´Ù. ¿­ ¼±ÅÃÀ» ÇÏ´Â Áß¿¡´Â ¹®ÀÚ°¡ ¾ø´Â ºÎºÐÀ¸·Îµµ À̵¿ÇÒ ¼ö ÀÖ¾î¾ß Á÷»ç°¢Çü ¿µ¿ªÀ» ¼±ÅÃÇÒ ¼ö ÀÖ´Ù.

ÀÌ Àå¿¡¼­´Â ¿­¸ðµå·Î ºí·ÏÀ» ¼±ÅÃÇÏ´Â ±â´ÉÀ» ÀÛ¼ºÇϴµ¥ ±× Àü¿¡ °¡»ó À§Ä¡·Î À̵¿ÇÏ´Â ±â´ÉÀÌ ¸ÕÀú ÀÛ¼ºµÇ¾î¾ß ÇÑ´Ù. °¡»ó À§Ä¡¿¡ ij·µÀÌ À§Ä¡ÇÒ ¶§´Â Åë»óÀûÀÎ Çà·Ä ÁÂÇ¥·Î ij·µÀÇ ÁÂÇ¥¸¦ Ç¥ÇöÇÒ ¼ö ¾øÀ¸¹Ç·Î º°µµÀÇ Ãß°¡ Á¤º¸°¡ ÇÊ¿äÇÏ´Ù. ¹º°¡ °ñÄ¡¾ÆÆÄÁø´Ù´Â »ý°¢ÀÌ µé °ÍÀÌ´Ù. ÀÌ Á¤º¸µéÀº ºäÀÇ »óÅ¿¡ ¼ÓÇϹǷΠ´ÙÀ½ º¯¼öµéÀ» ±âº» ºä Ŭ·¡½º¿¡ ¼±¾ðÇÑ´Ù.

 

class CApiEditText : public CWindow

{

     ....

     BOOL bVirtualPos;

     int ExtraX;

     int ignoreVirt;

 

public:

     virtual BOOL GetVirtualPos() { return bVirtualPos; }

     virtual void SetVirtualPos(int aValue);

     virtual BOOL IsVirtualPosable();

};

 

°¡»ó À§Ä¡¿¡ ij·µÀÌ ÀÖ´Â »óŸ¦ ±â¾ïÇÏ´Â ¹æ¹ý¿¡´Â ¿©·¯ °¡Áö°¡ ÀÖÀ» ¼ö ÀÖ´Ù. ApiEdit´Â ExtraX·Î ÁÙ ³¡¿¡¼­ ¹þ¾î³­ Á¤µµ¸¦ °ø¹éÆø ´ÜÀ§·Î ±â¾ïÇÑ´Ù. ExtraX´Â 0À» Æ÷ÇÔÇÑ ¾çÀÇ Á¤¼öÀÌ´Ù. Áö±Ý±îÁö ij·µÀÇ À§Ä¡´Â off·Î¸¸ °áÁ¤µÇ¾úÁö¸¸ ÀÌÁ¦ ExtraXµµ °°ÀÌ °í·ÁµÇ¾î¾ß ÇÑ´Ù. ¹®¼­ÀÇ ÇöÀç »óŸ¦ ³ªÅ¸³»´Â »óŰªÀÇ ÀÏÁ¾À̹ǷΠÇÔ¼ö Çϳª·Î Á¶»çÇÒ ¼ö ¾øÀ¸¸ç Àü¿ªÀûÀÎ º¯¼ö¿¡ ±â¾ïÇØ µÎ¾î¾ß ÇÑ´Ù.

ExtraX Á¤º¸·Î ÀÎÇØ ¼öÆòÀ¸·Î ÁÙ ³Ê¸Ó¿¡ ij·µÀÌ ÀÖ´Â »óŸ¦ Ç¥ÇöÇÒ ¼ö ÀÖÁö¸¸ ¼öÁ÷À¸·Î ¹®¼­ ³Ê¸Ó·Î´Â ij·µÀÌ À̵¿ÇÒ ¼ö ¾ø´Ù. ¸¸¾à ²À ÇÊ¿äÇÏ´Ù¸é ExtraY¶ó´Â º¯¼ö¸¦ ¸¸µé°í ¹®¼­ ³¡¿¡¼­ºÎÅÍ ¸î ÁÙÀ̳ª ´õ ³»·Á°¡ ÀÖ´ÂÁö¸¦ ±â¾ïÇÒ ¼ö ÀÖ°ÚÁö¸¸ ExtraX Çϳª¸¸ ÇØµµ ÃæºÐÈ÷ º¹ÀâÇϹǷΠ¹®¼­ ³¡À» ³Ñ¾î¼± À§Ä¡±îÁö´Â °í·ÁÇÏÁö ¾Ê±â·Î ÇÑ´Ù. ¿­¸ðµå¿¡¼­µµ ¹®¼­ ³Ê¸Ó±îÁö ¼±ÅÃÇÒ ÇÊ¿ä´Â ¾ø´Ù. ´ëÃæ ¿¹»óÀÌ µÇ°ÚÁö¸¸ ExtraX¸¦ Á¦´ë·Î °ü¸®ÇÏ´Â °ÍÀº ¹«Ã´ ¾î·Æ°í ±î´Ù·Ó´Ù.

bVirtualPos´Â °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö Àִ°¡ ¾Æ´Ñ°¡¸¦ ±â¾ïÇÏ´Â ¿É¼Ç º¯¼öÀ̸ç ÀÌ °ªÀÌ TRUE¿©¾ß¸¸ °¡»ó À§Ä¡·Î ij·µÀÌ À̵¿ÇÒ ¼ö ÀÖ´Ù. ignoreVirt´Â °¡»ó À§Ä¡ ¿É¼ÇÀ» ÀϽÃÀûÀ¸·Î Á¤Áö½Ã۱â À§ÇÑ Ä«¿îÆ® º¯¼öÀε¥ ÀÌ º¯¼ö°¡ 0ÀÏ ¶§¸¸ °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö ÀÖÀ¸¸ç 0ÀÌ ¾Æ´Ï¸é ¼³»ç bVirtualPos°¡ TRUEÀÌ´õ¶óµµ °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö ¾ø´Ù. ÀÌ º¯¼ö°¡ ¿Ö ÇÊ¿äÇѰ¡ ÇÏ¸é °¡»ó À§Ä¡·Î À̵¿ °¡´ÉÇϵµ·Ï ¼³Á¤µÈ »óȲ¿¡¼­µµ ºí·ÏÀ» ¼±ÅÃÇÒ ¶§¸¸Å­Àº °¡»ó À§Ä¡±îÁö ¼±ÅÃÇÒ ¼ö ¾ø¾î¾ß Çϱ⠶§¹®ÀÌ´Ù. Àá½Ã ÈÄ ÀÌ µÎ º¯¼öÀÇ ¿ªÇÒÀ» º¸¸é ÀÌ·± »óŰªÀÌ ¿Ö ÇÊ¿äÇÑÁö ¾Ë ¼ö ÀÖÀ» °ÍÀÌ´Ù.

bVirtualPos °ªÀ» ÀÐ°í ¾²´Â ¾×¼¼½º ÇÔ¼ö°¡ ÀÛ¼ºµÇ¾î Àִµ¥ Get ÇÔ¼ö´Â °£´ÜÇϹǷΠÀζóÀÎÀ¸·Î ÀÛ¼ºÇßÀ¸¸ç Set ÇÔ¼ö´Â ´ÙÀ½°ú °°ÀÌ ÀÛ¼ºÇÑ´Ù. °¡»ó À§Ä¡ ¿É¼ÇÀÌ ÇØÁ¦µÉ ¶§ ExtraX´Â 0ÀÌ µÇ¾î¾ß ÇÏ¸ç °¡»ó À§Ä¡·Î ¹þ¾î³ª Àִ ij·µÀº ÁÙ ³¡À¸·Î °­Á¦·Î ¿Å°Ü¾ß ÇÑ´Ù.

 

void CApiEditText::SetVirtualPos(int aValue)

{

     bVirtualPos=aValue;

     if (bVirtualPos==FALSE && ExtraX > 0) {

          ExtraX=0;

          SetCaret();

     }

}

 

°¡»ó À§Ä¡·ÎÀÇ À̵¿ ±â´ÉÀº Àß »ç¿ëµÇÁö ¾ÊÀ¸¹Ç·Î bVirtualPos ¿É¼ÇÀÇ µðÆúÆ®°ªÀº FALSE·Î ¼³Á¤ÇÏ´Â °ÍÀÌ ÇÕ¸®ÀûÀ̳ª Áö±ÝÀº ÀÌ ±â´ÉÀ» ¸¸µé°í ÀÖ´Â ÁßÀ̹ǷΠ Å×½ºÆ®¸¦ À§ÇØ TRUE·Î ÁöÁ¤ÇÏÀÚ. SetDefaultSetting¿¡¼­ ÀÌ º¯¼öÀÇ ÃʱⰪÀ» ¼³Á¤ÇÑ´Ù.

 

void CApiEditText::SetDefaultSetting()

{

     ....

     bVirtualPos=TRUE;

}

 

ºä°¡ ¸¸µé¾îÁú ¶§´Â °¡»ó À§Ä¡¿¡ ij·µÀÌ °¡ ÀÖ´Â °ÍÀÌ ¾Æ´Ï¹Ç·Î ExtraX´Â 0À¸·Î, ignoreVirtµµ 0À¸·Î ÃʱâÈ­ÇÑ´Ù. ÀÌ µÎ º¯¼ö°ªÀº ºäÀÇ »óŰªÀ̹ǷΠºä°¡ ÃʱâÈ­µÇ´Â InitView¿¡¼­ ÃʱâÈ­ÇÏ´Â °ÍÀÌ ¿Ç´Ù. ºñ½ÁÇÑ ¿ªÇÒÀ» ÇÏ´Â º¯¼öµéµµ ÃʱâÈ­ ½ÃÁ¡À» °áÁ¤ÇϱⰡ ½±Áö ¾Ê´Ù.

 

void CApiEditText::InitView()

{

     ....

    ExtraX=0;

    ignoreVirt=0;

     Invalidate(-1);

}

 

IsVirtualPosable ÇÔ¼ö´Â ÇöÀç ¼³Á¤ »óÅ¿¡¼­ ij·µÀÌ °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö Àִ°¡¸¦ Á¶»çÇϴµ¥ ´ÙÀ½°ú °°ÀÌ ÀÛ¼ºÇÑ´Ù.

 

BOOL CApiEditText::IsVirtualPosable()

{

     if (bVirtualPos) {

          if (ignoreVirt > 0) {

              return FALSE;

          } else {

              return TRUE;

          }

     }

     return FALSE;

}

 

bVirtualPos ¿É¼ÇÀÌ FALSE¶ó¸é °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö ¾ø´Ù. ÀÌ ¿É¼ÇÀÌ TRUEÀÌ´õ¶óµµ ignoreVirt°¡ 0ÀÌ ¾Æ´Ï¸é ÀϽÃÀûÀ¸·Î À̵¿ÀÌ ±ÝÁöµÈ »óÅÂÀ̹ǷΠÀ̶§µµ °¡»ó À§Ä¡·Î °¥ ¼ö ¾ø´Ù. Áï °¡»ó À§Ä¡·Î À̵¿ÇÏ·Á¸é bVirtualPos°¡ TRUE¿©¾ß Çϰí ignoreVirt°¡ 0À̾î¾ß ÇÑ´Ù. ÇöÀç´Â ÀÌ Á¶°Ç»ÓÀÌÁö¸¸ ¿­¸ðµå¿¡¼­´Â Á» ´õ ¸¹Àº Á¶°ÇÀÌ ÇÊ¿äÇØÁú °ÍÀÌ´Ù.

±×·³ ½ÇÁ¦·Î °¡»ó À§Ä¡·Î À̵¿½ÃŰ´Â Äڵ带 ÀÛ¼ºÇØ º¸ÀÚ. ´ëÇ¥ÀûÀ¸·Î ¿À¸¥ÂÊÀ¸·Î À̵¿ÇÏ´Â VK_RIGHTÀÇ Äڵ带 ÀÛ¼ºÇØ º¸ÀÚ. ¿À¸¥ÂÊÀ¸·Î À̵¿ÇÒ ¶§ ij·µÀÌ ÁÙ ³¡¿¡ ´êÀ¸¸é Åë»ó ´ÙÀ½ÁٷΠij·µÀ» ³»¸®´Âµ¥ °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö ÀÖÀ» ¶§´Â ÇöÀç ÁÙ¿¡ ¸Ó¹°¸é¼­ ExtraX¸¦ Áõ°¡½ÃÄÑ¾ß ÇÑ´Ù. OnKeyÀÇ VK_RIGHT¸¦ ´ÙÀ½°ú °°ÀÌ ¼öÁ¤ÇÑ´Ù.

 

     case VK_RIGHT:

        if (off < pFrame->doclen || IsVirtualPosable()) {

              GetRCFromOff(off,r,c);

 

              OldOff=off;

              if (bControl) {

                   off=GetNextWord(off);

              } else {

               if (ExtraX > 0) {

                   ExtraX++;

               } else {

                        if (off==pLine[r].End) {

                       if (AeIsLineEnd(pFrame->buf+off)) {

                          if (IsVirtualPosable()) {

                              ExtraX++;

                          } else {

                                      off=pFrame->GetNextOff(off);

                                 }

                            }

                            bLineEnd=FALSE;

                        } else {

                            off=pFrame->GetNextOff(off);

                            if (off==pLine[r].End && !pFrame->IsEnterCode(off) &&

                                 pFrame->bUseLineEnd) {

                                 bLineEnd=TRUE;

                            } else {

                                 bLineEnd=FALSE;

                            }

                        }

               }

              }

              ....

 

À̵¿ °¡´É Á¶°ÇÀÌ ÃÖÃÊ off °¡ ¹®¼­ ±æÀÌ ¾ÈÂÊÀÏ ¶§¿´´Âµ¥ ¿©±â¿¡ ÇϳªÀÇ Á¶°ÇÀÌ ´õ Ãß°¡µÇ¾î °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö ÀÖÀ¸¸é ¹®¼­ ³¡ÀÌ¶óµµ ´õ À̵¿ÇÑ´Ù. ¸ÕÀú ÁÙ ³¡¿¡ ´êÀº »óÅ¿¡¼­ ¿À¸¥ÂÊÀ¸·Î À̵¿ÇÒ ¶§ÀÎ ¾Æ·¡ Äڵ带 º¸ÀÚ. ¹®¼­ ³¡ÀÏ ¶§µµ ¹Ù·Î ¸®ÅÏÇÏÁö ¾ÊÀ¸¹Ç·Î ÁÙ ³¡ÀÎÁö¸¦ Á¡°ËÇÒ ¶§ AeIsLineEnd ¸ÅÅ©·Î¸¦ »ç¿ëÇØ¾ß ÇÑ´Ù. Áñ ³¡ÀÌ°í °¡»ó À§Ä¡·Î ¿òÁ÷ÀÏ ¼ö ÀÖ´Â »óŶó¸é ¿ÀÇÁ¼ÂÀº °Çµå¸®Áö ¾Ê°í ExtraX¸¸ 1Áõ°¡½ÃŲ´Ù. ¿ÀÇÁ¼ÂÀº ¿©ÀüÈ÷ ÁÙ ³¡À» °¡¸®Å°°í Àִµ¥ ¿ÀÇÁ¼ÂÀº ½ÇÁ¦ ÆíÁý ´ë»ó ÄÚµåÀ̹ǷΠÀý´ë·Î ¹®¼­¹ÛÀ¸·Î ¹þ¾î³ªÁö ¾Ê°Ô °ü¸®ÇØ¾ß ÇÑ´Ù.  À§ÂÊÀÇ ÄÚµå´Â ExtraX°¡ 0º¸´Ù ´õ Ŭ ¶§, Áï ÀÌ¹Ì °¡»ó À§Ä¡¹ÛÀ¸·Î ³ª°¡ ÀÖ´Â »óÅ¿¡¼­ ¿À¸¥ÂÊÀ¸·Î À̵¿ÇÒ ¶§Àε¥ À̶§´Â off´Â °Çµå¸± ÇÊ¿ä¾øÀÌ ExtraX¸¸ Áõ°¡½ÃŰ¸é µÈ´Ù.

VK_RIGHTÀÇ ÄÚµå´Â ÁÙ ³¡¿¡¼­ ÃÖÃÊ ¿À¸¥ÂÊÀ¸·Î ÇÑÄ­ À̵¿ÇÒ¶§ ExtraX°¡ 1ÀÌ µÇ¸ç ÀÌÈĺÎÅÍ´Â ExtraX¸¸ °è¼Ó Áõ°¡ÇÔÀ¸·Î½á ij·µÀ» ÁÙ ³¡À¸·Î °è¼Ó À̵¿½ÃŰ´Â °ÍÀÌ´Ù. ´ÙÀ½Àº ¿ÞÂÊÀ¸·Î À̵¿ÇÏ´Â VK_LEFTÀÇ Äڵ带 ¼öÁ¤ÇØ º¸ÀÚ.

 

     case VK_LEFT:

          if (off > 0) {

              GetRCFromOff(off,r,c);

 

              OldOff=off;

              if (bControl) {

                   off=GetPrevWord(off);

              } else {

               if (ExtraX > 0) {

                   ExtraX--;

               } else {

                        if (off==pLine[r].Start) {

                            if (pFrame->IsEnterCode(pFrame->GetPrevOff(off)) ||

                                 pFrame->bUseLineEnd==FALSE) {

                                 off=pFrame->GetPrevOff(off);

                                 bLineEnd=FALSE;

                            } else {

                                 bLineEnd=TRUE;

                            }

                        } else {

                            off=pFrame->GetPrevOff(off);

                            bLineEnd=FALSE;

                        }

               }

              }

              ....

 

VK_LEFTÀÏ ¶§´Â ÀÌ¹Ì °¡»ó À§Ä¡·Î ³ª°¡ ÀÖÀ» ¶§¸¸ ó¸®ÇÏ¸é µÈ´Ù. ExtraX°¡ 0º¸´Ù Å« »óÅ¿¡¼­ ÇÑÄ­ ¿ÞÂÊÀ¸·Î À̵¿Çϸé ExtraX¸¸ 1 °¨¼Ò½ÃŲ´Ù. off´Â °è¼Ó ÁÙ³¡¿¡ ÀÖÀ¸¸ç ExtraX°¡ 0ÀÌ µÇ±â Àü¿¡´Â Àý´ë·Î º¯°æµÇÁö ¾Ê´Â´Ù. ExtraX°¡ 0ÀÌ µÇ¾î ¹®ÀÚ°¡ ÀÖ´Â °÷À¸·Î µé¾î¿À¸é ±×¶§ºÎÅÍ´Â ÀϹÝÀûÀΠij·µ À̵¿ ¹æ¹ý°ú µ¿ÀÏÇÏ°Ô µ¿ÀÛÇÑ´Ù. °¡»ó À§Ä¡ÀÇ °³³äÀÌ ¸¸µé¾îÁüÀ¸·Î½á ij·µÀÇ À§Ä¡¿Í Çà·Ä, È­¸é ÁÂÇ¥¸¦ °è»êÇÏ´Â ¸ðµç À¯Æ¿¸®Æ¼ ÇÔ¼ö°¡ °¡»ó À§Ä¡¸¦ °è»ê¿¡ Æ÷ÇÔÇϵµ·Ï ¼öÁ¤µÇ¾î¾ß ÇÑ´Ù.

 

void CApiEditText::GetRCFromOff(int nPos, int &r, int &c)

{

     ....

     c=nPos-pLine[r].Start;

    if (ExtraX > 0) {

        c+=ExtraX;

    }

}

 

int CApiEditText::GetOffFromRC(int r, int c)

{

     int len;

 

     assert(r >= 0 && r <= TotalLine-1);

     len=pLine[r].End-pLine[r].Start;

     if (IsVirtualPosable()) {

          ExtraX=max(c-len,0);

     } else {

          ExtraX=0;

     }

     return pLine[r].Start+min(c,len);

}

 

Çà¿­À» ±¸ÇÒ ¶§ °¡»ó À§Ä¡¿¡ ÀÖÀ» °æ¿ì ¿­¹øÈ£¿¡ ExtraX¸¦ ´õÇØ¾ß ÇÑ´Ù. offÀÇ ¿­ µÚÂÊÀ¸·Î ExtraX¸¸Å­ ´õ ¿À¸¥ÂÊ ¿­À» °¡¸®Å°°í ÀÖ´Ù´Â ¶æÀÌ´Ù. ¹°·Ð ÀÌ ¿­¿¡´Â ½ÇÁ¦·Î ¹®ÀÚ°¡ Á¸ÀçÇÏÁö´Â ¾ÊÁö¸¸ °ø¹éÀÌ ExtraX°³¼ö¸¸Å­ ÀÖ´Ù°í °¡Á¤ÇÏ´Â °ÍÀÌ´Ù.

Çà¿­·ÎºÎÅÍ ¿ÀÇÁ¼ÂÀ» ±¸ÇÒ ¶§´Â ¿­ÀÌ ÇöÀçÇàÀÇ ³¡º¸´Ù ´õ µÚÂÊ¿¡ ÀÖÀ¸¸é ExtraX¿¡ ÃʰúµÈ ¿­¹øÈ£¸¦ ´ëÀÔÇÑ´Ù. ¿¹¸¦ µé¾î ÁÙÀÇ ±æÀ̰¡ 10¿­Àε¥ c°¡ 15¿­À» °¡¸®Å°°í ÀÖ´Ù¸é off´Â 10¿­ÀÇ À§Ä¡¸¦ °¡¸®Å°°í ExtaX´Â 15-10ÀÎ 5ÀÇ °ªÀ» °¡Áø´Ù. ´Ü, ¿­ÀÌ ÇàÀÇ ¹üÀ§ ³»¿¡ ÀÖÀ» ¶§´Â ExtraX°¡ À½¼ö°¡ µÇÁö ¾Ê¾Æ¾ß ÇÑ´Ù. ExtraX´Â Ç×»ó 0º¸´Ù Ä¿¾ß ÇÑ´Ù. °¡»ó À§Ä¡·ÎÀÇ À̵¿ÀÌ Çã°¡µÇÁö ¾Ê´Â »óȲÀ̸é ExtraX¸¦ ¹«Á¶°Ç 0À¸·Î ¸¸µç´Ù. off´Â Ç×»ó ÁÙ ³»ÀÇ ½ÇÁ¦ ¿ÀÇÁ¼ÂÀ» °¡¸®ÄÑ¾ß ÇϹǷΠ±âÁ¸ ¹æ½Ä´ë·Î °è»êÇÏ¸é µÈ´Ù.

¿ÀÇÁ¼ÂÀ¸·ÎºÎÅÍ È­¸é À§Ä¡¸¦ °è»êÇÏ´Â ÇÔ¼öµéµµ ´ÙÀ½°ú °°ÀÌ ¼öÁ¤µÈ´Ù. Çà·ÄÀÇ °æ¿ì¿Í ¸¶Âù°¡Áö·Î ¿ÀÇÁ¼ÂÀÌ ÁÙ ³¡ÀÎ °æ¿ì´Â ExtraX¸¦ °è»ê¿¡ Æ÷ÇÔ½ÃÄÑ¾ß Çϸç ÁöÁ¤ÇÑ ÁÂÇ¥Àü¿¡ ÁÙ ³¡À» ¸¸³­ °æ¿ì´Â ExtraX¿¡ ÃʰúºÐÀ» °è»êÇÑ´Ù.

 

void CApiEditText::GetXYFromOff(int nPos, int &x, int &y)

{

     ....

    if (ExtraX > 0) {

        x += arChWidth[' ']*ExtraX;

    }

}

 

int CApiEditText::GetXPosOnLine(int r,int DestX)

{

     TCHAR *p;

     int len, acwidth;

 

     assert(r >= 0 && r <= TotalLine-1);

     if (DestX == MarginWidth) {

          return pLine[r].Start;

     }

     for (p=pFrame->buf+pLine[r].Start, acwidth=MarginWidth;;) {

          if (p-pFrame->buf == pLine[r].End) {

           if (IsVirtualPosable()) {

               ExtraX=(DestX-acwidth)/arChWidth[' '];

           }

              break;

        }

          ....

          if (acwidth >= DestX) {

           ExtraX=0;

              break;

          }

     }

     ....

 

int CApiEditText::GetOffFromXY(int x, int y)

{

     ....

     for (p=pFrame->buf+pLine[r].Start,acwidth=MarginWidth;;) {

          if (p-pFrame->buf == pLine[r].End) {

           if (IsVirtualPosable()) {

               ExtraX=(x-acwidth)/arChWidth[' '];

           } else {

               ExtraX=0;

           }

              break;

          }

          ....

          acwidth += chWidth;

          if (acwidth-chWidth/2 >= x) {

           ExtraX=0;

              break;

          }

 

GetXYFromOff ÇÔ¼ö´Â ExtraX°¡ 0º¸´Ù Ŭ °æ¿ì xÁÂÇ¥¿¡ ExtraX*°ø¹éÆøÀ» ´õÇÑ´Ù. ij·µÀÌ °¡»ó À§Ä¡¿¡ ÀÖÀ» ¶§ ExtraX¸¸Å­ ´õ ¿À¸¥ÂÊ ÁÂÇ¥°¡ °è»êµÉ °ÍÀÌ´Ù. ³ª¸ÓÁö µÎ ÇÔ¼öµµ ºñ½ÁÇÏ´Ù. ¸ñÇ¥ ¿ÀÇÁ¼ÂÀ» ã±â Àü¿¡ ÁÙ ³¡À» ¸¸³µÀ¸¸é ³²Àº Çȼ¿¼ö¸¦ °ø¹éÆøÀ¸·Î ³ª´«¸¸Å­ ExtraX¸¦ Á¤ÀÇÇÔÀ¸·Î½á ¸ñÇ¥ ¿ÀÇÁ¼Âº¸´Ù ´õ ¿À¸¥ÂÊÀ» ã´Â´Ù. ¹°·Ð ÁÙ ³»¿¡ ¸ñÇ¥ ¿ÀÇÁ¼ÂÀÌ ¹ß°ßµÇ¾úÀ¸¸é ExtraX´Â 0ÀÌ´Ù. ¿¹¸¦ µé¾î DestX°¡ 600Àε¥ 500Çȼ¿ À§Ä¡¿¡¼­ ÁÙ ³¡À» ¸¸³µ´Ù¸é ExtraX´Â ³²Àº 100Çȼ¿À» °ø¹éÆøÀ¸·Î ³ª´©¾î ´ëÀԹ޴´Ù.

GetOffFromXY´Â ÁÙ³¡À» ¸¸³µÀ» ¶§ °¡»ó À§Ä¡ ±ÝÁö »óÅÂÀÌ¸é °­Á¦·Î ExtraX¸¦ 0À¸·Î ¸¸µå´Â else¹®ÀÌ ÇÊ¿äÇÏ´Ù. ¸¶¿ì½º·Î ¼±ÅÃÁß¿¡ °¡»ó À§Ä¡¿¡¼­ ¼±ÅÃÀ» ½ÃÀÛÇß´õ¶óµµ ½ÇÁ¦ ¿ÀÇÁ¼ÂÀ» ±¸ÇØ¾ß Çϱ⠶§¹®ÀÌ´Ù. ±×·¯³ª GetXPosOnLineÀº Űº¸µå¿¡ ÀÇÇØ¼­¸¸ È£ÃâµÇ¹Ç·Î ÀÌ else¹®Àº ÇÊ¿äÇÏÁö ¾Ê´Ù. GetXPosOnLine ÇÔ¼ö°¡ ExtraX¸¦ °è»ê¿¡ Æ÷ÇÔ½Ã۱⠶§¹®¿¡ »óÇÏ À̵¿, PgUp, PgDn µîÀÇ À̵¿ ÇÔ¼öµéÀº ¼öÁ¤ÇÏÁö ¾Ê¾Æµµ µÈ´Ù.

¿©±â±îÁö ÀÛ¼ºÇÑ ÈÄ ½ÇÇàÇØ º¸¸é ÁÙÀÇ ¿À¸¥ÂÊ ³¡À» Áö³ª ij·µÀÌ À̵¿ÇÒ ¼ö ÀÖÀ» °ÍÀÌ´Ù. SetCaretÀº ÀÌ ÇÔ¼öµé·ÎºÎÅÍ ±¸ÇØÁö´Â Á¤º¸·ÎºÎÅÍ Ä³·µÀÇ À§Ä¡¸¦ °è»êÇϹǷΠ¼öÁ¤ÇÏÁö ¾Ê¾Æµµ Àß µ¿ÀÛÇÑ´Ù. ¸¶¿ì½º·Îµµ °¡»ó À§Ä¡ À̵¿ÀÌ °¡´ÉÇѵ¥ À¯Æ¿¸®Æ¼ ÇÔ¼öµéÀÌ °¡»ó À§Ä¡¸¦ Àß °ü¸®Çϰí Àֱ⠶§¹®ÀÌ´Ù. ±×·¯³ª ¾ÆÁ÷±îÁö ´õ ¸¹Àº ºÎºÐÀ» ¼Õ ºÁ¾ß ÇÑ´Ù.

¿¹¸¦ µé¾î ¼öÆò ½ºÅ©·Ñ ¹üÀ§¸¦ ¹þ¾î³­ °¡»ó À§Ä¡·Î À̵¿ÇÒ °æ¿ì ±×´ë·Î ³»¹ö·Á µÎ¸é ¹üÀ§¸¦ ³Ñ¾î¼­±îÁö ½ºÅ©·Ñ µÉ °ÍÀÌ´Ù. ¶ÇÇÑ ÀÚµ¿ °³Çà »óÅ¿¡¼­ Æ÷¸ËÆÃ ¿µ¿ª ¿À¸¥ÂÊÀ¸·Î À̵¿ÇÒ ¶§´Â ij·µÀÌ ½ºÅ©·Ñ ºÒ°¡´ÉÇÑ ¿µ¿ªÀ¸·Î ¼û¾î ¹ö¸± ¼öµµ ÀÖ´Ù. ÀÌ ¹®Á¦ÀÇ ÇØ°á ¹æ¹ýÀº ¿©·¯ °¡Áö°¡ ÀÖ°ÚÁö¸¸ ÀÏ´Ü ´ÙÀ½ µÎ °¡Áö¸¦ »ý°¢ÇÒ ¼ö ÀÖ´Ù.

 

¹æ¹ý1:°¡»ó ¿µ¿ªÀ¸·Î À̵¿ÇÏ´õ¶óµµ ½ºÅ©·Ñ ¹üÀ§¸¦ ³Ñ¾î¼³ ¶§´Â °¡Áö ¸øÇÏ°Ô ±ÝÁöÇÏ°í Æ÷¸ËÆÃ ¿µ¿ª Å©±â°¡ ¹Ù²ð ¶§ ExtraX¸¦ ¹«Á¶°Ç 0À¸·Î ¸¸µé¾î ÁÙ ³¡À¸·Î ij·µÀ» º¸³½´Ù.

¹æ¹ý2:½ºÅ©·Ñ ¹üÀ§¸¦ ¹þ¾î³ª°Å³ª Æ÷¸ËÆÃ ¿µ¿ª ¹Ù±ùÀ¸·Î À̵¿ÇÒ ¶§´Â ´ÙÀ½ ÇàÀÇ Ã³À½À¸·Î º¸³½´Ù. ¸¶Áö¸· ÇàÀÏ ¶§´Â ¾î¿ ¼ö ¾øÀÌ À̵¿ ±ÝÁö½ÃÄÑ¾ß ÇÑ´Ù.

 

µÑ Áß Çϳª¸¦ ¼±ÅÃÇØ¾ß ÇÑ´Ù¸é ¹æ¹ý2°¡ ´õ ÁÁÀº ÇØ°áÃ¥ÀÌ´Ù. ±×·¯³ª ApiEdit´Â ÀÌ ¹®Á¦¿¡ ´ëÇØ¼­´Â ¾Æ¹«·± 󸮵µ ÇÏÁö ¾Ê±â·Î ÇÑ´Ù. Áï, ij·µÀÌ ¾Èº¸ÀÌ´Â »óŰ¡ µÇ´õ¶óµµ ±×´ë·Î ¹æÄ¡ÇÑ´Ù. ÀÌ ¹®Á¦´Â ¿Àµ¿ÀÛÇÒ Á¤µµÀÇ Å« ¹®Á¦´Â ¾Æ´Ñµ¥´Ù »ç¿ëÀÚ°¡ ¿Ö ij·µÀÌ ¾Èº¸ÀÌ´Â »óȲÀÌ µÇ¾ú´ÂÁö¸¦ ¸íÈ®ÇÏ°Ô ¾Ë ¼ö ÀÖÀ¸¹Ç·Î Å« ¹®Á¦°¡ µÇÁö ¾Ê´Â´Ù. ¼²ºÒ¸® ÀÌ·± ¹®Á¦¸¦ ÇØ°áÇÏ·Á°í Çϸé ÇÁ·Î±×·¥ÀÇ º¹Àâµµ°¡ Áõ°¡ÇÏ¸ç ±×´ë·Î µÎ´Â °ÍÀÌ ´õ ÀÚ¿¬½º·´´Ù.

³ª.°¡»ó À§Ä¡¿¡ ÀÔ·Â

°¡»ó À§Ä¡·Î ij·µÀ» ¿Å±â´Â ÀÌÀ¯´Â ¹®ÀÚ°¡ ¾ø´Â ºó °ø°£¿¡µµ ¹®ÀÚ¸¦ ÀÔ·ÂÇϱâ À§Çؼ­ÀÌ´Ù. ±×·¡¼­ °¡»ó À§Ä¡¿¡¼­ ¹®ÀÚ¿­À» ÀÔ·ÂÇϸé ÃʰúºÐ¸¸Å­ °ø¹éÀ» Áï½Ã »ðÀÔÇØ¾ß ÇÑ´Ù. ±×·¡¾ß °¡»ó À§Ä¡·Î À̵¿ÇÑ Àǹ̰¡ ÀÖ´Ù. ¹®ÀÚ¸¦ ÀÔ·ÂÇÏÁöµµ ¸øÇÑ´Ù¸é ¿Ö °¡»ó À§Ä¡·Î ij·µÀ» ¿Å±â·Á°í Çϰڴ°¡? ´ÙÀ½ ÇÔ¼ö´Â ÇöÀç offÀ§Ä¡¿¡ ExtraX¸¸Å­ °ø¹éÀ» ¸ÕÀú »ðÀÔÇϰí off¸¦ °ø¹é ´ÙÀ½À¸·Î À̵¿½ÃŲ´Ù. ÇöÀç ij·µÀÌ ÀÖ´Â ºÎºÐ±îÁö °ø¹éÀ» ÀÔ·ÂÇÏ¿© °¡»ó À§Ä¡¸¦ ½ÇÁ¦ À§Ä¡·Î ¹Ù²Ù´Â °ÍÀÌ´Ù. °¡»ó °ø¹éÀ» Àû¿ëÇÑ ÈÄ ExtraX´Â 0ÀÌ µÇ¾î¾ß ÇÑ´Ù.

 

BOOL CApiEditText::InputExtraSpace(int &nPos)

{

     TCHAR *pExSpace;

 

     if (ExtraX > 0) {

          pExSpace=(TCHAR *)malloc(ExtraX+1);

          memset(pExSpace,' ',ExtraX);

          pExSpace[ExtraX]=0;

          Insert(nPos,pExSpace,ExtraX);

          nPos+=ExtraX;

          free(pExSpace);

          ExtraX=0;

          return TRUE;

     }

     return FALSE;

}

 

ExtraX°¡ 0º¸´Ù Ŭ °æ¿ì´Â °¡»ó À§Ä¡¿¡ ¿Í ÀÖ´Ù´Â ¶æÀÌ´Ù. À̶§ ExtraX ±æÀ̸¸Å­ °ø¹é ¹®ÀÚ¿­À» ÀÛ¼ºÇϰí Insert ÇÔ¼ö·Î °ø¹é ¹®ÀÚ¿­À» »ðÀÔÇÑ´Ù. ±×¸®°í nPos´Â °ø¹é ¹®ÀÚ¿­ÀÇ ³¡ ºÎºÐÀ¸·Î ¿Å±â¸ç °¡»ó °ø¹éÀÌ »ðÀԵǾúÀ¸¹Ç·Î ExtraX´Â 0À¸·Î ¸¸µç´Ù. ¸®ÅϰªÀ¸·Î´Â °¡»ó °ø¹éÀ» »ðÀÔÇß´ÂÁöÀÇ ¿©ºÎ¸¦ µ¹·ÁÁØ´Ù. ÀÌ ÇÔ¼ö¸¦ È£ÃâÇØ¾ß ÇÒ °÷Àº ¸ðµÎ 4±ºµ¥ÀÌ´Ù.

 

void CApiEditText::OnChar(HWND hWnd, TCHAR ch, int cRepeat)

{

     ....

    InputExtraSpace(off);

 

     if (SelStart != SelEnd) {

          pFrame->StartUndoGroup("¼±Åà ´ëü");

     }

     ....

 

LRESULT CApiEditText::OnImeComposition(HWND hWnd, WPARAM wParam, LPARAM lParam)

{

     if (pFrame->bReadOnly || bCapture)

          return 0;

 

    InputExtraSpace(off);

     ....

 

ÀÌ µÎ ±ºµ¥´Â »ç¿ëÀÚ°¡ Á÷Á¢ ¹®ÀÚ¿­À» ÀÔ·ÂÇÒ ¶§À̹ǷΠ°¡»ó °ø¹éÀ» ó¸®ÇØ¾ß ÇÑ´Ù. InputExtraSpace ÇÔ¼ö³»¿¡¼­ ExtraX¸¦ Á¡°ËÇϰí ÀÖÀ¸¹Ç·Î ¹«Á¶°Ç È£ÃâÇϱ⸸ ÇÏ¸é µÈ´Ù. ÀÌ ¿Ü¿¡ ºÙ¿© ³Ö±â, ¹®ÀÚ¿­ »ðÀÔ µî¿¡µµ °¡»ó °ø¹é 󸮰¡ ÇÊ¿äÇÏ´Ù.

 

void CApiEditText::OnCommand(HWND hWnd, int id, HWND hwndCtl, UINT codeNotify)

{

     switch (id) {

     case IDM_AE_PASTE:

          BOOL bPrevSel;

          TCHAR *dest;

          int Format;

          if (IsClipboardFormatAvailable(CF_TEXT) && pFrame->bReadOnly==FALSE &&

               bCapture==FALSE) {

           InputExtraSpace(off);

              ....

 

void CApiEditText::InsertText(TCHAR *Text)

{

     if (pFrame->bReadOnly) {

          return;

     }

 

    InputExtraSpace(off);

 

CopyString ÇÔ¼ö¿¡¼­µµ °¡»ó °ø¹éÀ» »ðÀÔÇØ¾ß Çϴµ¥ off À§Ä¡°¡ ¾Æ´Ñ µå·ÓµÈ À§Ä¡¿¡ »ðÀÔµÇ¸ç ¶ÇÇÑ »ðÀÔ ÈÄ ¿øº» ¹®ÀÚ¿­ÀÇ ¿ÀÇÁ¼Âµµ º¯°æÇØ¾ß ÇÑ´Ù. InputExtraSpace È£Ãâ Àü¿¡ ExtraX¸¦ ¹é¾÷ÇØ ³õ°í to¸¦ ¸ÕÀú Á¶Á¤ÇÑ ÈÄ fromÀ» Á¶Á¤ÇÑ´Ù.

 

void CApiEditText::CopyString(BOOL bCopy, int from, int &to, int len, BOOL bRec/*=TRUE*/)

{

     TCHAR *t;

     int orito=to;

    int BkExtraX;

 

    BkExtraX=ExtraX;

    if (InputExtraSpace(to)) {

        if (from > to-BkExtraX) {

           from+=BkExtraX;

        }

    }

 

     t=(TCHAR *)malloc(len);

 

¹®ÀÚ°¡ ÀԷµDZâ Á÷Àü¿¡ Ç×»ó °¡»ó °ø¹éÀ» ¸ÕÀú »ðÀÔÇßÀ¸¹Ç·Î ij·µÀÌ ¾îµð¿¡ ÀÖµçÁö ij·µÀÌ ÀÖ´Â À§Ä¡¿¡ ¹®ÀÚ°¡ Á¤È®ÇÏ°Ô ÀÔ·ÂµÉ °ÍÀÌ´Ù. ¹®ÀÚ¸¦ »ðÀÔÇÏ´Â ¸ðµç ·çƾÀº Insert¸¦ È£ÃâÇϹǷΠInsert ÇÔ¼ö¿¡¼­ ExtraX¸¦ Á¡°ËÇÏ¿© ¿©±â¼­ °¡»ó °ø¹éÀ» »ðÀÔÇϴ ó¸®¸¦ ÇÒ ¼öµµ ÀÖÀ» °Í °°´Ù. ±×·¯³ª À̰ÍÀº ºÒ°¡´ÉÇÏ´Ù. ¿Ö³ÄÇϸé Insert¸¦ È£ÃâÇÑ °÷¿¡¼­´Â ÀÔ·ÂµÈ ¹®ÀÚ¿­¸¸Å­¸¸ ¿ÀÇÁ¼ÂÀ» À̵¿½Ã۴µ¥ Insert°¡ Àμö·Î Àü´ÞµÈ strº¸´Ù ´õ ±ä ¹®ÀÚ¿­À» »ðÀÔÇØ ¹ö¸®¸é È£Ãâ¿ø¿¡¼­ ¿ÀÇÁ¼Â ¹× ij·µ °»½ÅÀ» Á¤È®ÇÏ°Ô ¼öÇàÇÒ ¼ö ¾ø±â ¶§¹®ÀÌ´Ù.

²À ±×·¸°Ô ÇÏ·Á¸é Insert°¡ °¡»ó °ø¹éÀ» Æ÷ÇÔÇØ¼­ ½ÇÁ¦·Î »ðÀÔÇÑ ¹ÙÀÌÆ® ¼ö¸¦ ¸®ÅÏÇØ¾ß Çϸç Insert¸¦ È£ÃâÇÏ´Â ¸ðµç ·çƾ¿¡¼­´Â Insert°¡ ½ÇÁ¦·Î ¸î ¹ÙÀÌÆ®³ª »ðÀÔÇß´ÂÁö¸¦ ÀÏÀÏÀÌ Á¡°ËÇÏ¿© ¿ÀÇÁ¼ÂÀ» °ü¸®ÇØ¾ß ÇÑ´Ù. °¡»ó °ø¹é 󸮸¦ ÇÑ °÷¿¡ ÁýÁßÇÑ´Ù´Â Á¡¿¡¼­´Â ´õ ÁÁÀ»Áö ¸ô¶óµµ ÄÚµå´Â ÈξÀ ´õ º¹ÀâÇØÁö°í Áö±Ý±îÁö ¸¸µç ±¸Á¶¿Íµµ ¸ÂÁö ¾Ê´Ù.

´Ù.ÀϽÃÀûÀÎ ±ÝÁö

bVirtualPos ¿É¼ÇÀÌ ÄÑÁ® ÀÖ´õ¶óµµ ÀÌ ¿É¼ÇÀÇ ¿µÇâÀ» ¹Þ¾Æ¼­´Â ¾ÈµÇ´Â ±â´ÉµéÀÌ ÀÖ´Ù. ¿¹¸¦ µé¾î EndŰ´Â ÇàÀÇ ³¡À» ãÀ» ¶§ ¹é¸¸¹øÂ° ¿­·Î À̵¿Çϴµ¥ ¿¹Àü¿¡´Â GetOffFromRC°¡ ÃæºÐÈ÷ Å« ¿­¹øÈ£¸¦ ÁÖ¸é ¾Ë¾Æ¼­ ÇàÀÇ ³¡¿­À» ã¾Æ ¹é¸¸¹øÂ° ¿­ÀÌ Çà ³¡ÀÌ µÇ¾úÁö¸¸ Áö±ÝÀº ±×·¸Áö ¾Ê´Ù. Áö±ÝÀº °¡»ó À§Ä¡·Î À̵¿ÇÒ ¼ö ÀÖÀ¸¹Ç·Î GetOffFromRC°¡ ÁøÂ¥ ¹é¸¸¹øÂ° ¿­ÀÇ À§Ä¡¸¦ ÂüÁ¶Çϵµ·Ï ExtraX¿¡ ÃʰúºÐÀ» ´ëÀÔÇØ ¹ö¸®±â ¶§¹®ÀÌ´Ù.

ÀÌ·¸°Ô µÇ¸é ij·µÀº ½ºÅ©·Ñ ¹üÀ§¸¦ ÈξÀ Áö³ªÃÄ µµÀúÈ÷ »ó»óÀÌ ¾ÈµÇ´Â À§Ä¡·Î °¡ ¹ö¸®°Ô µÉ °ÍÀÌ´Ù. À̰ÍÀº ¿ì¸®°¡ ¿øÇÏ´Â ¹Ù°¡ ¾Æ´Ï¸ç ÀÌ´ë·Î µÎ¾î¼­´Â ¾ÈµÈ´Ù. ¼³»ç °¡»ó À§Ä¡·Î À̵¿ ¿É¼ÇÀÌ ÄÑÁ® ÀÖ´õ¶óµµ À̶§¸¸Å­Àº ÀϽÃÀûÀ¸·Î GetOffFromRC°¡ Àá½Ã °¡»ó À§Ä¡ ¼³Á¤À» ¹«½ÃÇØ¾ß ÇÑ´Ù. VK_ENDÀÇ Äڵ带 ´ÙÀ½°ú °°ÀÌ ¼öÁ¤ÇÏÀÚ.

 

     case VK_END:

          ....

           ignoreVirt++;

              off=GetOffFromRC(r,1000000);

           ignoreVirt--;

          ....

 

IsVirtualPossable ÇÔ¼ö´Â ºñ·Ï bVirtualPos°¡ TRUEÀÌ´õ¶óµµ ignoreVirt°¡ 0 ÀÌ»óÀÇ °ªÀ» °¡Áö¸é FALSE¸¦ ¸®ÅÏÇϹǷΠÀÌ °ªÀ» Áõ°¡½ÃŲ ÈÄ GetOffFromRC¸¦ È£ÃâÇϸé Àá½Ã °¡»ó À§Ä¡¸¦ ¹«½ÃÇÒ ¼ö ÀÖ´Ù. ÀÌ »óÅ¿¡¼­ ¹é¸¸¹øÂ° ¿­À» ãÀ¸¸é ÇàÀÇ ³¡À» ãÀ» °ÍÀÌ´Ù. ¹°·Ð 󸮰¡ ³¡³­ ÈÄ´Â ´Ù¸¥ Äڵ忡¼­ °¡»ó À§Ä¡ ¿É¼ÇÀ» Á¦´ë·Î ÀνÄÇϵµ·Ï ignoreVirt¸¦ 1 °¨¼Ò½ÃÄÑ¾ß ÇÑ´Ù. ignorVirt´Â ÁßøÀÌ °¡´ÉÇϹǷΠBOOLÇüÀ¸·Î ¾µ ¼ö ¾øÀ¸¸ç Á¤¼öÇüÀÇ Ä«¿îÆ®¸¦ ½á¾ß ÇÑ´Ù.

°¡»ó À§Ä¡·ÎÀÇ À̵¿À» ÀϽÃÀûÀ¸·Î ±ÝÁöÇØ¾ß ÇÏ´Â ¶Ç ´Ù¸¥ °æ¿ì´Â ¸¶¿ì½º·Î ºí·ÏÀ» ¼±ÅÃÇÒ ¶§ÀÌ´Ù. °¡»ó À§Ä¡´Â ¾îµð±îÁö³ª ¹®ÀÚ¸¦ ÀÔ·ÂÇÒ ¼ö ÀÖ´Â À§Ä¡ÀÏ »ÓÀÌÁö ¿©±â¿¡´Â ½ÇÁ¦ ¹®ÀÚ°¡ ¾øÀ¸¹Ç·Î ¼±ÅÃÇÒ ¼ö ¾ø´Ù. ¸¶¿ì½º·Î ¼±Åà ºí·ÏÀ» È®ÀåÇϴ ó¸®´Â OnMouseMove¿¡¼­ ÇϹǷΠÀÌ ÇÔ¼ö¸¦ ¼öÁ¤ÇÑ´Ù.

 

void CApiEditText::OnMouseMove(HWND hWnd, int x, int y, UINT keyFlags)

     if (bDragSel) {

          ....

     } else {

          OldOff=off;

          if (bSelLine) {

              ....

          } else {

              // ¼±Åà Áß¿¡´Â °¡»ó À§Ä¡·Î ¹þ¾î³¯ ¼ö ¾øÀ½. ´Ü, Ä÷³ ¸ðµåÀÏ ¶§´Â ¿¹¿Ü

           ignoreVirt++;

              off=SelEnd=GetOffFromXY(x+xPos,y+yPos);

           ignoreVirt--;

          }

 

¼±ÅÃÀÇ ³¡ÀÎ SelEnd ¸¦ °è»êÇϱâ Àü¿¡ ignoreVirt¸¦ Áõ°¡½ÃÄÑ ¼±Åà ³¡Á¡ÀÌ °¡»ó À§Ä¡°¡ ¾Æ´Ïµµ·Ï Á¶Á¤ÇÑ´Ù. ÀÌ·¸°Ô ÇÏ¸é ¼±Åà ³¡Á¡Àº Ç×»ó ½ÇÁ¦ À§Ä¡¸¸À» °¡¸®Å²´Ù. Űº¸µå·Î ¼±ÅÃÇÒ ¶§µµ ¸¶Âù°¡ÁöÀÌ´Ù. À̵¿Àº ¸¶À½´ë·Î ÇÒ ¼ö ÀÖÁö¸¸ ShiftŰ¿Í ÇÔ²¾ À̵¿ÇÒ ¶§´Â ¼±ÅÃÀ» ÇÏ´Â °ÍÀ̹ǷΠÀ̶§µµ °¡»ó À§Ä¡·ÎÀÇ À̵¿À» ÀϽÃÀûÀ¸·Î ±ÝÁö½ÃÄÑ¾ß ÇÑ´Ù.

 

void CApiEditText::OnKey(HWND hWnd, UINT vk, BOOL fDown, int cRepeat, UINT flags)

{

     ....

     if (fDown==FALSE)

          return;

 

    if (bShift) {

        ignoreVirt++;

    }

     bFindSelect=FALSE;

     ....

     // switch¹®ÀÇ ¸ðµç return¹®Àº break·Î º¯°æÇÑ´Ù.

     ....

    if (bShift) {

        ignoreVirt--;

    }

}

 

°¢°¢ÀÇ Å° ·çƾ¿¡¼­ ÀÌ Ã³¸®¸¦ Çϱâ´Â Çö½ÇÀûÀ¸·Î ¾î·Á¿ì¹Ç·Î OnKey ÇÔ¼ö¿¡¼­ ÀϰýÀûÀ¸·Î ÀÌ ¿É¼ÇÀ» ÀϽà Á¤Áö½ÃŲ´Ù. Shift+À̵¿Å°´Â ¸ðµÎ ºí·° ¼±ÅÃÀ̹ǷΠbShiftÀÏ ¶§´Â ignoreVirt¸¦ 1Áõ°¡½ÃŲ ÈÄ Å° ÀÔ·ÂÀ» ó¸®Çϰí 󸮰¡ ³¡³­ ÈÄ ´Ù½Ã ¿ø·¡´ë·Î µ¹·Á ³õ´Â´Ù. OnKeyÀÇ switch¹®¿¡´Â °¢ Ű¿¡ ´ëÇÑ Ã³¸®¸¦ ¸¶Ä£ ÈÄ °ð¹Ù·Î ¸®ÅÏÇϴµ¥ ÀÌÁ¦ ÀÌ·¸°Ô ÇØ¼­´Â ¾ÈµÇ¸ç ignoreVirt¸¦ ¿ø·¡´ë·Î µ¹·Á ³õ±â À§ÇØ break·Î switch¹®À» Å»ÃâÇØ¾ß ÇÑ´Ù. OnKey ÇÔ¼öÀÇ ¸ðµç return¹®À» break·Î º¯°æÇÑ´Ù.

½¬ÇÁÆ®¸¦ ´©¸¥ »óÅ¿¡¼­ À̵¿ÇÒ ¶§´Â IsVirtualPosable()ÀÌ FALSE¸¦ ¸®ÅÏÇϹǷΠ¿À¸¥ÂÊ À̵¿½Ã ExtraX¸¦ 0ÀÌ»óÀ¸·Î ¸¸µéÁö ¾ÊÀ¸¸ç »óÇÏ À̵¿½Ã GetXPosOnLineÀÌ ¸¶Âù°¡Áö·Î ExtraX¸¦ 0À¸·Î ¸¸µéÁö ¾Ê´Â´Ù. µû¶ó¼­ °¡»ó À§Ä¡·Î´Â ¼±ÅÃÀÌ È®ÀåµÇÁö ¾Ê´Â´Ù. ±×·¸´Ù¸é ÀÌ¹Ì °¡»ó À§Ä¡¿¡ ij·µÀÌ ³ª°¡ ÀÖ´Â »óÅ¿¡¼­ Shift+À̵¿Å°¸¦ ´©¸£¸é ¾î¶»°Ô µÇ°Ú´Â°¡? À̶§´Â ignoreVirt°¡ Á¡°ËµÇÁö ¾Ê±â ¶§¹®¿¡ ij·µÀÌ °¡»ó À§Ä¡¿¡ ±×´ë·Î ¸Ó¹«¸£°Ô µÈ´Ù. °¡»ó À§Ä¡¿¡¼­ ´Ü¾î À̵¿À» ÇÒ ¶§µµ µ¿ÀÏÇÑ ¹®Á¦°¡ ÀÖ´Ù. ±×·¡¼­ ´ÙÀ½ Äڵ尡 ÇÊ¿äÇÏ´Ù.

 

     case VK_LEFT:

          if (off > 0) {

              GetRCFromOff(off,r,c);

 

              OldOff=off;

              if (bControl) {

                   off=GetPrevWord(off);

               ExtraX=0;

              } else {

                   if (ExtraX > 0) {

                   if (IsVirtualPosable()) {

                            ExtraX--;

                   } else {

                       ExtraX=0;

                   }

          ....

     case VK_RIGHT:

          if (off < pFrame->doclen || IsVirtualPosable()) {

              GetRCFromOff(off,r,c);

 

              OldOff=off;

              if (bControl) {

                   off=GetNextWord(off);

               ExtraX=0;

              } else {

                   if (ExtraX > 0) {

                   if (IsVirtualPosable()) {

                            ExtraX++;

                   } else {

                       ExtraX=0;

                   }

 

ExtraX°¡ 0º¸´Ù Å« »óÅÂ, Áï ÀÌ¹Ì °¡»ó À§Ä¡·Î ij·µÀÌ ³ª¿Í ÀÖ´Â »óÅÂ¶óµµ °¡»ó À§Ä¡°¡ Çã¿ëµÇÁö ¾Ê´Â »óȲÀ̸é ExtraX¸¦ Áï½Ã 0À¸·Î ¸¸µç´Ù. ÀÌÁ¦ °¡»ó À§Ä¡¿¡¼­ Shift+Á¿ì À̵¿½Ã Áï½Ã À¯È¿ À§Ä¡·Î ÀÏ´Ü µ¹¾Æ¿Â´Ù. ¼±Åà Áß »óÇÏ À̵¿½Ã ExtraX°¡ À߸ø °è»êµÇ´Â ¹®Á¦°¡ Àִµ¥ ÀÏ´Ü Áõ¼¼ºÎÅÍ È®ÀÎÇØ º¸ÀÚ. ´ÙÀ½°ú °°ÀÌ ¼±ÅÃµÈ »óÅ¿¡¼­ ¾Æ·¡ÂÊÀÇ ºóÁٷΠij·µÀ» ÇÑÄ­ ³»·Á º¸ÀÚ.

aÁ¡À¸·Î ij·µÀÌ °¡¾ß Çϴµ¥ bÁ¡À¸·Î °£´Ù. ¿Ö ±×·¸°Ô µÇ´ÂÁö VK_DOWNÀÇ Äڵ带 Á» »ìÆì º¸ÀÚ. ÃÖÃÊ VK_DOWNÀÌ È£ÃâµÉ ¶§ PrevX´Â 80À̰í ExtraX´Â 0ÀÌ´Ù. 80À̶ó´Â °ªÀº "PrevX°¡" ¹®ÀÚ¿­ÀÇ ÆøÀε¥ ¹°·Ð ¼±ÅÃµÈ ±Û²Ã¿¡ µû¶ó ½ÇÁ¦°ªÀº ´Þ¶óÁú °ÍÀÌ´Ù. ÀÌ »óÅ¿¡¼­ VK_DOWNÀÌ È£ÃâµÇ¸é GetXPosOnLineÀÌ PrevX¿¡ ¸Â´Â ´ÙÀ½ ÁÙÀÇ ¿ÀÇÁ¼ÂÀ» ±¸Çϴµ¥ ºñ¾î ÀÖÀ¸¹Ç·Î ¿ÀÇÁ¼ÂÀº ÁÙÀÇ Ã³À½À» ãÀ» °ÍÀ̰í ExtraX´Â aÁ¡±îÁöÀÇ °ø¹é °³¼öÀÎ 13À» Á¶»çÇÑ´Ù. ÀÌ »óÅ´ë·Î ÇÑÄ­ ³»·Á¿À¸é ºÐ¸íÈ÷ aÁ¡À¸·Î À̵¿ÇÑ´Ù.

±×·±µ¥ ¹®Á¦´Â ¼±Åÿµ¿ªÀÌ ÀÖ´Â »óÅ¿¡¼­ ¾Æ·¡·Î À̵¿Àº ¼±ÅÃÀ» Ç®°Ô µÇ´Âµ¥ ÀÌ ¶§ SetCaretÀÌ È£ÃâµÇ¸ç SetCaretÀº ij·µ À§Ä¡ °è»êÀ» À§ÇØ GetXYFromOff¸¦ È£ÃâÇÑ´Ù. GetXYFromOff´Â ¼±Åà ³¡Á¡ÀÇ ÁÂÇ¥·Î 132¸¦ °è»êÇϴµ¥ ÀÌ °ªÀº PrevX+ExtraX*°ø¹éÆøÀÌ´Ù. ÀÌ °ªÀÌ ±×´ë·Î PrevX°¡ µÈ´Ù. VK_DOWNÀº ¼±ÅÃÀ» Ç®°í ÇÑÄ­ ´õ ³»·Á°¡±â À§ÇØ Çѹø ´õ È£ÃâµÇ´Âµ¥ À̶§ GetXPosOnLineÀº PrevX°ªÀ» ±×´ë·Î ¹Þ¾Æµé¿© bÁ¡À¸·Î À̵¿Çϵµ·Ï ExtraXÀÇ °ªÀ» ¼³Á¤ÇÑ´Ù. ±×·¯´Ù º¸´Ï ij·µÀÇ À§Ä¡°¡ Ʋ·ÁÁö´Â °ÍÀÌ´Ù. ´ÙÀ½°ú °°ÀÌ ¼öÁ¤ÇØ¾ß ÇÑ´Ù.

 

     case VK_UP:

              ....

          if (bShift) {

              ExpandSelection(OldOff,off);

          } else {

              if (SelStart != SelEnd) {

                   off=min(SelStart, SelEnd);

                   ClearSelection();

               SetCaret(!bVirtualPos);

                   SendMessage(hWnd,WM_KEYDOWN,VK_UP,(LPARAM)0);

              }

          }

          SetCaret(FALSE);

     case VK_DOWN:

          ....

          if (bShift) {

              ExpandSelection(OldOff,off);

          } else {

              if (SelStart != SelEnd) {

                   off=max(SelStart, SelEnd);

                   ClearSelection();

               SetCaret(!bVirtualPos);

                   SendMessage(hWnd,WM_KEYDOWN,VK_DOWN,(LPARAM)0);

              }

          }

          SetCaret(FALSE);

     }

 

°¡»ó À§Ä¡ Çã°¡ »óÅ¿¡¼­ ¼±ÅÃÀ» Ç® ¶§ÀÇ SetCaret È£Ãâ½Ã¿¡´Â PrevX¸¦ ¾÷µ¥ÀÌÆ®ÇÏÁö ¾Ê¾Ò´Ù. ±×¿ÜÀÇ °æ¿ì´Â ¼±Åà ³¡Á¡ ¹Ù·Î ¾Æ·¡·Î À̵¿Çϱâ À§ÇØ SetCaretÀÌ PrevX¸¦ °»½ÅÇØ¾ß ÇÑ´Ù. Áõ¼¼´Â »ç¼ÒÇÏÁö¸¸ ¿øÀÎÀº ¹«Ã´ º¹ÀâÇÑ ÆíÀÌ´Ù. ¼±Åà ¿µ¿ª¿¡ Ä¿¼­°¡ ÀÖ´ÂÁö Á¶»çÇÏ´Â ÇÔ¼öµµ ¼öÁ¤ÇÑ´Ù.

 

BOOL CApiEditText::IsInSelection(int x,int y)

{

    BOOL bRet;

    int BkExtraX;

     ....

     SelFirst=min(SelStart,SelEnd);

     SelSecond=max(SelStart,SelEnd);

 

    BkExtraX=ExtraX;

    ignoreVirt++;

     toff=GetOffFromXY(x,y);

     GetRCFromOff(toff,r,c);

 

     if (SelFirst > pLine[r].End || SelSecond <= pLine[r].Start) {

        bRet=FALSE;

        goto End;

     }

 

     ....

     SetRect(&rt,x1,y1,x2,y1+LineHeight);

     pt.x=x;

     pt.y=y;

    bRet=PtInRect(&rt,pt);

 

End:

    ignoreVirt--;

    ExtraX=BkExtraX;

    return bRet;

}

 

´Ü¼øÈ÷ Á¶»ç¸¸ Çϴµ¥´Ù°¡ ¼±Åà ¿µ¿ªÀº °¡»ó À§Ä¡¿¡ °ÉÄ¥ ¼ö ¾ø±â ¶§¹®¿¡ ExtraX¸¦ ÂüÁ¶ÇÒ Çʿ䵵 ¾ø°í º¯°æÇؼ­µµ ¾ÈµÈ´Ù. ±×´ë·Î µÎ¸é GetOffFromXY, GetRCFromOff ÇÔ¼ö°¡ ExtraX¸¦ ¸¶¿ì½º À§Ä¡¿¡ ¸Â°Ô º¯°æÇØ ¹ö¸°´Ù. ´ë°³ÀÇ °æ¿ì º° ¹®Á¦°¡ ¾øÁö¸¸ ¼±ÅÃÀÌ ÀÖ´Â »óÅ¿¡¼­ ´Ù¸¥ ÇÁ·Î±×·¥À¸·Î Æ÷Ä¿½º¸¦ À̵¿Çß´Ù°¡ ´Ù½Ã µ¹¾Æ¿À¸é ij·µÀ» ´Ù½Ã Ç¥½ÃÇÒ ¶§ ExtraXÀÇ ¿µÇâÀ» ¹Þ´Â´Ù. ¿ø·¡°ªÀ» ±×´ë·Î À¯ÁöÇϱâ À§ÇØ BkExtraX¿¡ Àá½Ã °ªÀ» ÀúÀåÇØ µÎ°í °è»êÀÌ ³¡³­ ÈÄ º¹±¸Çß´Ù.

ExtraX´Â ¹®¼­ÀÇ ÇöÀç »óÅÂÀ̹ǷΠÀÌ °ªÀº Ç×»ó Àß À¯ÁöÇØ¾ß ÇÑ´Ù. ÃÖ¼Ò, ÃÖ´ëÈ­, Æ÷Ä¿½º À̵¿, ÀçÁ¤·Ä µîÀÇ »óȲ¿¡µµ ExtraX´Â ¿ø·¡ °ªÀ» Àß À¯ÁöÇÏ¸ç º° ¹®Á¦°¡ ¾ø´Ù. ±×·¯³ª ÇѰ¡Áö ¿¹¿Ü »óȲÀÌ Àִµ¥ ÆíÁý Ãë¼Ò/Àç½ÇÇà½Ã¿¡´Â ExtraX¸¦ °­Á¦·Î 0À¸·Î ¸¸µé¾î¾ß ÇÑ´Ù. °¡»ó À§Ä¡¿¡¼­ ÆíÁýÀÌ ÀϾ´Â °æ¿ì´Â ¾ø±â ¶§¹®¿¡ ¹«Á¶°Ç ExtraX¸¦ 0À¸·Î ¸¸µé¾îµµ ¹«¹æÇÏ´Ù. ÆíÁýÀ» ÇÏ´Â Áï½Ã °ø¹éÀ¸·Î ä¿ö ¹ö¸®¹Ç·Î ±× ÀÚ¸®´Â ´õ ÀÌ»ó °¡»ó À§Ä¡°¡ ¾Æ´Ï´Ù.

 

void CApiEdit::Undo()

{

     int from, to, len, dest;

     int tick;

     CApiEditText *pView;

 

     pView=GetActiveView();

    pView->ExtraX=0;

     ....

void CApiEdit::Redo()

{

     int from, to, len;

     int tick;

     CApiEditText *pView;

 

     pView=GetActiveView();

    pView->ExtraX=0;

     ....

 

¿©±â±îÁö Äڵ带 ÀÛ¼ºÇÑ ÈÄ Å×½ºÆ®ÇØ º¸¸é °¡»ó À§Ä¡·Î ij·µµµ Àß À̵¿ÇÏ°í °¡»ó À§Ä¡¿¡¼­ ÀÔ·ÂÇÏ¸é °ø¹éÀ» ÀÔ·ÂÇÑ ÈÄ ¹®ÀÚ¸¦ »ðÀÔÇÒ °ÍÀÌ´Ù. Á¦¾î ÄÚµå º¸±â ¿É¼ÇÀ» ÄÑ ³õ°í È®ÀÎÇØ º¸¸é °ø¹éÀÌ µé¾î°¡´Â ¸ð¾çÀ» Àç¹ÌÀÖ°Ô Áñ±æ ¼ö ÀÖ´Ù. °¡»ó À§Ä¡¶õ ´Ù¼Ò ºñÁ¤»óÀûÀÎ À§Ä¡À̱⠶§¹®¿¡ »ç½Ç ´Ù·ç±â°¡ ¹«Ã´ ±î´Ù·Î¿ì¸é ÃÖÁ¾ ¿Ï¼º Äڵ带 ¸¸µé±â±îÁö »ó´çÇÑ µð¹ö±ëÀ» ÇØ¾ß¸¸ Çß¾ú´Ù. ±×·±µ¥ ExtraX°°Àº °ªÀº ¼ö½Ã·Î º¯Çϴµ¥´Ù º¯°æÇϰí ÂüÁ¶ÇÏ´Â °÷ÀÌ ¿ö³« ¸¹¾Æ¼­ µð¹ö°Å·Î ÀÌ °ªÀÇ º¯È­¸¦ °üÂûÇϱⰡ ¹«Ã´À̳ª ¾î·Æ´Ù. °üÂûÀÌ °ï¶õÇÑ ÀÌ·± °ªÀº ŸÀ̸Ӹ¦ ¼³Ä¡Çؼ­ ÁÖ±âÀûÀ¸·Î Ãâ·ÂÇÏ´Â ¹æ¹ýÀ» »ç¿ëÇÒ ¼ö ÀÖ´Ù. ÀÏÁ¾ÀÇ µð¹ö±ë ÆÁÀÌ¸ç ½ÇÀü¿¡¼­ ÀÚÁÖ »ç¿ëµÇ¹Ç·Î Àß ºÁ µÎµµ·Ï ÇÏÀÚ.

 

BOOL CApiEditText::OnCreate(HWND hWnd, LPCREATESTRUCT lpCreateStruct)

{

     ...

#ifdef _DEBUG

     SetTimer(hWnd,100,200,NULL);

#endif

     return TRUE;

}

 

OnCreate¿¡¼­ µð¹ö±ë¿ëÀÇ Å¸À̸Ӹ¦ ¼³Ä¡Ç쵂 ÁÖ±â´Â °ªÀ» »ìÆì º¸±â¿¡ Àû´çÇÑ °ªÀ» ÁØ´Ù. 200À¸·Î ÁÖ¾úÀ¸¹Ç·Î ÃÊ´ç 5¹ø¾¿ °ªÀ» °¨½ÃÇÒ ¼ö ÀÖ´Ù. ÀÌ·± ±â´ÉÀº µð¹ö±ë Áß¿¡¸¸ »ç¿ëÇϹǷΠ¸±¸®Áî ¸ðµå¿¡¼­´Â Á¦¿ÜÇÏ´Â °ÍÀÌ ÁÁ´Ù. ¾Æ´Ï¸é Àá½Ã¸¸ ¾²°í »èÁ¦Çصµ »ó°ü¾øÁö¸¸ °³¹ßÀ» ÇÏ´Ù º¸¸é ¼ö½Ã·Î ÀÌ·± ÀåÄ¡°¡ ÇÊ¿äÇØÁö¹Ç·Î Á¶°ÇºÎ ÄÄÆÄÀÏ·Î ÀÛ¼ºÇØ ³õ´Â °ÍÀÌ Æí¸®ÇÏ´Ù. OnTimer¿¡¼­ °ü½ÉÀÖ´Â °ªÀ» ÁÖ±âÀûÀ¸·Î Ãâ·ÂÇÑ´Ù.

 

void CApiEditText::OnTimer(HWND hWnd, UINT id)

{

     POINT pt;

 

     switch (id) {

     case 1:

          GetCursorPos(&pt);

          ScreenToClient(hWnd, &pt);

          SendMessage(hWnd, WM_MOUSEMOVE, 0, MAKELPARAM(pt.x, pt.y));

          break;

#ifdef _DEBUG

     case 100:

          TCHAR szDebug[256];

          wsprintf(szDebug,"PrevX=%d, ExtraX=%d",PrevX,ExtraX);

          SetWindowText(GetParent(pFrame->hWnd),szDebug);

          break;

#endif

     }

}

 

ExtraX°ªÀ» ¹®ÀÚ¿­·Î Á¶¸³ÇÑ ÈÄ Å¸ÀÌÆ² ¹Ù¿¡ Ãâ·ÂÇß´Ù. µð¹ö°ÅÀÇ Ãâ·ÂâÀ» Ȱ¿ëÇÒ ¼öµµ ÀÖÁö¸¸ °£´ÜÇÑ °ª Çϳª¶ó¸é Ç×»ó Àß º¸À̴ ŸÀÌÆ² ¹Ù¸¦ Ȱ¿ëÇÏ´Â °ÍÀÌ ´õ °£ÆíÇÏ´Ù. ¾ÆÁÖ °£´ÜÇÑ ÆÁÀÎ °Í °°Áö¸¸ µð¹ö°ÅÀÇ ¿ÍÄ¡ ±â´Éº¸´Ù ¿ÀÈ÷·Á Æí¸®ÇÏ°í °­·ÂÇÑ µð¹ö±ë ¹æ¹ýÀÌ´Ù. ¶ÇÇÑ ÀÌ ¿¹Á¦°¡ ExtraX¸¦ ¾î¶»°Ô °ü¸®ÇÏ´ÂÁö ÀÚ¼¼È÷ °üÂûÇÏ°í ½ÍÀ» ¶§µµ ÀÌ·± ¹æ¹ýÀ» ¾µ ¼ö ÀÖ´Ù.