|
#include <windows.h>
#include <sql.h>
#include <sqlext.h>
LRESULT CALLBACK WndProc(HWND,UINT,WPARAM,LPARAM);
HINSTANCE ebony_odbc;
HWND hWndMain;
LPSTR lpszClass="ebonyOdbcApi";
int APIENTRY WinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance
,LPSTR lpszCmdParam,int nCmdShow)
{
HWND hWnd;
MSG Message;
WNDCLASS WndClass;
ebony_odbc=hInstance;
WndClass.cbClsExtra=0;
WndClass.cbWndExtra=0;
WndClass.hbrBackground=(HBRUSH)GetStockObject(WHITE_BRUSH);
WndClass.hCursor=LoadCursor(NULL,IDC_ARROW);
WndClass.hIcon=LoadIcon(NULL,IDI_APPLICATION);
WndClass.hInstance=hInstance;
WndClass.lpfnWndProc=(WNDPROC)WndProc;
WndClass.lpszClassName=lpszClass;
WndClass.lpszMenuName=NULL;
WndClass.style=CS_HREDRAW | CS_VREDRAW;
RegisterClass(&WndClass);
hWnd=CreateWindow(lpszClass,lpszClass,WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,
NULL,(HMENU)NULL,hInstance,NULL);
ShowWindow(hWnd,nCmdShow);
hWndMain=hWnd;
while(GetMessage(&Message,0,0,0)) {
TranslateMessage(&Message);
DispatchMessage(&Message);
}
return Message.wParam;
}
void OdbcApi()
{
// 핸들
SQLHENV hEnv;
SQLHDBC hDbc;
SQLHSTMT hStmt;
// 연결 설정 변수들
SQLCHAR InCon[255];
SQLCHAR OutCon[255];
SQLSMALLINT cbOutCon;
char Dir[MAX_PATH];
// 쿼리질한 후 결과값을 돌려받기 변수들
SQLCHAR .....;
int ......;
BOOL ......;
SQLINTEGER ...... <---- 결과 값과는 별도로 하나씩 변수를 더 선언한다. =ㅅ=;;
등등............
// 화면 출력을 위한 변수들
int y=1;
HDC hdc;
int arTab[2]={200,400};
char str[255];
// 환경 핸들을 할당하고 버전 속성을 설정한다. <---- MDAC 버젼이 호환이 안되거나 야시꾸리한거 받으면 돌아버린다.
SQLAllocHandle(SQL_HANDLE_ENV,SQL_NULL_HANDLE,&hEnv);
SQLSetEnvAttr(hEnv,SQL_ATTR_ODBC_VERSION,(SQLPOINTER)SQL_OV_ODBC3,SQL_IS_INTEGER);
* 이 부분이 궁금이님이 에러나신 부분인데 헐 글쎄요 단순하게 버젼 체크하고 핸들설정하는 부분이네여
헐 저도 기억이 가물가물~ 잘 살펴보세여 =ㅅ=;;
// 연결 핸들을 할당하고 연결한다.
SQLAllocHandle(SQL_HANDLE_DBC,hEnv,&hDbc);
GetCurrentDirectory(MAX_PATH,Dir);
wsprintf((char *)InCon,"DRIVER={Microsoft Access Driver (*.mdb)};"
"DBQ=C:\\ebony.mdb;",Dir); <-- 제 faq 에서 연결스트링이랑 비슷하져?
SQLDriverConnect(hDbc,hWndMain,InCon,sizeof(InCon),OutCon,
sizeof(OutCon), &cbOutCon, SQL_DRIVER_NOPROMPT);
// 명령 핸들을 할당한다.
SQLAllocHandle(SQL_HANDLE_STMT,hDbc,&hStmt);
// 결과를 돌려받기 위해 바인딩한다.
SQLBindCol(hStmt,1,SQL_C_CHAR, 결과값 변수1,sizeof(변수1),변수1의 SQLINTEGER 형의 주소형);
SQLBindCol(hStmt,2,SQL_C_ULONG,결과값 변수2,0,변수2의 SQLINTEGER 형의 주소형);
SQLBindCol(hStmt,3,SQL_C_ULONG,결과값 변수3,0,&변수3의 SQLINTEGER 형의 주소형);
/***1,2,3 은 주소형....
예를들어 SQLCHAR a1; 이라고 선언햇스면 SQLINTEGER la1; 이라고 선언된게 잇섯져.
그러면 아래와 같이 써줌니다.
SQLBindCol(hStmt,1,SQL_C_CHAR, a1,sizeof(a1),&la1);
// SQL문을 실행한다.
SQLExecDirect(hStmt,(SQLCHAR *)"select * from bbs",SQL_NTS);
헐 이 함수 하나로 쿼리질은 다 됨다.
// 읽어온 데이터 출력
hdc=GetDC(hWndMain);
while(SQLFetch(hStmt)!=SQL_NO_DATA) {
wsprintf(str, "...",..,~);
TabbedTextOut(hdc,10,y*20,str,strlen(str),2,arTab,0);
y++;
};
ReleaseDC(hWndMain,hdc);
// 뒷정리
SQLCloseCursor(hStmt);
SQLFreeHandle(SQL_HANDLE_STMT,hStmt);
SQLDisconnect(hDbc);
SQLFreeHandle(SQL_HANDLE_DBC,hDbc);
SQLFreeHandle(SQL_HANDLE_ENV,hEnv);
}
LRESULT CALLBACK WndProc(HWND hWnd,UINT iMessage,WPARAM wParam,LPARAM lParam)
{
switch(iMessage) {
case WM_LBUTTONDOWN:
OdbcApi();
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return(DefWindowProc(hWnd,iMessage,wParam,lParam));
}
안녕하세요 에보니입니다. =ㅅ=;;
궁금이님이 메일로 저에게 물엇던 부분인데 사실 이런걸 권장해 드리고 싶은 생각은 죽어도 없슴다.
사실 위에게 머하는 소스냐 하면 단순히 odbc 로 액세스를 연결해 쿼리질 한번하는 VC++ 의 노가다입니다.
그것도 그리드가 아니라...
저거한번 치다간 돌아버립니다. 미친짓이져.. 빌더가 얼마나 좋은지 알수있져?
빌더많이 쓰라니깐.....
OdbcApi 함수가 디비 커넥에서 쿼리질하는 부분이니깐 참고해서 보세요.
혹 빌더에서도 이런짓을 하실 분이 계시다면 말리지 않겟슴다. =ㅅ=;;
나머진 VC++ 하신분이나 윈도우즈 프로그래밍 책을 잘 본 사람이라면 이해할 수 있슬거에여..
자 그럼...
p.s.
예전에 아폴로라는 디비 기생충이 잇섯는데.... 아마 그넘은 아무 디비나 잘 기붙기로 유명햇서여...
odbc api 를 어떻게 컴포넌트화 시킨것이 아니엇슬까 생각한적이 있었는데여.... 음 잘모르고 넘어가서 아
쉬운적이 잇섯는데.... 근데 요즘 같이 oledb가 창궐하는 시점에서 odbc가 헐...
음 열심히 공부해서 비디이를 능가하는 디비엔진이나 컴포넌트를 하나 만들순 업슬까 =ㅅ=;;
이상 미친 생각을 함 해본 에보니입니다.
|