Skip to content

Commit 30ef372

Browse files
authored
Merge 1f088c1 into c1568de
2 parents c1568de + 1f088c1 commit 30ef372

File tree

15 files changed

+466
-106
lines changed

15 files changed

+466
-106
lines changed

sakura_core/CGrepAgent.cpp

Lines changed: 248 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,9 @@
3030
#include "CSearchAgent.h"
3131
#include "dlg/CDlgCancel.h"
3232
#include "_main/CAppMode.h"
33+
#include "_main/CMutex.h"
34+
#include "env/CShareData.h"
35+
#include "env/CSakuraEnvironment.h"
3336
#include "COpeBlk.h"
3437
#include "window/CEditWnd.h"
3538
#include "charset/CCodeMediator.h"
@@ -46,6 +49,7 @@
4649
#include <iterator>
4750
#include <deque>
4851
#include <memory>
52+
#include "apiwrap/StdApi.h"
4953
#include "apiwrap/StdControl.h"
5054
#include "CSelectLang.h"
5155
#include "sakura_rc.h"
@@ -105,6 +109,93 @@ std::wstring FormatPathList( const ContainerType& containter )
105109
return strPatterns;
106110
}
107111

112+
class CFileLoadOrWnd{
113+
CFileLoad m_cfl;
114+
HWND m_hWnd;
115+
int m_nLineCurrent;
116+
int m_nLineNum;
117+
public:
118+
CFileLoadOrWnd(const SEncodingConfig& encode, HWND hWnd)
119+
: m_cfl(encode)
120+
, m_hWnd(hWnd)
121+
, m_nLineCurrent(0)
122+
, m_nLineNum(0)
123+
{
124+
}
125+
~CFileLoadOrWnd(){
126+
}
127+
ECodeType FileOpen(const WCHAR* pszFile, bool bBigFile, ECodeType charCode, int nFlag)
128+
{
129+
if( m_hWnd ){
130+
DWORD_PTR dwMsgResult = 0;
131+
if( 0 == ::SendMessageTimeout(m_hWnd, MYWM_GETLINECOUNT, 0, 0, SMTO_NORMAL, 10000, &dwMsgResult) ){
132+
// エラーかタイムアウト
133+
throw CError_FileOpen();
134+
}
135+
m_nLineCurrent = 0;
136+
m_nLineNum = (int)dwMsgResult;
137+
::SendMessageAny(m_hWnd, MYWM_GETFILEINFO, 0, 0);
138+
const EditInfo* editInfo = &GetDllShareData().m_sWorkBuffer.m_EditInfo_MYWM_GETFILEINFO;
139+
return editInfo->m_nCharCode;
140+
}
141+
return m_cfl.FileOpen(pszFile, bBigFile, charCode, nFlag);
142+
}
143+
EConvertResult ReadLine(CNativeW* buffer, CEol* pcEol){
144+
if( m_hWnd ){
145+
const int max_size = (int)GetDllShareData().m_sWorkBuffer.GetWorkBufferCount<const WCHAR>();
146+
const WCHAR* pLineData = GetDllShareData().m_sWorkBuffer.GetWorkBuffer<const WCHAR>();
147+
buffer->SetStringHoldBuffer(L"", 0);
148+
if( m_nLineNum <= m_nLineCurrent ){
149+
return RESULT_FAILURE;
150+
}
151+
int nLineOffset = 0;
152+
int nLineLen = 0; //初回用仮値
153+
do{
154+
// m_sWorkBuffer#m_Workの排他制御。外部コマンド出力/TraceOut/Diffが対象
155+
LockGuard<CMutex> guard( CShareData::GetMutexShareWork() );
156+
{
157+
nLineLen = ::SendMessageAny(m_hWnd, MYWM_GETLINEDATA, m_nLineCurrent, nLineOffset);
158+
if( nLineLen == 0 ){ return RESULT_FAILURE; } // EOF => 正常終了
159+
if( nLineLen < 0 ){ return RESULT_FAILURE; } // 何かエラー
160+
buffer->AllocStringBuffer(max_size);
161+
buffer->AppendString(pLineData, t_min(nLineLen, max_size));
162+
}
163+
nLineOffset += max_size;
164+
}while(max_size < nLineLen);
165+
if( 0 < nLineLen ){
166+
if( 1 < nLineLen && (*buffer)[nLineLen - 2] == WCODE::CR &&
167+
(*buffer)[nLineLen - 1] == WCODE::LF){
168+
pcEol->SetType(EEolType::cr_and_lf);
169+
}else{
170+
pcEol->SetTypeByString(buffer->GetStringPtr() + nLineLen - 1, 1);
171+
}
172+
}
173+
m_nLineCurrent++;
174+
return RESULT_COMPLETE;
175+
}
176+
return m_cfl.ReadLine(buffer, pcEol);
177+
}
178+
LONGLONG GetFileSize(){
179+
if( m_hWnd ){
180+
return 0;
181+
}
182+
return m_cfl.GetFileSize();
183+
}
184+
int GetPercent(){
185+
if( m_hWnd ){
186+
return (int)(m_nLineCurrent * 100.0 / m_nLineNum);
187+
}
188+
return m_cfl.GetPercent();
189+
}
190+
191+
void FileClose(){
192+
if( m_hWnd ){
193+
return;
194+
}
195+
m_cfl.FileClose();
196+
}
197+
};
198+
108199
CGrepAgent::CGrepAgent()
109200
: m_bGrepMode( false ) /* Grepモードか */
110201
, m_bGrepRunning( false ) /* Grep処理中 */
@@ -207,6 +298,60 @@ void CGrepAgent::AddTail( CEditView* pcEditView, const CNativeW& cmem, bool bAdd
207298
}
208299
}
209300

