サクラエディタ

長年使用していたWZ4だが、放置プレーなので、乗換えを検討してみた。
カスタマイズできるフリーのエディタの中で、サクラエディタは選択していない状態でCtrl+Xを入力すると1行削除になり、割とWZ(VZ)に近いので、使ってみることにした。

が、問題が二つ。
a. ペーストすると、コピーした内容の改行コードがそのまま使われる
b. 改行コードがCRLFの時、行末まで一致する検索・置換を行うと、CRまでが含まれる

(a)は仕様のようで、まあ好みの問題なのだけど、こういう動作をするものは少数派ではないか。改行コードが混在するテキストを編集するシチュエーションは稀だし、文字コードは変換されるのに改行コードが変換されないというのは統一感がない。

というわけで、入力改行コードに変換するようにしてみた。


CEditView.cpp:
...
static char *ConvertEOL( const char *pszBuffer, const CEOL &eol )
{
char *pDst = new char[strlen(pszBuffer) * 2 + 1];
char *p = pDst;
char c;
while ( ( c = *pszBuffer++ ) != '\0' ) {
if ( c == '\r' ) {
if ( *pszBuffer == '\n' ||
( *pszBuffer == '\r' && *(pszBuffer + 1) == '\n' ) ) {
continue;
}
}
if ( c == '\n' || c == '\r' ) {
switch ( eol.GetType() ) {
default:
case EOL_CRLF:
*p++ = '\r';
case EOL_LF:
*p++ = '\n';
break;
case EOL_LFCR:
*p++ = '\n';
case EOL_CR:
*p++ = '\r';
break;
}
} else {
*p++ = c;
}
}
*p = '\0';
return pDst;
}
...
hglb = ::GetClipboardData( CF_UNICODETEXT );
...
cmemUnicode.UnicodeToSJIS();
// cmemBuf.SetDataSz( cmemUnicode.GetPtr() );
char *pszBuffer = ConvertEOL( cmemUnicode.GetPtr(), m_pcEditDoc->GetNewLineCode() );
cmemBuf.SetDataSz( pszBuffer );
delete [] pszBuffer;
...
hglb = ::GetClipboardData( CF_OEMTEXT );
...
lptstr = (char*)::GlobalLock(hglb);
// cmemBuf.SetDataSz( lptstr );
char *pszBuffer = ConvertEOL( lptstr, m_pcEditDoc->GetNewLineCode() );
cmemBuf.SetDataSz( pszBuffer );
delete [] pszBuffer;
...

(b)はバグだと思うのだが、サクラエディタでは明確に\rを指定しないといけないのだろうか。
\r\nの途中にマッチした場合、位置を一つ前にずらすようにしてみた。
ただし、行末表現($)が入っているとおかしいまま。これは直せなかった。


CBregexp.cpp:
...
static void FixResult( BREGEXP *RegExp )
{
int i;
for ( i = 0; i <= RegExp->nparens; ++i ) {
char *p = RegExp->endp[i];
if ( p == RegExp->startp[i] || p == NULL ) {
continue;
}
if ( *( p - 1 ) == '\r' && *p == '\n' ) {
--(RegExp->endp[i]);
}
}
}
...
result = BSubstEx(...
if ( result > 0 ) {
FixResult( m_pRegExp );
}
...