bool IsRootPath(const string &Path) { size_t PathRootLen = GetPathRootLength(Path); if (Path.GetLength() == PathRootLen) return true; if (Path.GetLength() == PathRootLen + 1 && IsSlash(Path[Path.GetLength() - 1])) return true; return false; }
bool History::GetSimilar(string &strStr, int LastCmdPartLength, bool bAppend) { int Length=(int)strStr.GetLength(); if (LastCmdPartLength!=-1 && LastCmdPartLength<Length) Length=LastCmdPartLength; if (LastCmdPartLength==-1) { ResetPosition(); } for (HistoryRecord *HistoryItem=HistoryList.Prev(CurrentItem); HistoryItem != CurrentItem; HistoryItem=HistoryList.Prev(HistoryItem)) { if (!HistoryItem) continue; if (!StrCmpNI(strStr,HistoryItem->strName,Length) && StrCmp(strStr,HistoryItem->strName)) { if (bAppend) strStr += &HistoryItem->strName[Length]; else strStr = HistoryItem->strName; CurrentItem = HistoryItem; return true; } } return false; }
BOOL AddEndSlash(string &strPath, wchar_t TypeSlash) { wchar_t *lpwszPath = strPath.GetBuffer(strPath.GetLength()+2); BOOL Result = AddEndSlash(lpwszPath, TypeSlash); strPath.ReleaseBuffer(); return Result; }
int DizList::GetDizPosEx(const string& Name, const string& ShortName, int *TextPos) { int DizPos=GetDizPos(Name,TextPos); if (DizPos==-1) DizPos=GetDizPos(ShortName,TextPos); //если файл описаний был в OEM/ANSI то имена файлов могут не совпадать с юникодными if (DizPos==-1 && !IsUnicodeOrUtfCodePage(OrigCodePage) && OrigCodePage!=CP_DEFAULT) { size_t len = Name.GetLength(); char *tmp = (char *)xf_realloc_nomove(AnsiBuf, len+1); if (!tmp) return -1; AnsiBuf = tmp; WideCharToMultiByte(OrigCodePage, 0, Name, static_cast<int>(len), AnsiBuf, static_cast<int>(len), nullptr, nullptr); AnsiBuf[len]=0; string strRecoded(AnsiBuf, OrigCodePage); if (strRecoded==Name) return -1; return GetDizPos(strRecoded,TextPos); } return DizPos; }
void QuoteSpaceOnly(string& strSrc) { TCHAR* lpBuffer = strSrc.GetBuffer(strSrc.GetLength()+5); FSF.QuoteSpaceOnly(lpBuffer); strSrc.ReleaseBuffer(); }
void farQuoteSpaceOnly(string& strStr) { TCHAR* pBuffer = strStr.GetBuffer(strStr.GetLength()+2); FSF.QuoteSpaceOnly(pBuffer); strStr.ReleaseBuffer(); }
void UnquoteExternal(string &strStr) { size_t len = strStr.GetLength(); if (len > 1 && strStr.At(0) == L'\"' && strStr.At(len-1) == L'\"') { strStr.SetLength(len-1); strStr.LShift(1); } }
int GetRegKey(const wchar_t *Key,const wchar_t *ValueName,string &strValueData,const wchar_t *Default,DWORD *pType) { int ExitCode=!ERROR_SUCCESS; HKEY hKey=OpenRegKey(Key); if (hKey) // надобно проверить! { DWORD Type,QueryDataSize=0; if ((ExitCode = RegQueryValueEx( hKey, ValueName, 0, &Type, nullptr, &QueryDataSize )) == ERROR_SUCCESS) { wchar_t *TempBuffer = strValueData.GetBuffer(QueryDataSize/sizeof(wchar_t)+1); // ...то выделим сколько надо ExitCode = RegQueryValueEx(hKey,ValueName,0,&Type,(unsigned char *)TempBuffer,&QueryDataSize); strValueData.ReleaseBuffer(QueryDataSize/sizeof(wchar_t)); if (strValueData.GetLength() > 0 && !strValueData.At(strValueData.GetLength()-1)) strValueData.SetLength(strValueData.GetLength()-1); } if (pType) *pType=Type; CloseRegKey(hKey); } if (ExitCode!=ERROR_SUCCESS) { strValueData = Default; return FALSE; } return TRUE; }
bool FindLastSlash(size_t &Pos, const string &Str) { for (size_t p = Str.GetLength(); p > 0; p--) { if (IsSlash(Str[p - 1])) { Pos = p - 1; return true; } } return false; }
bool FindSlash(size_t &Pos, const string &Str, size_t StartPos) { for (size_t p = StartPos; p < Str.GetLength(); p++) { if (IsSlash(Str[p])) { Pos = p; return true; } } return false; }
string& WINAPI RemoveTrailingSpaces(string &strStr) { if (strStr.IsEmpty()) return strStr; const wchar_t *Str = strStr; const wchar_t *ChPtr = Str + strStr.GetLength() - 1; for (; ChPtr >= Str && (IsSpace(*ChPtr) || IsEol(*ChPtr)); ChPtr--) ; strStr.SetLength(ChPtr < Str ? 0 : ChPtr-Str+1); return strStr; }
string ReplaceBrackets(const string& SearchStr,const string& ReplaceStr,RegExpMatch* Match,int Count) { string result; size_t pos=0,length=ReplaceStr.GetLength(); while (pos<length) { bool common=true; if (ReplaceStr[pos]=='$') { ++pos; if (pos>length) break; wchar_t symbol=Upper(ReplaceStr[pos]); int index=-1; if (symbol>='0'&&symbol<='9') { index=symbol-'0'; } else if (symbol>='A'&&symbol<='Z') { index=symbol-'A'+10; } if (index>=0) { if (index<Count) { string bracket(SearchStr.CPtr()+Match[index].start,Match[index].end-Match[index].start); result+=bracket; } common=false; } } if (common) { result+=ReplaceStr[pos]; } ++pos; } return result; }
/* $ 02.02.2001 IS Заменяет пробелами непечатные символы в строке. В настоящий момент обрабатываются только cr и lf. */ string& WINAPI RemoveUnprintableCharacters(string &strStr) { wchar_t *p = strStr.GetBuffer(); while (*p) { if (IsEol(*p)) *p=L' '; p++; } strStr.ReleaseBuffer(strStr.GetLength()); return RemoveExternalSpaces(strStr); }
string ExtractFileName(const string &Path) { size_t p; if (FindLastSlash(p, Path)) p++; else p = 0; size_t PathRootLen = GetPathRootLength(Path); if (p <= PathRootLen && PathRootLen) return string(); return string(Path.CPtr() + p, Path.GetLength() - p); }
// Заменить в строке Str Count вхождений подстроки FindStr на подстроку ReplStr // Если Count < 0 - заменять "до полной победы" // Return - количество замен int ReplaceStrings(string &strStr,const wchar_t *FindStr,const wchar_t *ReplStr,int Count,BOOL IgnoreCase) { const int LenFindStr=StrLength(FindStr); if ( !LenFindStr || !Count ) return 0; const int LenReplStr=StrLength(ReplStr); size_t L=strStr.GetLength(); const int Delta = LenReplStr-LenFindStr; const int AllocDelta = Delta > 0 ? Delta*10 : 0; size_t I=0; int J=0; while (I+LenFindStr <= L) { int Res=IgnoreCase?StrCmpNI(&strStr[I], FindStr, LenFindStr):StrCmpN(&strStr[I], FindStr, LenFindStr); if (!Res) { wchar_t *Str; if (L+Delta+1 > strStr.GetSize()) Str = strStr.GetBuffer(L+AllocDelta); else Str = strStr.GetBuffer(); if (Delta > 0) wmemmove(Str+I+Delta,Str+I,L-I+1); else if (Delta < 0) wmemmove(Str+I,Str+I-Delta,L-I+Delta+1); wmemcpy(Str+I,ReplStr,LenReplStr); I += LenReplStr; L+=Delta; strStr.ReleaseBuffer(L); if (++J == Count && Count > 0) break; } else { I++; } } return J; }
BOOL DeleteEndSlash(string &strPath, bool AllEndSlash) { BOOL Ret=FALSE; if (!strPath.IsEmpty()) { size_t len=strPath.GetLength(); wchar_t *lpwszPath = strPath.GetBuffer(); while (len && IsSlash(lpwszPath[--len])) { Ret=TRUE; lpwszPath[len] = L'\0'; if (!AllEndSlash) break; } strPath.ReleaseBuffer(); } return Ret; }
int PrepareHotKey(string &strHotKey) { int FuncNum=0; if (strHotKey.GetLength() > 1) { // если хоткей больше 1 символа, считаем это случаем "F?", причем при кривизне всегда будет "F1" FuncNum=_wtoi(strHotKey.CPtr()+1); if (FuncNum < 1 || FuncNum > 24) { FuncNum=1; strHotKey=L"F1"; } } else { // при наличии "&" продублируем if (strHotKey.At(0) == L'&') strHotKey += L"&"; } return FuncNum; }
// На основе имени файла (Src) и маски (Dest) генерируем новое имя // SelectedFolderNameLength - длина каталога. Например, есть // каталог dir1, а в нем файл file1. Нужно сгенерировать имя по маске для dir1. // Параметры могут быть следующими: Src="dir1", SelectedFolderNameLength=0 // или Src="dir1\\file1", а SelectedFolderNameLength=4 (длина "dir1") int ConvertWildcards(const wchar_t *SrcName, string &strDest, int SelectedFolderNameLength) { string strPartAfterFolderName; string strSrc = SrcName; wchar_t *DestName = strDest.GetBuffer(strDest.GetLength()+strSrc.GetLength()+1); //??? wchar_t *DestNamePtr = (wchar_t*)PointToName(DestName); string strWildName = DestNamePtr; if (!wcschr(strWildName, L'*') && !wcschr(strWildName, L'?')) { //strDest.ReleaseBuffer (); не надо так как строка не поменялась return FALSE; } if (SelectedFolderNameLength) { strPartAfterFolderName = ((const wchar_t *)strSrc+SelectedFolderNameLength); strSrc.SetLength(SelectedFolderNameLength); } const wchar_t *Src = strSrc; const wchar_t *SrcNamePtr = PointToName(Src); int BeforeNameLength = DestNamePtr==DestName ? (int)(SrcNamePtr-Src) : 0; wchar_t *PartBeforeName = (wchar_t*)xf_malloc((BeforeNameLength+1)*sizeof(wchar_t)); xwcsncpy(PartBeforeName, Src, BeforeNameLength+1); const wchar_t *SrcNameDot = wcsrchr(SrcNamePtr, L'.'); const wchar_t *CurWildPtr = strWildName; while (*CurWildPtr) { switch (*CurWildPtr) { case L'?': CurWildPtr++; if (*SrcNamePtr) *(DestNamePtr++)=*(SrcNamePtr++); break; case L'*': CurWildPtr++; while (*SrcNamePtr) { if (*CurWildPtr==L'.' && SrcNameDot && !wcschr(CurWildPtr+1,L'.')) { if (SrcNamePtr==SrcNameDot) break; } else if (*SrcNamePtr==*CurWildPtr) { break; } *(DestNamePtr++)=*(SrcNamePtr++); } break; case L'.': CurWildPtr++; *(DestNamePtr++)=L'.'; if (wcspbrk(CurWildPtr,L"*?")) while (*SrcNamePtr) if (*(SrcNamePtr++)==L'.') break; break; default: *(DestNamePtr++)=*(CurWildPtr++); if (*SrcNamePtr && *SrcNamePtr!=L'.') SrcNamePtr++; break; } } *DestNamePtr=0; if (DestNamePtr!=DestName && *(DestNamePtr-1)==L'.') *(DestNamePtr-1)=0; strDest.ReleaseBuffer(); if (*PartBeforeName) strDest = PartBeforeName+strDest; if (SelectedFolderNameLength) strDest += strPartAfterFolderName; //BUGBUG???, was src in 1.7x xf_free(PartBeforeName); return TRUE; }
bool PathStartsWith(const string &Path, const string &Start) { string PathPart(Start); DeleteEndSlash(PathPart, true); return Path.IsSubStrAt(0, PathPart) && (Path.GetLength() == PathPart.GetLength() || IsSlash(Path[PathPart.GetLength()])); }
bool SearchString(const string& Source, const string& Str, string& ReplaceStr,int& CurPos, int Position,int Case,int WholeWords,int Reverse,int Regexp, int *SearchLength,const wchar_t* WordDiv) { int StrSize=StrLength(Source); *SearchLength = 0; if (!WordDiv) WordDiv=Global->Opt->strWordDiv; if (Reverse) { Position--; if (Position>=StrSize) Position=StrSize-1; if (Position<0) return false; } if ((Position<StrSize || (!Position && !StrSize)) && !Str.IsEmpty()) { if (Regexp) { string strSlash(Str); InsertRegexpQuote(strSlash); RegExp re; // Q: что важнее: опция диалога или опция RegExp`а? if (!re.Compile(strSlash, OP_PERLSTYLE|OP_OPTIMIZE|(!Case?OP_IGNORECASE:0))) return false; SMatch m[10*2], *pm = m; intptr_t n = re.GetBracketsCount(); if (n > static_cast<int>(ARRAYSIZE(m)/2)) { pm = (SMatch *)xf_malloc(2*n*sizeof(SMatch)); if (!pm) return false; } bool found = false; int half = 0; if (!Reverse) { if (re.SearchEx(Source,Source+Position,Source+StrSize,pm,n)) found = true; } else { int pos = 0; for (;;) { if (!re.SearchEx(Source,Source+pos,Source+StrSize,pm+half,n)) break; pos = static_cast<int>(pm[half].start); if (pos > Position) break; found = true; ++pos; half = n - half; } half = n - half; } if (found) { *SearchLength = pm[half].end - pm[half].start; CurPos = pm[half].start; ReplaceStr=ReplaceBrackets(Source,ReplaceStr,pm+half,n); } if (pm != m) xf_free(pm); return found; } if (Position==StrSize) return false; int Length = *SearchLength = (int)Str.GetLength(); for (int I=Position; (Reverse && I>=0) || (!Reverse && I<StrSize); Reverse ? I--:I++) { for (int J=0;; J++) { if (!Str[J]) { CurPos=I; return true; } if (WholeWords) { int locResultLeft=FALSE; int locResultRight=FALSE; wchar_t ChLeft=Source[I-1]; if (I>0) locResultLeft=(IsSpace(ChLeft) || wcschr(WordDiv,ChLeft)); else locResultLeft=TRUE; if (I+Length<StrSize) { wchar_t ChRight=Source[I+Length]; locResultRight=(IsSpace(ChRight) || wcschr(WordDiv,ChRight)); } else { locResultRight=TRUE; } if (!locResultLeft || !locResultRight) break; } wchar_t Ch=Source[I+J]; if (Case) { if (Ch!=Str[J]) break; } else { if (Upper(Ch)!=Upper(Str[J])) break; } } } } return false; }