/////////////////////////////////////////////////////////// // Gtinyd.CPP Demo program for gwin class in { gwtiny.h } /////////////////////////////////////////////////////////// /* In a small program used for mathematical tasks one would need to perform computations and plot graphs. Gtiny is a program that does just that. The computations are in the function num, and a graph is in the function plot. These two functions can easily be modified to perform similar new tasks which may be needed. A set of basic display and graphics functions are declared in gwtiny.h and defined in gwtiny.cpp. Typically one would start a new Win32 project, include the three files {gtiny.cpp, gtiny.rc, gwtiny.cpp}, build, and run. In cases where the set of basic functions in gwtiny is rich enough, one would simply copy {gtiny.h, gtiny.rc, gtiny.cpp} to a set with new names, say {myprog.h, myprog.rc, myprog.cpp}, and then make the modifications to suit the current task. At a later stage, new functions could be added to the class gwin in gwtiny. For example, one could add the function gwin::tics(int n1,int n2), which would put tics on a graph frame. Suggestion: get something very simple working smoothly before venturing off into the unknown. There are some more notes in the file gwtiny.cpp. gtinyd id gtiny with a simple data table added [Oct 2002] Richard Hall */ #include "gwtiny.h" #include "gtinyd.h" #include "gtinyd.rc" char prog[] = "Gtinyd" ; // -------------------------------------------------------------------------- void num(gwin &w); // program items void plot(gwin &w); // -------------------------------------------------------------------------- // simnple examples of external additions to gwtiny // when these are satisfactory, they can be added to class gwin void axes(gwin &w) { double x0 = w.getscale(1); double x1 = w.getscale(2); double y0 = w.getscale(3); double y1 = w.getscale(4); if ((y0 < 0)&&(y1 > 0)) // x axis { w.move(x0,0); w.line(x1,0); } if ((x0 < 0)&&(x1 > 0)) // y axis { w.move(0,y0); w.line(0,y1); } } // add scale list at bottom of graph void pscale1(gwin &w) { double x0 = w.getscale(1); double x1 = w.getscale(2); double y0 = w.getscale(3); double y1 = w.getscale(4); w.unclip(); double yp = y0 - (y1-y0)/10; w.pf(x0, yp,"[%3.2f,%3.2f,%3.2f,%3.2f]",x0,x1,y0,y1); w.clip(); } // add scale labels // more complicated code is required to suit all window sizes // this is tolerable for a large window void pscale(gwin &w, char *xs, char* ys) { double x0 = w.getscale(1); double x1 = w.getscale(2); double y0 = w.getscale(3); double y1 = w.getscale(4); int scan = w.getscan(); // convenient temporary scale w.scale(0,100,0,100,100); w.unclip(); w.pf(0,-10,"%3.2f", x0); w.pf(90,-10,"%3.2f", x1); w.p(45,-10,xs); w.pf(-10,0,"%3.2f",y0); w.pf(-10,98,"%3.2f",y1); w.p(-10,50,ys); // restore original scale w.scale(x0,x1,y0,y1,scan); w.clip(); } // -------------------------------------------------------------------- LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM); // Win32 // NB For Win16 replace the above line by the 2 lines below //LRESULT FAR PASCAL _export WndProc(HWND hWnd, UINT message, // Win16 // WPARAM wParam, LPARAM lParam); // Other function prototypes. LRESULT PerformMenuCommand(HWND hWnd, WPARAM wParam,gwin &w); BOOL CALLBACK DataDlgProc (HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam); // Global instance handle. HINSTANCE hInstance; // modeless dialogbox handle HWND hDlgDataBox; // --------------------------------------------------------------------------- // global data buffer int dataflag = 1; const int DATA_SIZE = 50; const int DN = 10; int DataID[DN] = {IDM_DATA0,IDM_DATA1,IDM_DATA2,IDM_DATA3,IDM_DATA4, IDM_DATA5,IDM_DATA6,IDM_DATA7,IDM_DATA8,IDM_DATA9}; // container class for data strings class DataBuffer { public: char *s; inline DataBuffer(char *si = NULL) { s = new char[DATA_SIZE+1]; strcpy(s,"0"); if (si != NULL) strcpy(s,si); } ~DataBuffer() { if (s != NULL) delete [] s; s = NULL; } }; // initial entried in array of DataBuffer static DataBuffer db[DN] = { DataBuffer("0.5"), DataBuffer("9"), DataBuffer("1"), DataBuffer("1"), DataBuffer("1"), DataBuffer("1"), DataBuffer("1"), DataBuffer("1"), DataBuffer("1"), DataBuffer("exp(-a x^2)cos(bx)"), }; // global parameters double a,b,c,d,e,h,k; int n,m; // conversion function data-strings --> parameters void setdata() { a = atof(db[0].s); b = atof(db[1].s); c = atof(db[2].s); d = atof(db[3].s); e = atof(db[4].s); h = atof(db[5].s); k = atof(db[6].s); n = atoi(db[7].s); m = atoi(db[8].s); } // ------------------------------------------------------------------ // Some demo functions (which use the global parameters) // To avoid global parameters, use objects derived from fun class double g(double x) // test functions for gwin::xplot { return exp(-x*x*a); } char gstr[80] = "g(x) = exp(-a x^2)cos(bx)"; double gm(double x) { return -g(x); } double f(double x) { return g(x)*cos(b*x); } // -------------------------------------------------------------- /////////////////////////////////////////////////////////// // WinMain /////////////////////////////////////////////////////////// int PASCAL WinMain(HINSTANCE hCurrentInst, HINSTANCE hPreviousInst, LPSTR /*lpszCmdLine */, int nCmdShow) { WNDCLASS wndClass; HWND hwnd; MSG msg; // If there's no previous instance of this application, // define and register the window class. if (hPreviousInst == NULL) { wndClass.style = CS_HREDRAW | CS_VREDRAW; wndClass.lpfnWndProc = WndProc; wndClass.cbClsExtra = 0; wndClass.cbWndExtra = 0; wndClass.hInstance = hCurrentInst; wndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION); wndClass.hCursor = LoadCursor(NULL, IDC_ARROW); wndClass.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH); wndClass.lpszMenuName = MAKEINTRESOURCE(MENU_1); wndClass.lpszClassName = prog; RegisterClass(&wndClass); } hInstance = hCurrentInst; // Get the size of the screen. UINT width = GetSystemMetrics(SM_CXSCREEN) / 2; UINT height = GetSystemMetrics(SM_CYSCREEN) / 2; // Create a window of the previously defined class. hwnd = CreateWindow( prog, // Window class's name. "Gtiny Application", // Title bar text. WS_OVERLAPPEDWINDOW, // The window's style. 10, // X position. 10, // Y position. width, // Width. height, // Height. NULL, // Parent window's handle. NULL, // Menu handle. hCurrentInst, // Instance handle. NULL); // No additional data. // Display the window on the screen. ShowWindow(hwnd, nCmdShow); // Force the window to repaint itself. UpdateWindow(hwnd); // Start the message loop. while (GetMessage(&msg, NULL, NULL, NULL)) { TranslateMessage(&msg); DispatchMessage(&msg); } return msg.wParam; } /////////////////////////////////////////////////////////// // WndProc() // // This is the main window procedure, which is called by // Windows. /////////////////////////////////////////////////////////// LRESULT CALLBACK WndProc (HWND hwnd, UINT message, // Win 32 WPARAM wParam, LPARAM lParam) // NB For Win16 replace the above 2 lines by the two lines below //LRESULT FAR PASCAL _export WndProc(HWND hwnd, UINT message, // WPARAM wParam, LPARAM lParam) { static gwin w(hwnd); // Handle the messages to which the application // must respond. switch(message) { case WM_COMMAND: return PerformMenuCommand(hwnd, wParam,w); case WM_DESTROY: PostQuitMessage(0); return 0; } // Make sure all unhandled messages get returned to Windows. return DefWindowProc(hwnd, message, wParam, lParam); } /////////////////////////////////////////////////////////// // PerformMenuCommand() /////////////////////////////////////////////////////////// LRESULT PerformMenuCommand(HWND hwnd, WPARAM wParam,gwin &w) { switch(wParam) { case CM_EXIT : close(hwnd); return 0 ; case CM_CLEAR : clear(hwnd); return 0; case IDM_DATA : if (dataflag == 1) // don't open more than once { dataflag = 0; hDlgDataBox = CreateDialog(hInstance,"DataBox",hwnd, (DLGPROC) DataDlgProc); } return 0 ; case CM_NUM : num(w); return 0; case CM_PLOT: plot(w); return 0; case CM_HELP : MessageBox (hwnd, "Num: Text\n\n\ Plot: Graphics\n\n\ Data: Parameters\n\n\n\ gtinyd v(0.91) (c) Richard Hall", "Help", MB_OK); return 0 ; } // end of switch return 0; } // ----------------------------------------------------------------------------- BOOL CALLBACK DataDlgProc (HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) { int i = 0; switch (message) { case WM_INITDIALOG : for (i = 0; i < DN; i++) SendDlgItemMessage(hDlg,DataID[i],WM_SETTEXT,0,(LPARAM) db[i].s); return TRUE ; case WM_COMMAND : switch (LOWORD (wParam)) { case IDM_DATAu : for (i = 0; i < DN; i++) GetDlgItemText(hDlg,DataID[i],db[i].s,DATA_SIZE); return TRUE; case IDCANCEL : dataflag = 1; // reset data flag EndDialog (hDlg, TRUE) ; return TRUE ; } break ; } return FALSE ; } // ------------------------------------------------------------------------ void num(gwin &w) { setdata(); w.open(); w.locate(10,90,10,90); w.preframe(); w.scale(0,10,15,0,100); w.p(1,1,"Hello World"); w.p(1,2,"This is my first program"); w.p(1,3,db[9].s); w.pf(1,4,"a = %8.4f b = %8.4f",a,b); double y = g(a); w.pf(1,5,"g(a) = g(%.6f) = %.6f",a,y); w.close(); } // ------------------------------------------------------------------ void plot(gwin &w) { setdata(); w.open(); w.locate(20,80,20,80); w.preframe(); w.scale(-3,3,-1.2,1.2,200); axes(w); pscale(w,"x","y"); // plot graphs w.xplot(g); w.xplot(gm); w.xplot(f); // label a graph double x = 0.5, y = g(x), d = 0.1; w.move(x,y); w.line(x+d,y+d); w.pf(x+d,y+2*d,"g(%.6g) = %.6g",x,y); // graph title w.scale(0,100,0,100,10); // % w.unclip(); w.p(5,110,db[9].s); char lab[80]; sprintf(lab,"a = %s b = %s",db[0].s,db[1].s); w.p(60,110,lab); w.clip(); w.close(); } // ------------------------------------------------------------------