|
Christian Graus wrote: I believe that you need to do the typedef outside the class. Better yet, don't do it, those things are nasty, they just make your code unreadable.
Nothing's wrong with typedef s; they make code more readable not less so. Nothing's wrong with typedef s inside class definitions either: in fact in some cases it's just good encapsulations and is exactly where they should go. The OP’s problem was simply that the use of a member typedef needs to be qualified with the containing class name if used outside the containing class, just like for any other member.
Steve
|
|
|
|
|
Stephen Hewitt wrote: they make code more readable not less so.
That's a matter of opinion. I've worked on code that contained a ton of STL containers, all typedefed, and it was plain illegible.
Stephen Hewitt wrote: The OP’s problem was simply that the use of a member typedef needs to be qualified with the containing class name if used outside the containing class, just like for any other member.
Yes, I realised that, but pulling it out seemed the simplest solution.
Christian Graus - Microsoft MVP - C++
Metal Musings - Rex and my new metal blog
"I am working on a project that will convert a FORTRAN code to corresponding C++ code.I am not aware of FORTRAN syntax" ( spotted in the C++/CLI forum )
|
|
|
|
|
Christian Graus wrote: That's a matter of opinion. I've worked on code that contained a ton of STL containers, all typedefed, and it was plain illegible.
In the end almost anything can be considered a matter of opinion, but I’ll explain some instances in which typedef s can be useful. A STL std::set looks something like this:
template <class _K, class _Pr = less<_K>, class _A = allocator<_K> >
class set;
If we have one of these beasts where we’ve made explicit use of all three template arguments we’d have to specify the whole long type in every use. A simple typedef with a descriptive name eliminates all this. Surely this is a simplification, especially since some of the arguments are implementation details. Say, at a later stage, we make a design decision to change the allocator used: we would have to go through the code and change all uses of the type. If a typedef is used we can make the change in one place. This is an example of the general design principle that, if possible, a single design decision should be expressed in a single place (or as few places as possible). Another example is generic programming; STL containers use typedef s with standard names to expose implementation dependent types in a standard manner which enables uniform usage despite the differences.
Steve
|
|
|
|
|
If you must (against Christian's advice) nest the typedef you need to use a scope resolution
operator to reference the nested class/type from outside the class:
WordTable::OccurrenceList& WordTable::getOccurrences(string word)
{
WordTable::OccurrenceList list;
return list;
}
A template defines a class. If you nest the class in another class then you need to resolve the
scope anywhere outside of the class, as shown above.
Plus there's a bug, noted above
Mark
"Posting a VB.NET question in the C++ forum will end in tears." Chris Maunder
|
|
|
|
|
Hi Mark:
Thank you for your solution. This is EXACTLY what my problem was!!!!
So happy to get it solved.
Thank you again.
|
|
|
|
|
Hi C_Zealot,
Try a forward declaration (in the h file, or the cpp file):
class OccurrenceList;
Jeff
|
|
|
|
|
Please help me find a simple example of CTreeCtrl (view not dialog) actually using TVN_SELCHANGED message and GetSelectedItem function. My code always returns first item in the tree and the MS CmnCtrl1 sample code refuses to give me the whole text of the selected item. I get only first character. It should return CString.
Thanks for reading
Vaclav
I got it!
I have neglected to bypass first TVN_SELCHANGED message which gets posted on initial drawing of first node of the tree! Hence I always see first node "selected".
-- modified at 21:57 Thursday 31st May, 2007
|
|
|
|
|
Vaclav_Sal wrote: refuses to give me the whole text of the selected item
How did you verify that? Through debugging? Try putting a message box. If _UNICODE is define in your project, you must set some settings of MSDEV.
tools->options->Debug-> Now tick the "Display UNICODE string check box".
|
|
|
|
|
Nave,
I changed to display UNICODE and it works now. However I am using MS sample code and did not find UNICODE defined!
Thanks for your help
|
|
|
|
|
Vaclav_Sal wrote: and did not find UNICODE defined!
Check the following location.
project settings->C++->And in the Preprocess definitions edit box check _UNICODE is defined.
|
|
|
|
|
You are absolutely correct!
Thanks
|
|
|
|
|
Hi all:
When I am trying to write the function definition for:
OccurrenceList& getOccurrences(string word);
I wrote:
<code>......
typedef vector<streampos> OccurrenceList;
......
78: OccurrenceList& WordTable::getOccurrences(string word) {
79: OccurrenceList list;
80: return list; //Return nothing to simplify the function for debugging.
81: }</code>
But I have 5 (!!) errors, they are:
78: error C2143: syntax error : missing ';' before '&';
78: error C4430: missing type specifier - int assumed. Note: C++ does not support default-int;
79: error C4430: missing type specifier - int assumed. Note: C++ does not support default-int;
79: 'int &WordTable::getOccurrences(std::string)' : overloaded function differs only by return type from 'WordTable::OccurrenceList &WordTable::getOccurrences(std::string)';
79: 'WordTable::getOccurrences' : redefinition; different basic types;
When I commented out this function, the rest of my program ran sweet. I really do not know what caused those problems.
Thank you
|
|
|
|
|
It looks like the compiler doesn't know what a "OccurrenceList" type is at that point.
Are you missing a header file containing the declaration of the class?
Mark
"Posting a VB.NET question in the C++ forum will end in tears." Chris Maunder
|
|
|
|
|
Hi:
That IS the problem.
Thank you
|
|
|
|
|
Hello,
I would like to wrap VC++6 code; it should be used at C# calss (all at VS2005).
Do you know how to do it? Do you have any example?
thanks.
|
|
|
|
|
I guess this is a pretty well trodden route.
First port your VC6 C++ to VC8. The project will auto convert but you still need to tidy up all the Safe CRT change consequences to get rid of W4 Warnings. Make sure it all works with the new MFC/ATL etc.
Second if the substance of your C++ is not in COM objects, you may be in a deal of trouble. Fortunately it's not usually hard to start chunking your C++ into COM objects, depending on how big it is.
Third, once you've got the code you want to use in one or more C++ COM objects take a look at articles on C# COM Interop. It works really well once you get over the inital strangeness, doesn't require you to write a lot of code or even any PInvokes or proxy/stub nastiness.
Step four is probably to move this post to the C# Managed and mixed development forum before somebody moans;)
Nothing is exactly what it seems but everything with seems can be unpicked.
|
|
|
|
|
if you can put your code in a C-interfaced DLL, you can use it from C# (or any language, really) without too much hassle.
|
|
|
|
|
I agree with Chris Losinger Dll is a good choice.
|
|
|
|
|
When I compile this code in MSVC++ 2005 express I get the following error.
SERVICE_TABLE_ENTRY DispatchTable[]=
{{"Service1",serviceMain},{NULL,NULL}};
error C2440: 'initializing' : cannot convert from 'const char [9]' to 'LPWSTR'
Pretty much where ever I am using a string I get the same error. Why doesn't the code work?
|
|
|
|
|
I would have to see the definition of SERVICE_TABLE_ENTRY to be sure but I suspect it's defined to contain a wide character (UNICODE) string whereas "Service1" is a constant narrow character or (ASCII) string. UNICODE strings, usually, have 16bits per character while ASCII characters have only 8bits each so conversion between the two is non trivial. There's a whole world of pain involved here, code pages, locales, W2A macros, multi-byte character sets, UTF-8 and then some but what you need to do to make the above code work is make use of the _T() macro Microsoft so kindly supply.
SERVICE_TABLE_ENTRY DispatchTable[]=<br />
{{ _T( "Service1" ) , serviceMain }, {NULL, NULL}};
Enjoy.
Nothing is exactly what it seems but everything with seems can be unpicked.
|
|
|
|
|
Add L before "", it declare it as wide char.
<br />
SERVICE_TABLE_ENTRY DispatchTable[]=<br />
{{L"Service1",serviceMain},{NULL,NULL}};<br />
Best Regards.
|
|
|
|
|
Anybody see what the problem is with this code? GetDIBits fails, and when I call GetLastError(), it tells me that Windows "ERROR_FILE_NOT_FOUND".
<br />
<br />
GetClientRect(hDlg, &rc);
<br />
hdc = GetDC(hDlg);
<br />
rc.bottom -= (GetSystemMetrics(SM_CYHSCROLL)+GetSystemMetrics(SM_CYEDGE));<br />
<br />
hSavedXYContext = CreateCompatibleDC(hdc);
hSavedXYBitmap = CreateCompatibleBitmap(hdc, rc.right-rc.left,rc.bottom-rc.top); <br />
<br />
hTheDCsOriginalBitmap = (HBITMAP)SelectObject(hSavedXYContext, hSavedXYBitmap); <br />
<br />
BitBlt(hSavedXYContext,0,0,rc.right-rc.left, rc.bottom-rc.top,hdc,0,0,SRCCOPY);<br />
<br />
hSavedXYBitmap = (HBITMAP)SelectObject(hSavedXYContext, hTheDCsOriginalBitmap); <br />
<br />
<br />
<br />
<br />
<br />
GetObject(hSavedXYBitmap,sizeof(BITMAP),(LPSTR)(&bmp));<br />
<br />
cClrBits = (WORD)(bmp.bmPlanes*bmp.bmBitsPixel);<br />
<br />
cClrBits = 4;<br />
<br />
pbmi = (PBITMAPINFO) LocalAlloc(LPTR,sizeof(BITMAPINFOHEADER));<br />
<br />
<br />
pbmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);<br />
pbmi->bmiHeader.biWidth = bmp.bmWidth;<br />
pbmi->bmiHeader.biHeight = bmp.bmHeight;<br />
pbmi->bmiHeader.biPlanes = bmp.bmPlanes;<br />
pbmi->bmiHeader.biBitCount =4;<br />
<br />
pbmi->bmiHeader.biCompression = BI_RGB;<br />
<br />
pbmi->bmiHeader.biSizeImage = (pbmi->bmiHeader.biWidth + 15)/16 <br />
* pbmi->bmiHeader.biHeight * 4;<br />
<br />
pbmi->bmiHeader.biClrImportant = 0;<br />
<br />
<br />
pBitmapInfoHeader = (PBITMAPINFOHEADER)pbmi;<br />
<br />
lpBits = (LPBYTE) GlobalAlloc(GMEM_FIXED,pbmi->bmiHeader.biSizeImage);<br />
<br />
test = GetDIBits(hdc,hSavedXYBitmap,0,(WORD) pbmi->bmiHeader.biHeight,<br />
lpBits,pbmi,DIB_RGB_COLORS);<br />
<br />
test = GetLastError();<br />
I would appreciate any feedback, as I am out of ideas.
|
|
|
|
|
You have to check all the values passed to GetDIBits very carefully. That functions is very touchy and will fail if a single bit is not correct. I do not think the error message has anything to do with the code you are showing, as GeDIBits will often fail without generating any error at all.
See CDibData[^], it might help.
Note: CDibData has a minor bug that I still have not updated, but it has been a while since I played with graphics.
INTP
"Program testing can be used to show the presence of bugs, but never to show their absence."Edsger Dijkstra
|
|
|
|
|
I see a few problems -
TheDelChop wrote: GetObject(hSavedXYBitmap,sizeof(BITMAP),(LPSTR)(&bmp));
Irrelevent, but cast to a LPSTR?? No cast to a void pointer is necessary
Problems:
Creating a BITMAPINFO the size of a BITMAPINFOHEADER.
Using the planes value from the DDB when it HAS to be 1 in a DIB.
bmiHeader.biSizeImage is calculated wrong - rows of pixel data in a DIB need to be DWORD aligned.
You've provided no color table (16-colors) for your destination 4-bit DIB
The resulting GetDIBits call should fail based on the above.
Something like this maybe will get you closer:
...
int nNumColors = 1 << cClrBits;
LONG lBytesPerRow = (((bmp.bmWidth * (long)cClrBits + 31L) & (~31L)) / 8L);
BYTE* pBitmapBits;
LONG SizeOfBitmapInfo = sizeof(BITMAPINFO) + ((nNumColors - 1) * sizeof(RGBQUAD));
BITMAPINFO *pbmi = (PBITMAPINFO) LocalAlloc(LPTR, SizeOfBitmapInfo);
memset(pbmi, 0, SizeOfBitmapInfo);
pbmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
pbmi->bmiHeader.biWidth = bmp.bmWidth;
pbmi->bmiHeader.biHeight = bmp.bmHeight;
pbmi->bmiHeader.biPlanes = 1;
pbmi->bmiHeader.biBitCount = cClrBits;
pbmi->bmiHeader.biCompression = BI_RGB;
pbmi->bmiHeader.biSizeImage = lBytesPerRow * bmp.bmHeight;
pBitmapInfoHeader = (PBITMAPINFOHEADER)pbmi;
lpBits = (LPBYTE) GlobalAlloc(GMEM_FIXED,pbmi->bmiHeader.biSizeImage);
test = ::GetDIBits(hdc, hSavedXYBitmap, 0, (WORD) pbmi->bmiHeader.biHeight, lpBits, pbmi, DIB_RGB_COLORS);
if (test == 0)
test = GetLastError();
"Posting a VB.NET question in the C++ forum will end in tears." Chris Maunder
|
|
|
|
|
I want to compile a project that I have created. The project has class objects separated in different files i.e. main.cpp, card.h, card.cpp, deck.h, deck.cpp. How am I able to do this so the deck class can create in instance of the card class i.e. vector<card*> x; I know this is really newbie but I got to know.
|
|
|
|
|