301+
int GetHwndTitle(HWND& hWndTarget, CNativeW* pmemTitle, WCHAR* pszWindowName, WCHAR* pszWindowPath, const WCHAR* pszFile)
302+
{
303+
if( 0 != wcsncmp(L":HWND:", pszFile, 6) ){
304+
return 0; // ハンドルGrepではない
305+
}
306+
#ifdef _WIN64
307+
_stscanf(pszFile + 6, L"%016I64x", &hWndTarget);
308+
#else
309+
_stscanf(pszFile + 6, L"%08x", &hWndTarget);
310+
#endif
311+
if( pmemTitle ){
312+
const wchar_t* p = L"Window:[";
313+
pmemTitle->SetStringHoldBuffer(p, 8);
314+
}
315+
if( !IsSakuraMainWindow(hWndTarget) ){
316+
return -1;
317+
}
318+
::SendMessageAny(hWndTarget, MYWM_GETFILEINFO, 0, 0);
319+
EditInfo* editInfo = &(GetDllShareData().m_sWorkBuffer.m_EditInfo_MYWM_GETFILEINFO);
320+
if( '\0' == editInfo->m_szPath[0] ){
321+
// Grepかアウトプットか無題
322+
WCHAR szTitle[_MAX_PATH]{};
323+
WCHAR szGrep[100]{};
324+
editInfo->m_bIsModified = false;
325+
const EditNode* node = CAppNodeManager::getInstance()->GetEditNode(hWndTarget);
326+
WCHAR* pszTagName = szTitle;
327+
if( editInfo->m_bIsGrep ){
328+
// Grepは検索キーとタグがぶつかることがあるので単に(Grep)と表示
329+
pszTagName = szGrep;
330+
wcsncpy_s(pszTagName, _countof(szGrep), L"(Grep)", _TRUNCATE);
331+
}
332+
CFileNameManager::getInstance()->GetMenuFullLabel_WinListNoEscape(szTitle, _countof(szTitle), editInfo, node->m_nId, -1, NULL );
333+
#ifdef _WIN64
334+
auto_sprintf(pszWindowName, L":HWND:[%016I64x]%s", hWndTarget, pszTagName);
335+
#else
336+
auto_sprintf(pszWindowName, L":HWND:[%08x]%s", hWndTarget, pszTagName);
337+
#endif
338+
if( pmemTitle ){
339+
pmemTitle->AppendString(szTitle);
340+
}
341+
pszWindowPath[0] = L'\0';
342+
}else{
343+
SplitPath_FolderAndFile(editInfo->m_szPath, pszWindowPath, pszWindowName);
344+
if( pmemTitle ){
345+
pmemTitle->AppendString(pszWindowName);
346+
}
347+
}
348+
if( pmemTitle ){
349+
pmemTitle->AppendString(L"]");
350+
}
351+
return 1;
352+
}
353+
354+
210355
/*! Grep実行
211356
212357
@param[in] pcmGrepKey 検索パターン
@@ -458,13 +603,28 @@ DWORD CGrepAgent::DoGrep(
458603
}
459604
}
460605

461-
cmemMessage.AppendString( LS( STR_GREP_SEARCH_TARGET ) ); //L"検索対象 "
606+
HWND hWndTarget = NULL;
607+
WCHAR szWindowName[_MAX_PATH];
608+
WCHAR szWindowPath[_MAX_PATH];
462609
{
463-
// 解析済みのファイルパターン配列を取得する
464-
const auto& vecSearchFileKeys = cGrepEnumKeys.m_vecSearchFileKeys;
465-
std::wstring strPatterns = FormatPathList( vecSearchFileKeys );
466-
cmemMessage.AppendString( strPatterns.c_str(), strPatterns.length() );
610+
int nHwndRet = GetHwndTitle(hWndTarget, &cmemWork, szWindowName, szWindowPath, pcmGrepFile->GetStringPtr());
611+
if( -1 == nHwndRet ){
612+
cmemMessage.AppendString(L"HWND handle error.\n");
613+
if( sGrepOption.bGrepHeader ){
614+
AddTail(pcViewDst, cmemMessage, sGrepOption.bGrepStdout);
615+
}
616+
return 0;
617+
}else if( 0 == nHwndRet ){
618+
{
619+
// 解析済みのファイルパターン配列を取得する
620+
const auto& vecSearchFileKeys = cGrepEnumKeys.m_vecSearchFileKeys;
621+
std::wstring strPatterns = FormatPathList( vecSearchFileKeys );
622+
cmemWork.SetString( strPatterns.c_str(), strPatterns.length() );
623+
}
624+
}
467625
}
626+
cmemMessage.AppendString( LS( STR_GREP_SEARCH_TARGET ) ); //L"検索対象 "
627+
cmemMessage += cmemWork;
468628
cmemMessage.AppendString( L"\r\n" );
469629

470630
cmemMessage.AppendString( LS( STR_GREP_SEARCH_FOLDER ) ); //L"フォルダ "
@@ -586,38 +746,87 @@ DWORD CGrepAgent::DoGrep(
586746

587747
int nGrepTreeResult = 0;
588748

589-
for( int nPath = 0; nPath < (int)vPaths.size(); nPath++ ){
590-
bool bOutputBaseFolder = false;
591-
std::wstring sPath = ChopYen( vPaths[nPath] );
592-
int nTreeRet = DoGrepTree(
593-
pcViewDst,
594-
&cDlgCancel,
595-
pcmGrepKey->GetStringPtr(),
596-
cmemReplace,
597-
cGrepEnumKeys,
598-
cGrepExceptAbsFiles,
599-
cGrepExceptAbsFolders,
600-
sPath.c_str(),
601-
sPath.c_str(),
602-
sSearchOption,
603-
sGrepOption,
604-
pattern,
605-
&cRegexp,
606-
0,
607-
bOutputBaseFolder,
608-
&nHitCount,
609-
cmemMessage,
610-
cUnicodeBuffer
611-
);
612-
if( nTreeRet == -1 ){
613-
nGrepTreeResult = -1;
614-
break;
749+
if( hWndTarget ){
750+
for( HWND hwnd = hWndTarget; NULL != hwnd; hwnd = NULL ){
751+
bool bOutputBaseFolder = false;
752+
bool bOutputFolderName = false;
753+
// 複数ウィンドウループ予約
754+
auto nPathLen = wcsnlen_s(szWindowPath, _countof(szWindowPath));
755+
std::wstring currentFile = szWindowPath;
756+
if( currentFile.size() ){
757+
currentFile += L'\\';
758+
nPathLen += 1;
759+
}
760+
currentFile += szWindowName;
761+
int nHitCount = nGrepTreeResult;
762+
int nTreeRet = DoGrepFile(
763+
pcViewDst,
764+
&cDlgCancel,
765+
hwnd,
766+
pcmGrepKey->GetStringPtr(),
767+
szWindowName,
768+
sSearchOption,
769+
sGrepOption,
770+
pattern,
771+
&cRegexp,
772+
&nHitCount,
773+
currentFile.c_str(),
774+
szWindowPath,
775+
(sGrepOption.bGrepSeparateFolder && sGrepOption.bGrepOutputBaseFolder ? L"" : szWindowPath),
776+
(sGrepOption.bGrepSeparateFolder ? szWindowName : currentFile.c_str() + nPathLen),
777+
bOutputBaseFolder,
778+
bOutputFolderName,
779+
cmemMessage,
780+
cUnicodeBuffer
781+
);
782+
if( nTreeRet == -1 ){
783+
nGrepTreeResult = -1;
784+
break;
785+
}
786+
nGrepTreeResult += nTreeRet;
787+
}
788+
if( 0 < cmemMessage.GetStringLength() ){
789+
AddTail( pcViewDst, cmemMessage, sGrepOption.bGrepStdout );
790+
pcViewDst->GetCommander().Command_GOFILEEND( false );
791+
if( !CEditWnd::getInstance()->UpdateTextWrap() )
792+
CEditWnd::getInstance()->RedrawAllViews( pcViewDst );
793+
cmemMessage.Clear();
794+
}
795+
nHitCount = nGrepTreeResult;
796+
}else{
797+
for( int nPath = 0; nPath < (int)vPaths.size(); nPath++ ){
798+
bool bOutputBaseFolder = false;
799+
std::wstring sPath = ChopYen( vPaths[nPath] );
800+
int nTreeRet = DoGrepTree(
801+
pcViewDst,
802+
&cDlgCancel,
803+
pcmGrepKey->GetStringPtr(),
804+
cmemReplace,
805+
cGrepEnumKeys,
806+
cGrepExceptAbsFiles,
807+
cGrepExceptAbsFolders,
808+
sPath.c_str(),
809+
sPath.c_str(),
810+
sSearchOption,
811+
sGrepOption,
812+
pattern,
813+
&cRegexp,
814+
0,
815+
bOutputBaseFolder,
816+
&nHitCount,
817+
cmemMessage,
818+
cUnicodeBuffer
819+
);
820+
if( nTreeRet == -1 ){
821+
nGrepTreeResult = -1;
822+
break;
823+
}
824+
nGrepTreeResult += nTreeRet;
825+
}
826+
if( 0 < cmemMessage.GetStringLength() ) {
827+
AddTail( pcViewDst, cmemMessage, sGrepOption.bGrepStdout );
828+
cmemMessage._SetStringLength(0);
615829
}
616-
nGrepTreeResult += nTreeRet;
617-
}
618-
if( 0 < cmemMessage.GetStringLength() ) {
619-
AddTail( pcViewDst, cmemMessage, sGrepOption.bGrepStdout );
620-
cmemMessage._SetStringLength(0);
621830
}
622831
if( -1 == nGrepTreeResult && sGrepOption.bGrepHeader ){
623832
const wchar_t* p = LS( STR_GREP_SUSPENDED ); //L"中断しました。\r\n"
@@ -781,6 +990,7 @@ int CGrepAgent::DoGrepTree(
781990
nRet = DoGrepFile(
782991
pcViewDst,
783992
pcDlgCancel,
993+
NULL,
784994
pszKey,
785995
lpFileName,
786996
sSearchOption,
@@ -1101,6 +1311,7 @@ static void OutputPathInfo(
11011311
int CGrepAgent::DoGrepFile(
11021312
CEditView* pcViewDst, //!<
11031313
CDlgCancel* pcDlgCancel, //!< [in] Cancelダイアログへのポインタ
1314+
HWND hWndTarget, //!< [in] 対象Windows(NULLでファイル)
11041315
const wchar_t* pszKey, //!< [in] 検索パターン
11051316
const WCHAR* pszFile, //!< [in] 処理対象ファイル名(表示用)
11061317
const SSearchOption& sSearchOption, //!< [in] 検索オプション
@@ -1132,7 +1343,7 @@ int CGrepAgent::DoGrepFile(
11321343
if( !CDocTypeManager().GetTypeConfigMini( CDocTypeManager().GetDocumentTypeOfPath( pszFile ), &type ) ){
11331344
return -1;
11341345
}
1135-
CFileLoad cfl( type->m_encoding ); // 2012/12/18 Uchi 検査するファイルのデフォルトの文字コードを取得する様に
1346+
CFileLoadOrWnd cfl( type->m_encoding, hWndTarget ); // 2012/12/18 Uchi 検査するファイルのデフォルトの文字コードを取得する様に
11361347
int nOldPercent = 0;
11371348

11381349
int nKeyLen = wcslen( pszKey );

sakura_core/CGrepAgent.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,7 @@ class CGrepAgent : public CDocListenerEx{
129129
int DoGrepFile(
130130
CEditView* pcViewDst,
131131
CDlgCancel* pcDlgCancel,
132+
HWND hWndTarget,
132133
const wchar_t* pszKey,
133134
const WCHAR* pszFile,
134135
const SSearchOption& sSearchOption,

sakura_core/String_define.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1323,5 +1323,7 @@
13231323
#define STR_FILEDIALOG_EOL 35039
13241324
#define STR_FILEDIALOG_MRU 35040
13251325
#define STR_FILEDIALOG_OPENFOLDER 35041
1326+
#define STR_DLGGREP_THISDOC 35045
1327+
#define STR_DLGGREP_THISDOC_ERROR 35046
13261328

13271329
// Now using max number 35044 by STR_STATUS_FONTZOOM_1

sakura_core/_main/CControlTray.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,8 @@ static LRESULT CALLBACK CControlTrayWndProc( HWND, UINT, WPARAM, LPARAM );
6868
//Stonee, 2001/07/01 多重起動された場合は前回のダイアログを前面に出すようにした。
6969
void CControlTray::DoGrep()
7070
{
71+
m_cDlgGrep.m_bEnableThisText = false;
72+
7173
//Stonee, 2001/06/30
7274
//前回のダイアログがあれば前面に (suggested by genta)
7375
if ( ::IsWindow(m_cDlgGrep.GetHwnd()) ){

0 commit comments

Comments
 (0)