/*! クリップボードに変更があった場合の処理・自分からの変更に反応しないようにせにゃ @param[in] hWnd ウインドウハンドル・使わないか @return HRESULT 終了状態コード */ HRESULT ClipStealDoing( HWND hWnd ) { LPTSTR ptTexts; LPSTR pcStrs; CHAR acBuffer[MAX_STRING]; TCHAR atMsg[MAX_STRING]; UINT_PTR cbSize, cbSplSz; DWORD wrote; HANDLE hFile; SYSTEMTIME stTime; // 保存するファイル指定が無いならナニもしない if( NULL == gatClipFile[0] ){ return E_NOTIMPL; } // クリップスティール機能有効? if( !(gbClipSteal) ){ return S_FALSE; } ptTexts = ClipboardDataGet( NULL ); if( !(ptTexts) ){ return E_ACCESSDENIED; } // クリップされたのが文字列ではなかったら直ぐ終わる // SJIS型に変換 pcStrs = SjisEncodeAlloc( ptTexts ); StringCchLengthA( pcStrs, STRSAFE_MAX_CCH, &cbSize ); // ゲットしたコピペ文字列の保存処理 hFile = CreateFile( gatClipFile, GENERIC_WRITE, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL ); if( INVALID_HANDLE_VALUE != hFile ) { SetFilePointer( hFile, 0, NULL, FILE_END ); if( gIsAST ) { GetLocalTime( &stTime ); StringCchPrintfA( acBuffer, MAX_STRING, ("[AA][%04u/%02u/%02u %02u:%02u:%02u]\r\n"), stTime.wYear, stTime.wMonth, stTime.wDay, stTime.wHour, stTime.wMinute, stTime.wSecond ); StringCchLengthA( acBuffer, MAX_STRING, &cbSplSz ); WriteFile( hFile, acBuffer, cbSplSz, &wrote, NULL ); } WriteFile( hFile, pcStrs, cbSize, &wrote, NULL ); if( gIsAST ){ StringCchCopyA( acBuffer, MAX_STRING, ("\r\n") ); } else{ StringCchCopyA( acBuffer, MAX_STRING, ("\r\n[SPLIT]\r\n") ); } StringCchLengthA( acBuffer, MAX_STRING, &cbSplSz ); WriteFile( hFile, acBuffer, cbSplSz, &wrote, NULL ); SetEndOfFile( hFile ); CloseHandle( hFile ); } FREE( ptTexts ); FREE( pcStrs ); // 保存したメッセージが必要 if( gGetMsgOn ) { StringCchPrintf( atMsg, MAX_STRING, TEXT("%u Byte 取得"), cbSize ); TaskTrayIconBalloon( hWnd, TEXT("コピーされた文字列を保存したよ。"), atMsg, 1 ); } return S_OK; }
/*! 指定されたページ全体をプレビュー用にSJISで確保する・freeは呼んだ方でやる @param[in] iPage ターゲット頁番号 @param[out] pdBytes 確保したバイト数返す・NULLターミネータも含む @return 確保した領域・SJIS文字列である */ LPSTR DocPageTextPreviewAlloc( INT iPage, PINT pdBytes ) { // SJISの場合は、ユニコード文字は&#dddd;で確保される UINT_PTR iLines, i, iLetters; INT_PTR iSize; LPSTR pcText = NULL; CHAR acEntity[10]; string srString; // シフトJISで確保 LINE_ITR itLine, itLineEnd; LETR_ITR itLtr; TCHAR atEntity[10]; wstring widString; LPTSTR ptCaret; srString.clear( ); if( pdBytes ) *pdBytes = 0; if( DocRangeIsError( gitFileIt, iPage, 0 ) ) return NULL; widString.clear(); if( (*gitFileIt).vcCont.at( iPage ).ptRawData ) // 生データ状態なら { ptCaret = (*gitFileIt).vcCont.at( iPage ).ptRawData; StringCchLength( ptCaret, STRSAFE_MAX_CCH, &iLetters ); for( i = 0; iLetters > i; i++ ) { if( HtmlEntityCheckW( ptCaret[i], atEntity, 10 ) ) { widString += wstring( atEntity ); } else if( TEXT('\r') == ptCaret[i] ) { widString += wstring( TEXT("<br>") ); i++; // 0x0A分進める } else { widString += ptCaret[i]; } } widString += wstring( TEXT("<br>") ); // 末尾に改行あっておk? pcText = SjisEncodeAlloc( widString.c_str() ); // Preview用 iSize = strlen( pcText ); } else { // ページ全体の行数 iLines = (*gitFileIt).vcCont.at( iPage ).ltPage.size( ); itLine = (*gitFileIt).vcCont.at( iPage ).ltPage.begin( ); itLineEnd = (*gitFileIt).vcCont.at( iPage ).ltPage.end( ); for( i = 0; itLine != itLineEnd; i++, itLine++ ) { // 各行の文字数 iLetters = itLine->vcLine.size( ); for( itLtr = itLine->vcLine.begin(); itLtr != itLine->vcLine.end(); itLtr++ ) { // HTML的にヤバイ文字をエンティティする if( HtmlEntityCheckA( itLtr->cchMozi, acEntity, 10 ) ) { srString += string( acEntity ); } else { srString += string( itLtr->acSjis ); } } //全行に改行あってかまわない? srString += string( "<br>" ); } iSize = srString.size( ) + 1; // NULLターミネータ分足す pcText = (LPSTR)malloc( iSize ); ZeroMemory( pcText, iSize ); StringCchCopyA( pcText, iSize, srString.c_str( ) ); } if( pdBytes ) *pdBytes = iSize; return pcText; }
/*! ページ全体を確保する・freeは呼んだ方でやる @param[in] bStyle 1ユニコードかシフトJIS @param[out] *pText 確保した領域を返す・ワイド文字かマルチ文字になる・NULLだと必要バイト数を返すのみ @return 確保したバイト数・NULLターミネータも含む */ INT DocPageTextAllGetAlloc( UINT bStyle, LPVOID *pText ) { // SJISの場合は、ユニコード文字は&#dddd;で確保される UINT_PTR iLines, i, iLetters, j; UINT_PTR cchSize; INT_PTR iSize; LPTSTR ptData; LPSTR pcStr; string srString; // ユニコード・シフトJISで確保 wstring wsString; LINE_ITR itLine; srString.clear( ); wsString.clear( ); if( gitFileIt->vcCont.at( gixFocusPage ).ptRawData ) // 生データ状態なら { ptData = (*gitFileIt).vcCont.at( gixFocusPage ).ptRawData; StringCchLength( ptData, STRSAFE_MAX_CCH, &cchSize ); if( bStyle & D_UNI ) // ユニコードである { iSize = (cchSize+1) * sizeof(TCHAR); // NULLターミネータ分足す if( pText ) { *pText = (LPTSTR)malloc( iSize ); ZeroMemory( *pText, iSize ); StringCchCopy( (LPTSTR)(*pText), cchSize, ptData ); } } else { pcStr = SjisEncodeAlloc( ptData ); if( pcStr ) { StringCchLengthA( pcStr, STRSAFE_MAX_CCH, &cchSize ); iSize = cchSize + 1; // NULLターミネータ分足す if( pText ){ *pText = pcStr; } else{ FREE( pcStr ); } } } } else { // ページ全体の行数 iLines = DocNowFilePageLineCount( ); itLine = (*gitFileIt).vcCont.at( gixFocusPage ).ltPage.begin(); for( i = 0; iLines > i; i++, itLine++ ) { // 各行の文字数 iLetters = itLine->vcLine.size( ); if( bStyle & D_UNI ) { for( j = 0; iLetters > j; j++ ) { wsString += itLine->vcLine.at( j ).cchMozi; } if( iLines > (i+1) ) wsString += wstring( CH_CRLFW ); } else { for( j = 0; iLetters > j; j++ ) { srString += string( itLine->vcLine.at( j ).acSjis ); } if( iLines > (i+1) ) srString += string( CH_CRLFA ); } } if( bStyle & D_UNI ) // ユニコードである { cchSize = wsString.size( ) + 1; // NULLターミネータ分足す iSize = cchSize * sizeof(TCHAR); // ユニコードなのでバイト数は2倍である if( pText ) { *pText = (LPTSTR)malloc( iSize ); ZeroMemory( *pText, iSize ); StringCchCopy( (LPTSTR)(*pText), cchSize, wsString.c_str( ) ); } } else { iSize = srString.size( ) + 1; // NULLターミネータ分足す if( pText ) { *pText = (LPSTR)malloc( iSize ); ZeroMemory( *pText, iSize ); StringCchCopyA( (LPSTR)(*pText), iSize, srString.c_str( ) ); } } } return iSize; }
/*! ページ全体を文字列で確保する・freeは呼んだ方でやる @param[in] itFile 確保するファイル @param[in] dPage 確保する頁番号 @param[in] bStyle 1ユニコードかシフトJISで、矩形かどうか @param[out] pText 確保した領域を返す・ワイド文字かマルチ文字になる・NULLだと必要バイト数を返すのみ @param[in] bCrLf 末端に改行付けるか @return 確保したバイト数・NULLターミネータ含む */ INT DocPageTextGetAlloc( FILES_ITR itFile, INT dPage, UINT bStyle, LPVOID *pText, BOOLEAN bCrLf ) { UINT_PTR iLines, iLetters, j, iSize; UINT_PTR i; UINT_PTR cchSize; LPSTR pcStr; string srString; wstring wsString; LINE_ITR itLines; #ifdef DO_TRY_CATCH try{ #endif srString.clear( ); wsString.clear( ); // デフォ的な if( 0 > dPage ){ dPage = gixFocusPage; } if( itFile->vcCont.at( dPage ).ptRawData ) // 生データ状態なら { if( bStyle & D_UNI ) // ユニコードである { wsString = wstring( itFile->vcCont.at( dPage ).ptRawData ); if( bCrLf ){ wsString += wstring( CH_CRLFW ); } } else // ShiftJISである { pcStr = SjisEncodeAlloc( itFile->vcCont.at( dPage ).ptRawData ); // ページ全体を文字列で確保 if( pcStr ) { srString = string( pcStr ); if( bCrLf ){ srString += string( CH_CRLFA ); } FREE( pcStr ); } } } else // ロード済みなら { // 全文字を頂く iLines = itFile->vcCont.at( dPage ).ltPage.size( ); for( itLines = itFile->vcCont.at( dPage ).ltPage.begin(), i = 0; itLines != itFile->vcCont.at( dPage ).ltPage.end(); itLines++, i++ ) { iLetters = itLines->vcLine.size( ); for( j = 0; iLetters > j; j++ ) { srString += string( itLines->vcLine.at( j ).acSjis ); wsString += itLines->vcLine.at( j ).cchMozi; } if( !(1 == iLines && 0 == iLetters) ) // 壱行かつ零文字は空である { if( iLines > (i+1) ) // とりあえずファイル末端改行はここでは付けない { srString += string( CH_CRLFA ); wsString += wstring( CH_CRLFW ); } } } if( bCrLf ) { srString += string( CH_CRLFA ); wsString += wstring( CH_CRLFW ); } } if( bStyle & D_UNI ) { cchSize = wsString.size( ) + 1; // NULLターミネータ iSize = cchSize * sizeof(TCHAR); // ユニコードなのでバイト数は2倍である if( pText ) { *pText = (LPTSTR)malloc( iSize ); ZeroMemory( *pText, iSize ); StringCchCopy( (LPTSTR)(*pText), cchSize, wsString.c_str( ) ); } } else { iSize = srString.size( ) + 1; // NULLターミネータ if( pText ) { *pText = (LPSTR)malloc( iSize ); ZeroMemory( *pText, iSize ); StringCchCopyA( (LPSTR)(*pText), iSize, srString.c_str( ) ); } } #ifdef DO_TRY_CATCH } catch( exception &err ){ return (INT)ETC_MSG( err.what(), 0 ); } catch( ... ){ return (INT)ETC_MSG( ("etc error") , 0 ); } #endif return (INT)iSize; }
/*! 編集の選択範囲からいただく @param[in] hWnd ウインドウハンドル @param[in] bSqSel 矩形であるかどうか */ UINT DraughtItemAddFromSelect( HWND hWnd, UINT bSqSel ) { LPTSTR ptString = NULL; UINT cchSize, cbSize; LPPOINT pstPos = NULL; UINT_PTR i, j, iTexts; LONG dMin = 0; INT insDot, yLine, iLines = 0, dOffset; LPTSTR ptSpace = NULL; LPSTR pcArts; wstring wsString; // 内部処理なのでUnicode固定 cbSize = DocSelectTextGetAlloc( D_UNI | bSqSel, (LPVOID *)(&ptString), (bSqSel & D_SQUARE) ? &pstPos : NULL ); StringCchLength( ptString, STRSAFE_MAX_CCH, &cchSize ); if( 0 >= cchSize ) return 0; // 文字列ないならなにもしない // オフセット設定が有る場合、その分を埋める空白が必要 if( pstPos ) // 最小オフセット値を探して、そこを左端にする { dMin = pstPos[0].x; yLine = 0; for( i = 0; cchSize > i; i++ ) { if( CC_CR == ptString[i] && CC_LF == ptString[i+1] ) // 改行であったら { // オフセット最小をさがす if( dMin > pstPos[yLine].x ){ dMin = pstPos[yLine].x; } i++; // 0x0D,0x0Aだから、壱文字飛ばすのがポイント yLine++; // 改行したからFocusは次の行へ } } // この時点で、yLineは行数になってる iLines = yLine; // 壱行目の空白を作って閃光入力しておく insDot = 0; dOffset = pstPos[0].x - dMin; ptSpace = DocPaddingSpaceUni( dOffset, NULL, NULL, NULL ); // 前方空白は無視されるのでユニコード使って問題無い StringCchLength( ptSpace, STRSAFE_MAX_CCH, &iTexts ); for( j = 0; iTexts > j; j++ ){ wsString += ptSpace[j]; } FREE(ptSpace); } yLine = 0; insDot = 0; for( i = 0; cchSize > i; i++ ) { if( CC_CR == ptString[i] && CC_LF == ptString[i+1] ) // 改行であったら { wsString += wstring( TEXT("\r\n") ); i++; // 0x0D,0x0Aだから、壱文字飛ばすのがポイント yLine++; // 改行したからFocusは次の行へ // オフセット分の空白を作る if( pstPos && (iLines > yLine) ) { dOffset = pstPos[yLine].x - dMin; ptSpace = DocPaddingSpaceUni( dOffset, NULL, NULL, NULL ); // 前方空白は無視されるのでユニコード使って問題無い StringCchLength( ptSpace, STRSAFE_MAX_CCH, &iTexts ); for( j = 0; iTexts > j; j++ ){ wsString += ptSpace[j]; } FREE(ptSpace); } } else if( CC_TAB == ptString[i] ){ /* タブは挿入しない */ } else{ wsString += ptString[i]; } } FREE(ptString); FREE(pstPos); pcArts = SjisEncodeAlloc( wsString.c_str() ); DraughtItemAdding( hWnd, pcArts ); FREE(pcArts); return yLine; }
/*! ツリーのファイルにアイテム追加・追加したいファイルのパスを受け取る @param[in] hWnd ウインドウハンドル @param[in] ptFile 追加したいファイルのフルパス */ HRESULT AacItemAdding( HWND hWnd, LPTSTR ptFile ) { HANDLE hFile; LPTSTR ptBuffer;//, ptExten; LPSTR pcOutput; // TCHAR atExBuf[10]; CHAR acCheck[6]; DWORD readed, wrote; UINT_PTR cchSize, cchSep, cbSize; ITEMADDINFO stIaInfo; ZeroMemory( &stIaInfo, sizeof(ITEMADDINFO) ); ZeroMemory( acCheck, sizeof(acCheck) ); // 拡張子確認 if( FileExtensionCheck( ptFile, TEXT(".ast") ) ){ stIaInfo.bType = 0; } else{ stIaInfo.bType = 1; } if( DialogBoxParam( GetModuleHandle(NULL), MAKEINTRESOURCE(IDD_MAA_IADD_DLG), hWnd, AaItemAddDlgProc, (LPARAM)(&stIaInfo) ) ) { if( stIaInfo.ptContent ) // 中身が有効なら処理する { hFile = CreateFile( ptFile, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL ); if( INVALID_HANDLE_VALUE != hFile ) { // ファイルはSJIS型であると見なす SetFilePointer( hFile, -2, NULL, FILE_END ); // 末尾の状況を確認 ReadFile( hFile, acCheck, 6, &readed, NULL ); // この時点でファイル末尾にくる SetFilePointer( hFile, 0, NULL, FILE_END ); // 念のため末尾 if( acCheck[0] != '\r' || acCheck[1] != '\n' ) // 末尾が改行じゃなかったら { acCheck[0] = '\r'; acCheck[1] = '\n'; acCheck[2] = NULL; WriteFile( hFile, acCheck, 2, &wrote, NULL ); // 改行書いておく } StringCchLength( stIaInfo.atSep, MAX_PATH, &cchSep ); StringCchLength( stIaInfo.ptContent, STRSAFE_MAX_CCH, &cchSize ); cchSize += (cchSep+6); ptBuffer = (LPTSTR)malloc( cchSize * sizeof(TCHAR) ); ZeroMemory( ptBuffer, cchSize * sizeof(TCHAR) ); StringCchPrintf( ptBuffer, cchSize, TEXT("%s%s\r\n"), stIaInfo.atSep, stIaInfo.ptContent ); pcOutput = SjisEncodeAlloc( ptBuffer ); cbSize = strlen( pcOutput ); WriteFile( hFile , pcOutput, cbSize, &wrote, NULL ); // 内容書き込む SetEndOfFile( hFile ); CloseHandle( hFile ); } FREE(stIaInfo.ptContent); } // もしメインで開けていたらロード・ていうかツリー側で追加っておかしくね? } return S_OK; }