--------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00113 Date: 04/27/98 From: ADAM MAJER Time: 07:31pm \/To: MATT SARNECKY (Read 3 times) Subj: Need borland help fast! MS>I am using Borland Turbo C++ 4.5 for Windows. (Which is compatible with MS>Borland C++ 4.02) and I created an application called lworks that uses WCC MS>controls. I have a dialog box called IDCDLGCLIENT which is a resource for th Post the function that is trubling you. I'll try to help. * SLMR 2.1a * I'm in shape ... round's a shape isn't it? --- FMail 0.92 * Origin: The Programmer's Oasis on FIDONET! (1:348/203) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00114 Date: 04/28/98 From: KURT KUZBA Time: 01:13am \/To: MARK HOOVER (Read 3 times) Subj: Interrupt Based Programmi MH> KK> ODOOR or RS232. Either is available as source for a fee. MH> Know where to find them? http://www.filepile.com > ] Yoda I am, of Borg. Assimilated you will be, hmmm???........ --- * Origin: *YOPS ]I[* 8.4 GIG * RA/FD/FE * Milwaukee, WI (1:154/750) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00115 Date: 04/28/98 From: KURT KUZBA Time: 01:13am \/To: GLEN OLDENHUIS (Read 3 times) Subj: vesatest.cpp 1/3 GO> activate 256 colors? C++ code for activating VESA modes 101h and 103h in Borland. This is not optimized for speed. It is set out as an example of the general method for using these modes. I don't know about 1024x1024x16M, having never attempted it, but if you have a list of VESA modes, you could add it. Handling the pixels would not be as simple as with 256 colors, of course, but a 24-bit color depth would be 3 bytes per pixel. Unless you want to use photographic quality graphics, 256 colors should be all that you need, really. Try the PC Game Programmer's Encyclopedia. [ PCGPE ] /*_|_| VESATEST.CPP PUBLIC DOMAIN PART 1 OF 3 _|_|_| Example of using 800x600 and 640x480 VESA modes. _|_|_| No warrantee or guarantee. Kurt Kuzba. (8/24/1997)*/ #include #include #include #include class Vesamodes { public: Vesamodes(int); ~Vesamodes(void); void Dot(int, int, int); void Line(int, int, int, int, int); void Circle(int, int, int, int, int, int, int); private: void Disk(int, int, int r, int c, int hg, int wd); int High, Wide, Color; }; Vesamodes::Vesamodes(int mode = 0) { switch(mode) { case 800: High = 600; Wide = 800; mode = 0x103; break; default: High = 480; Wide = 640; mode = 0x101; break; } Color = 7; _asm { mov ax, 4F02h; mov bx, mode; int 10h; } } void Vesamodes::Dot(int x, int y, int c) { long po, pa, px = (long)x, py = (long)y; int o; static int a = 0; if(x < 0 || x >= Wide || y < 0 || y >= High) return; switch(Wide) { case 800: po = pa = (py << 9) + (py << 8) + (py << 5) + px; break; default: po = pa = (py << 9) + (py << 7) + px; break; } po &= 0xffffL; pa /= 0x10000L; o = (int)po; if(a != (int)pa) { a = (int)pa; _asm { mov ax, 4F05h; xor bx, bx; mov dx, a; int 10h; } } _asm{ mov ax, 0A000h; mov di, o; mov es, ax; mov ax, c; stosb; } } /*_|_| end VESATEST.CPP PUBLIC DOMAIN PART 1 OF 3 */ > ] God's side of the tire is Never Flat........................ --- * Origin: *YOPS ]I[* 8.4 GIG * RA/FD/FE * Milwaukee, WI (1:154/750) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00116 Date: 04/28/98 From: KURT KUZBA Time: 01:13am \/To: GLEN OLDENHUIS (Read 3 times) Subj: vesatest.cpp 2/3 /*_|_| VESATEST.CPP PUBLIC DOMAIN PART 2 OF 3 _|_|_| Example of using 800x600 and 640x480 VESA modes. _|_|_| No warrantee or guarantee. Kurt Kuzba. (8/24/1997)*/ /* Circle is adapted from Bresnham.C in Bob Stout's SNIPPETS */ void Vesamodes::Circle(int xc, int yc, int r, int c, int WD = 0, int HG = 0, int dsk = 0) { int x = 0, d = (1 - r) << 1, w; HG = HG ? HG : High; WD = WD ? WD : Wide; w = (WD / HG) << 1; if(dsk) { Disk(xc, yc, r, c, HG, WD); } else { while(r >= 0) { Dot(xc + x, yc + r, c); Dot(xc + x, yc - r, c); Dot(xc - x, yc + r, c); Dot(xc - x, yc - r, c); if(d + r > 0) d -= (w * --r) - 1; if(x > d) d += ((++x) << 1) + 1; } } } void Vesamodes::Disk(int xc, int yc, int r, int c, int hg, int wd) { int l, x = 0, d = (1 - r) << 1, w = (wd / hg) << 1; while(r >= 0) { for(l = xc - x; l <= xc + x; l++) { Dot(l, yc + r, c); Dot(l, yc - r, c); } if(d + r > 0) d -= (w * --r) - 1; if(x > d) d += ((++x) << 1) + 1; } } void Vesamodes::~Vesamodes(void) { _asm{ mov ax, 0x03; int 10h; } } int rnd(int m){return (int)(((long)rand()*((long)m+1)-1)/RAND_MAX);} /*_|_| end VESATEST.CPP PUBLIC DOMAIN PART 2 OF 3 */ > ] Their numbers are 664 and 668, the neighbors of the beast... --- * Origin: *YOPS ]I[* 8.4 GIG * RA/FD/FE * Milwaukee, WI (1:154/750) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00117 Date: 04/28/98 From: KURT KUZBA Time: 01:13am \/To: GLEN OLDENHUIS (Read 3 times) Subj: vesatest.cpp 3/3 /*_|_| VESATEST.CPP PUBLIC DOMAIN PART 3 OF 3 _|_|_| Example of using 800x600 and 640x480 VESA modes. _|_|_| No warrantee or guarantee. Kurt Kuzba. (8/24/1997)*/ /* Line is adapted from Bresnham.C in Bob Stout's SNIPPETS */ void Vesamodes::Line(int x, int y, int x2, int y2, int c) { int i, steep = 0, sx, sy, dx, dy, e, ex, ey; dx = abs(x2 - x); sx = ((x2 - x) > 0) ? 1 : -1; dy = abs(y2 - y); sy = ((y2 - y) > 0) ? 1 : -1; if(dy > dx) { steep = x; x = y; y = steep; /* swap x and y */ steep = dx; dx = dy; dy = steep; /* swap dx and dy */ steep = sx; sx = sy; sy = steep; /* swap sx and sy */ steep = 1; } e = 2 * dy - dx; ex = dx << 1; ey = dy << 1; for(i = 0; i < dx; i++) { if(steep) Dot(y, x, c); else Dot(x, y, c); while(e >= 0) { y += sy; e -= ex; } x += sx; e += ey; } Dot(x2, y2, c); } void test(Vesamodes *V, int W = 640, int H = 480) { while(!kbhit()) { V->Line(rnd(W), rnd(H), rnd(W), rnd(H), rnd(255)); V->Circle(rnd(W), rnd(H), rnd(200), rnd(255)); V->Circle(rnd(W), rnd(H), rnd(200), rnd(255), 10 + rnd(100), 10 + rnd(100)); V->Circle(rnd(W), rnd(H), rnd(20), rnd(255), 10 + rnd(100), 10 + rnd(100), 1); } } int main(void) { time_t TM = time(NULL); srand((unsigned)TM); cout << "Hit any key to test 800x600x256" << endl; getch(); Vesamodes *VM = new Vesamodes (800); test(VM, 800, 600); delete VM; cout << "Hit any key to test 640x480x256" << endl; getch(); getch(); VM = new Vesamodes; test(VM); delete VM; cout << "Hit any key to exit Vesatest.cpp" << endl; getch(); getch(); return 0; } /*_|_| end VESATEST.CPP PUBLIC DOMAIN PART 3 OF 3 */ > ] Opossums on the Information Rustic Road..................... --- * Origin: *YOPS ]I[* 8.4 GIG * RA/FD/FE * Milwaukee, WI (1:154/750) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00118 Date: 04/26/98 From: TIM HUTZLER Time: 04:10pm \/To: GLEN OLDENHUIS (Read 3 times) Subj: Re: 256 color GO>What command do you have to enter to activate 256 colors? TH>That's a kind of a wide open question, isn't it? TH>Are you lookin' for a VESA controls, or what? GO>The lot. You mean the whole kit-and-kaboodle? Technically, there's a difference. [grin] ___ Blue Wave/QWK v2.12 --- Maximus/2 3.01 * Origin: Madman BBS * Chico, California * 530-893-8079 * (1:119/88) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00119 Date: 04/26/98 From: TIM HUTZLER Time: 04:27pm \/To: DARIN MCBRIDE (Read 3 times) Subj: Re: Default constructor DM>Now, in practical terms, this means that there are two types of DM>default constructors: - those with no actual arguments, and - DM>those with all default arguments. TH>Incorrect. TH>There is only one default constructor - no arguments. It doesnt even DM>You seem to be misinterpreting what I said. We're talking about DM>how it looks to the new C++ programmer Hi Darin; Maybe the discussion *should* be about how it looks to the developers of C++, namely Benjemin what's his name. [grin] DM>- in particular, how it looks(looked) to Rene. There are a lot of DM>concepts in following the two "types" that need to be ironed out. Yes, and it is important to get those concepts in correct *perspective* and accurately defined. There are certain rules no matter what level of programming one is at. And in C++ one of the rules is that there is only *one* _default_ constructor, no arguments, no returns. All other constructors are there to provide the desired functionality. DM>Since most C++ programmers have come from other languages, they DM>may not be used to the two concepts required here: overloading and DM>default arguments. True, overloading is an uncommon but nifty feature. But not default arguments - which, BTW, are not the same thing as a default constructor. Default arguments (or parameters, more correctly) can exist in *any* function whether it's a method to a class or not. A default constructor *must* exist in every class. If it is not specified (ie. one that takes no arguments), then the compiler will create one - behind the programmers back. DM>The easy default constructor to understand, the one that is coded DM>such that it cannot take arguments, is best seperated conceptually DM>from the more difficult one until the student can understand the DM>concepts enough to unite them again. Default constructors don't take arguments - never. Try it. Create a class with *one* constructor having one or more parameters. Specify an instance with no arguments. You will find that it both compiles *and* runs. Reason, the default constructor that was ommitted from the code was created by the compiler. DM>JMNSHO. ??? I'm not up on this acronym. [grin] cya around, friend. ___ Blue Wave/QWK v2.12 --- Maximus/2 3.01 * Origin: Madman BBS * Chico, California * 530-893-8079 * (1:119/88) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00120 Date: 04/28/98 From: RENE HERMAN Time: 02:59am \/To: TIM HUTZLER (Read 3 times) Subj: Default constructor Hello Tim ... Tuesday April 21 1998, you wrote Rene Herman RH>> According to ANSI C++, will a constructor with nothing but default RH>> arguments do as a default constructor? TH> It *is* the default constructor. Thanks, that was indeed what I was asking, sorry if I formulated badly. TH> Every class MUST have a default constructor. But, if a default TH> constructor (no args) is not specified in your code, the compiler TH> will create one for you. That's why there was no error. But now you're confusing me again. Not only was there no error, but declaring a TTime object as "TTime Time;" really resulted in the compiler calling my constructor with all arguments set to -1, not in calling an automatically generated no argument constructor. Furthermore, why must every class have a default constructor? When I never declare an object of the class without explicitly stating which constructor to use (ie only declare a TTime Time(1, 1, 1980, 0, 0);) there is no use for a default constructor, is there? Also, with simple classes that don't declare any virtual functions, there's really nothing to construct. When I have a class TClass { private: int i; public: void Set(int); }; declaring a TClass object doesn't generate any code. For the following main function int main() { TClass Class; Class.Set(0); return 0; } the compiler generated (part of -S output) _main proc near ; ; int main() ; enter 2,0 ; ; { ; TClass Class; ; ; Class.Set(0); ; push 0 lea ax,word ptr [bp-2] push ax call near ptr @TClass@Set$qi add sp,4 ; ; return 0; ; xor ax,ax ; ; } ; leave ret _main endp [ sidenote: making member function Set virtual, the compiler *does* indeed insert an (inline) constructor, initializing the objects VMT pointer: ; ; int main() ; enter 4,0 ; ; { ; TClass Class; ; mov word ptr [bp-4],offset @@TClass@ ; ; Class.Set(0); ; ] Or did I get you wrong? Rene --- * Origin: postmaster@rene.demon.nl (2:282/1.11) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00121 Date: 04/28/98 From: RENE HERMAN Time: 03:06am \/To: DARIN MCBRIDE (Read 3 times) Subj: Default constructor Hello Darin ... Friday April 24 1998, you wrote Rene Herman DM> Your TTime objects encapsulates a real object (in this case, an DM> abstract object that humans believe we understand): time. I see what you mean, and regret having to disagree with you. My TTime objects really didn't do anything remotely resembling encapsulating the real world concept of time, or even my notion of such a concept. What's the substance of time (its data members) and what influences it, that is, which methods should I provide? If I knew, I would have won a Nobel prize. :-) I hope I'm not over-interpreting your comments, but in my humble opinion object orientation shouldn't be made out to be more than a way of organizing computer code with advantages such as clarity and modularity, and disadvantages such as size and speed of the resulting code. Although it at times might provide for a useful abstraction, I feel that most real world objects, let alone concepts such as time, are far too complex to be encapsulated by, or even described by, a set amount of data and functions to operate on that data. DM> Abstract objects or abstract classes? I've never heard the term DM> 'abstract object' before. You were the one introducing the phrase, I just copied it. :-) But I must admit I thought you were referring to abstract classes. DM> A class is merely a description of what an object is and what DM> messages can be sent to it. I just browsed the chapter on Windows programming using OWL, but I guess here you mean "which methods it has for operating on an object of the class" when you say "what messages can be send to it"? :-) DM> I always put main last with everything implemented either in other DM> modules (where I have a header that is #include'd) or above it. I use DM> prototypes only in header files. Very glad to hear it, I really prefer it that way. Of course, style is a to a some degree a matter of personal taste, but I wouldn't want to start of by getting into habits that are frowned upon by most other programmers. [ void function() / void function(void) ] DM> Both work, but the empty parenthesis is the "right" way for DM> everything in C++. Thanks, I switched. [ NULL / 0 ] DM> I vastly prefer NULL. Hate to admit it, since I don't, but you do of course have a valid point. Will see if I'm able to switch. :-) DM> Use the one in comments for both - but, yeah, spreading it out will DM> make it more readable. Glad to hear it's "allowed", really disliked Tom Swan's way one-line way of doing things. I'm typing in most listings from the book as I go along, and everytime had to struggle with myself to *not* spread them out. :-) DM> One exception may be functions that merely redirect calls... DM> int baz(int i) { return b->baz(i); } Agreed. DM> Any time I see "m_" in front of a variable, I know I can find its DM> definition in the class - it is local to the class, but still global DM> in that it can be modified by multiple functions. Will have to consider this. I don't really like the "this->" method myself, but naming a constructors arguments the same as the class's data members does lend some clarity to the code, as far as I'm concerned. By the way, what does the "m" signify? I'm not sure I understand your comment about the "multiple" functions. Is there any other type? All class data members can be modified by all (non const) member functions, can they not? DM> Another possibility in this case is: DM> TExample(char* s) : s(strdup(s)) DM> {} I just might like this approach... :-) DM> I also have a "cchar" class that handles the strdup/delete paradigm DM> for you - it puts an array on the heap but it looks like any other DM> array on the stack - you don't have to delete it. :-) I am somewhat of a minimalist, I really prefer doing things such as that explicitly. Keeps me in touch with what's going on. :-) [ (draft) ANSI standard obtainable? ] DM> Someone else may help you there - I just go by what my compiler DM> allows me to do ... if it doesn't allow it (yet), there's no point in DM> doing it even if the standard allows it. :-) I agree, but what if you compiler *does* allow it, yet you aren't sure if others will? Or worse still, what if you aren't even sure yours will? For instance, I was wondering if it were safe to pass a NULL pointer to strdup, which would allow me to write something like TExample::TExample(const char *s) { this->s = strdup(s); } without having to check for s being NULL first. Neither Borland's online help nor Tom Swan's function reference said one way or the other, so I had to dig into the RTL source to find out it *wasn't* safe, at least not on my compiler. I'm assuming the standard would have explicitly told me so. RH>> Hope I didn't ask too many questions at once. Please be RH>> aware that if you do reply I will very likely have some RH>> more lined up for you by that time... :-) DM> And I probably won't be the only one answering... good luck! Thank you! I'll be addresing the next bunch to all again, hardly seems fair to make you into my personal teacher for having been the first one to answer that first question. Don't let it keep you from answering though, you're helping me lots! :-) Rene --- * Origin: postmaster@rene.demon.nl (2:282/1.11) --------------- FIDO MESSAGE AREA==> TOPIC: 203 C++ Ref: F5G00122 Date: 04/28/98 From: RENE HERMAN Time: 03:19am \/To: ALL (Read 3 times) Subj: Questions Hello All ... I'm a newcomer to the C++ language, and have some questions. Thanks in advance to anyone answering, please feel free to pick only question(s) that you feel like answering. First off, would anyone happen to know if/where one might obtain a copy of the (draft) ANSI C++ standard? If not that, I would also very much welcome an URL for a copy of the draft ANSI C standard, assuming it also includes the standard libary functions. I also read the C_ECHO, and remember a new draft being released? I thought I saved a message announcing it, but now I seem to have misplaced it. :-) Should I allow the compiler to allocate enums as single bytes? Or to use unsigned characters by default? It allows me to set these as options, but I believe both could get me into portability trouble? What's standard? When overloading operators for a class, when should I implement the functions as member functions, and when as friend functions? My textbook demonstrates both methods, but doesn't say when nor why to use either. When overloading the "=" operator for class X, should I use void X::operator=([const] X&); as my textbook does, or X& X::operator=([const] X&); returning "*this", as Borland's online help says I should do? Is there a difference? In an exercise which asked to to overload the ++ and -- prefix and postfix operators for a class, I wrote the following test code: cout << "a == " << a.GetValue() << "; ++a == " << ++a << endl << "a == " << a.GetValue() << "; a++ == " << a++ << endl << "a == " << a.GetValue() << "; --a == " << --a << endl << "a == " << a.GetValue() << "; a-- == " << a-- << endl << "a == " << a.GetValue(); First I was quite surprised by the really wrong output this produced but after some minutes of hard thought (and cursing buggy compilers), I concluded this really was to be expected as a result of the cdecl (by the way, is that an acronymn?) right-to-left style of argument passing. Indeed, splitting the single cout statement into 9 seperate cout statements solved the problem, and quite content that I had managed to solve the mystery I went back through the chapter since I remembered it did something similar, only to be rewarded with an example where the autor *did* string multiple statements onto a single cout (not everything as I did, but one line at a time, one GetValue call and one ++/-- call, which still produced wrong output, as I now expected) providing the following note: "Due apparently to a bug in Borland C++ 4.5, using that compiler did not produce the preceding results. If you experience this problem, repaired in Borland C++ 5, use the following main function, which divides the multipart output statements and ensures that the expressions are evaluated in strict left-to-right fashion: [ 9 couts]" Pardon? Bug? Annoying as it is, this behaviour is to be expected of cdecl isn't it? Furthermore, if it is a bug, it doesn't seem fixed... I guess this is a Borland specific question, but is there any way to stop name mangling for class member functions? I know that normally, when implementing functions in an external assembly language module I can declare them as extern "C" to stop name mangling, but the compiler doesn't seem to let me do that with member functions. Rene --- * Origin: postmaster@rene.demon.nl (2:282/1.11)