取得執行檔的完整路徑
String name = Application->ExeName;
//C:\\Borland\\CBuilder6\\Projects\\Project1.exe
取出檔案名稱
name = ExtractFileName(name);
// Project1.exe
改變副檔名
name = ChangeFileExt(name,".TXT");
//Project1.TXT
取出路徑(含斜線, 不支援反斜線)
name = ExtractFilePath(Application->ExeName);
//C:\Borland\CBuilder6\Projects\
取出路徑(不含斜線, 不支援反斜線)
name = ExtractFileDir(Application->ExeName);
//C:\Borland\CBuilder6\Projects
取出目錄名稱(在linux永遠是空白)
name = ExtractFileDrive(Application->ExeName);
//C:
取出副檔名
name = ExtractFileExt(Application->ExeName);
//.exe
2015年8月20日 星期四
2015年8月17日 星期一
使用command line 來編譯bcb的專案檔
BCB6 可以使用 BCB.exe -m Project.bpr 來編譯執行檔
不過使用這樣的編譯方式在編譯之前會喚起BCB的IDE介面
如果只是單純想編譯程式可以透過MAKE FILE的方式
在BCB3 與BCB4 的時候.bpr檔就是一個makefile文件
自從BCB5 之後 .bpr檔變成了 xml檔案
如果想要 makefile文件的話
可以透過工具程式 bpr2mak.exe Project.mak Project.bpr
來產生 Project.mak
之後再透過指令 make -f Project.mak
就可以編譯檔案了
不過使用這樣的編譯方式在編譯之前會喚起BCB的IDE介面
如果只是單純想編譯程式可以透過MAKE FILE的方式
在BCB3 與BCB4 的時候.bpr檔就是一個makefile文件
自從BCB5 之後 .bpr檔變成了 xml檔案
如果想要 makefile文件的話
可以透過工具程式 bpr2mak.exe Project.mak Project.bpr
來產生 Project.mak
之後再透過指令 make -f Project.mak
就可以編譯檔案了
2015年4月13日 星期一
BCB6 發生 E2015 Ambiguity between 'PLongint' and 'System::Plongint' 錯誤
參考 http://support.embarcadero.com/article/34594 的作法
將Psock.hpp 中的 typedef int *PLongint;註解掉就好了
BCB6.0 使用indy10
1. 首先使用 Administrator 安裝
2. 移除BCB6原來使用的Indy
2.1 放入安裝光碟
2.2 選擇 Modify 後按 Next
2.3 在 Custom Setup 中 選擇 Program Files/Indy 選 Do not Install
2.4 接著就是下一步到結束
3. 安裝新的 Indy
3.1 先開啟BCB6, 這時會發生連結不到 Indy Lib的訊息, 選Yes
3.2 在 Tools/Environment Options/Library Path 中加入Indy的路徑
3.3 在 Project/Options/Packages 加入 dclIndyCore60.bpl 與 dclIndyProtocols60.bpl
3.4 切換到 Directories/Conditionals TAB 在 Include Path 與 Library Path 加入 Indy的目錄(放到第一個)
3.5 記得左下角的 Default要打勾
關閉後重開如果出現找不到 IndySystem60.bpl的訊息, 先按yes 跳過
之後將IndySystem60.bpl, IndyProtocols60.bpl, IndyCore60.bpl放到c:\windows\system32的目錄下
2. 移除BCB6原來使用的Indy
2.1 放入安裝光碟
2.2 選擇 Modify 後按 Next
2.3 在 Custom Setup 中 選擇 Program Files/Indy 選 Do not Install
2.4 接著就是下一步到結束
3. 安裝新的 Indy
3.1 先開啟BCB6, 這時會發生連結不到 Indy Lib的訊息, 選Yes
3.2 在 Tools/Environment Options/Library Path 中加入Indy的路徑
3.3 在 Project/Options/Packages 加入 dclIndyCore60.bpl 與 dclIndyProtocols60.bpl
3.4 切換到 Directories/Conditionals TAB 在 Include Path 與 Library Path 加入 Indy的目錄(放到第一個)
3.5 記得左下角的 Default要打勾
關閉後重開如果出現找不到 IndySystem60.bpl的訊息, 先按yes 跳過
之後將IndySystem60.bpl, IndyProtocols60.bpl, IndyCore60.bpl放到c:\windows\system32的目錄下
2015年3月24日 星期二
BCB 上使用 GdiPlus (一)
在BCB上如果要使用 Gdi+ 來繪圖必須要先做下面六件事情
1. include
2. using namespace Gdiplus;
3. 宣告全域變數 GdiplusStartupInput m_gdiplusStartupInput;
unsigned long m_pGdiToken;
4. 使用前要先呼叫 GdiplusStartup(&m_pGdiToken,&m_gdiplusStartupInput,NULL);
5. 結束的時候呼叫 GdiplusShutdown(m_pGdiToken);
6. 將Gdiplus.lib加入專案
此方法使用靜態鏈結到gdiplus.dll
所以要確認系統有沒有這個檔案, 如果沒有就需要到微軟官網下載.
再使用bcb附的工具程式implib.exe 產生lib檔
implib gdiplus.lib gdiplus.dll
2014年9月25日 星期四
取得作業系統版本資訊
利用WINDOWS API 取得相關資訊
可以參考 GetVersionEx() function
得到的結構參考 OSVERSIONINFOEX
這次是為了取得是否是 Win7 以上的版本
相關的Code如下
bool IsWindows7OrGreater()
{
OSVERSIONINFO info;
GetVersionEx(&info);
return info.dwMajorVersion>=6;
}
可以參考 GetVersionEx() function
得到的結構參考 OSVERSIONINFOEX
這次是為了取得是否是 Win7 以上的版本
相關的Code如下
bool IsWindows7OrGreater()
{
OSVERSIONINFO info;
GetVersionEx(&info);
return info.dwMajorVersion>=6;
}
2014年5月22日 星期四
2014年4月14日 星期一
Services程式與一般程式之間共享資訊
主要是透過Share Memory的方式建立可以共同存取的記憶體
這樣A可以寫入資訊讓B去讀取, 彼此溝通
Process A:
Process B:
特別要注意的是紅色部分是 Service 要加入的部分, 透過這樣設定DACL授予普通用戶讀取權限的記憶體共享, 如果需要寫入的話, 要將 GR改成GWGR, 只是, 請注意, 這樣是不安全的!!
參考網頁:
http://msdn.microsoft.com/en-us/library/windows/desktop/aa366551(v=vs.85).aspx
http://stackoverflow.com/questions/898683/how-to-share-memory-between-services-and-user-processes
http://msdn.microsoft.com/en-us/library/windows/desktop/aa376401(v=vs.85).aspx
這樣A可以寫入資訊讓B去讀取, 彼此溝通
Process A:
HANDLE hFile;
char writeBuffer[128]={0};
LPCTSTR pBuf;
char szFileName[]="Global\\Test";
SECURITY_ATTRIBUTES security;
ZeroMemory(&security, sizeof(security));
security.nLength = sizeof(security);
ConvertStringSecurityDescriptorToSecurityDescriptor(
"D:P(A;OICI;GA;;;SY)(A;OICI;GA;;;BA)(A;OICI;GR;;;IU)",
SDDL_REVISION_1, &security.lpSecurityDescriptor,NULL);
hFile = CreateFileMapping((HANDLE)0xFFFFFFFF,&security,PAGE_READWRITE,0,sizeof(writeBuffer),szFileName );
pBuf = (LPCTSTR)MapViewOfFile(hFile,FILE_MAP_ALL_ACCESS,0,0,sizeof(writeBuffer));
strcat((char*)pBuf,"This is a Share Memory!!");
CloseHandle(hFile);Process B:
char szFileName[]="Global\\Test";
Char writeBuffer[128]={0};
LPCTSTR pBuf;
HANDLE hFile;
hFile = OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, szFileName);
pBuf=(LPCTSTR)MapViewOfFile(hFile,FILE_MAP_ALL_ACCESS,0,0,sizeof(writeBuffer));
if(strlen(pBuf))
Edit1->Text = pBuf;
CloseHandle(hFile);特別要注意的是紅色部分是 Service 要加入的部分, 透過這樣設定DACL授予普通用戶讀取權限的記憶體共享, 如果需要寫入的話, 要將 GR改成GWGR, 只是, 請注意, 這樣是不安全的!!
參考網頁:
http://msdn.microsoft.com/en-us/library/windows/desktop/aa366551(v=vs.85).aspx
http://stackoverflow.com/questions/898683/how-to-share-memory-between-services-and-user-processes
http://msdn.microsoft.com/en-us/library/windows/desktop/aa376401(v=vs.85).aspx
2014年2月17日 星期一
BCB6 Warring W8058 Cannot create pre-compiled header: write failed
出現這個問題的時候是因為
Option-》Compiler-》Pre-compiled Headers 下面的FileName 設定路徑不存在
Option-》Compiler-》Pre-compiled Headers 下面的FileName 設定路徑不存在
2013年12月1日 星期日
BCB 編譯的時候出現 Unresolved external ThrowIfOutOfRange Error
最近在編譯一個就的程式的時候出現了一個 Linker Error
Unresolved external '__stdcall System::AnsiString::ThrowIfOutOfRange(int) const'
仔細的去查了程式碼發現問題發生的原因是在程式中使用了
AnsiString 的 operator[]
在網路上找了幾天之後發現這個問題從BCB5就存在
解決的方法是
1. 在option -> Advanced Compiler -> Calling convention 改用 C
或是
2. 直接修改dstring.h
我的檔案是位在$(BCB)\Include\Vcl\dstring.h (208行)
將void ThrowIfOutOfRange(int idx) const;改成
void __cdecl ThrowIfOutOfRange(int idx) const;
Unresolved external '__stdcall System::AnsiString::ThrowIfOutOfRange(int) const'
仔細的去查了程式碼發現問題發生的原因是在程式中使用了
AnsiString 的 operator[]
在網路上找了幾天之後發現這個問題從BCB5就存在
解決的方法是
1. 在option -> Advanced Compiler -> Calling convention 改用 C
或是
2. 直接修改dstring.h
我的檔案是位在$(BCB)\Include\Vcl\dstring.h (208行)
將void ThrowIfOutOfRange(int idx) const;改成
void __cdecl ThrowIfOutOfRange(int idx) const;
2012年9月14日 星期五
BCB 使用OpenDialog時無法設定初始目錄
最近使用 BCB 的 OpenDialog 寫一個選取檔案的程式
OpenDialog1->InitialDir=ExtractFileDir(Application->ExeName);
才發現一直無法設定程式所在的目錄為開啟的預設目錄
會一直停留在上一次取檔的目錄
而且程式重啟也是會記得
在網路上程式的解法都是
1. OpenDialog1->Options->ofNoChangeDir = true
2. Execute 完 Dialog 後, 要把 FileName 清空
(有試過在設定InitialDir之前清除也可以)
後來發現其實有一個重點
應該是使用ExtractFileDir之後要接反斜線
OpenDialog1->InitialDir=ExtractFileDir(Application->ExeName)+"\\";
這樣就不用清空FileName
我猜是因為判定不是目錄的原因才會有問題
OpenDialog1->InitialDir=ExtractFileDir(Application->ExeName);
才發現一直無法設定程式所在的目錄為開啟的預設目錄
會一直停留在上一次取檔的目錄
而且程式重啟也是會記得
在網路上程式的解法都是
1. OpenDialog1->Options->ofNoChangeDir = true
2. Execute 完 Dialog 後, 要把 FileName 清空
(有試過在設定InitialDir之前清除也可以)
後來發現其實有一個重點
應該是使用ExtractFileDir之後要接反斜線
OpenDialog1->InitialDir=ExtractFileDir(Application->ExeName)+"\\";
這樣就不用清空FileName
我猜是因為判定不是目錄的原因才會有問題
訂閱:
文章 (Atom)
