Hello,
I'm trying to use the NumberFmt structure to display numbers and it
will not display the number. When I remove the NumberFmt structure
from the GetNumberFormat function, it displays the number with no
problem. I can't determine what I'm doing wrong.
Here's the code:

CRect m_rectangle = new CRect(400,500,800,400);
TCHAR szNum[]="14555435";
TCHAR szBuf[20];
NUMBERFMT numFormat;
numFormat.Grouping=3;
numFormat.LeadingZero=10;
numFormat.NumDigits=1;
numFormat.NegativeOrder=0;
numFormat.lpDecimalSep = ".";
numFormat.lpThousandSep = ",";
GetNumberFormat( LOCALE_USER_DEFAULT, 0, szNum, &numFormat, szBuf,
sizeof(szBuf) );
dc.DrawTextA( (LPCTSTR)szBuf, sizeof(szBuf), m_rectangle, DT_VCENTER |
DT_SINGLELINE );

Any help is appreciated.
Thanks.

Re: Newbie Q - Numberfmt not display number by Ulrich

Ulrich
Wed Apr 12 09:58:59 CDT 2006

lakepeir@yahoo.com wrote:
> I'm trying to use the NumberFmt structure to display numbers and it
> will not display the number. When I remove the NumberFmt structure
> from the GetNumberFormat function, it displays the number with no
> problem. I can't determine what I'm doing wrong.
> Here's the code:
>
> CRect m_rectangle = new CRect(400,500,800,400);

Huh? Are you sure this is C++ code? I think this shouldn't compile. What you
mean is
CRect m_rectangle(400,500,800,400);
or maybe
CRect m_rectangle = CRect(400,500,800,400);

Also note that the 'm_' prefix is typically used for member variables, not
for locals.

> TCHAR szNum[]="14555435";
> TCHAR szBuf[20];
> NUMBERFMT numFormat;
> numFormat.Grouping=3;
> numFormat.LeadingZero=10;
> numFormat.NumDigits=1;
> numFormat.NegativeOrder=0;
> numFormat.lpDecimalSep = ".";
> numFormat.lpThousandSep = ",";
> GetNumberFormat( LOCALE_USER_DEFAULT, 0, szNum, &numFormat, szBuf,
> sizeof(szBuf) );

What is the returnvalue of GetNumberFormat()? Use ASSERT() or VERIFY() to
make sure that things succeed. Also, what is the content of the string
afterwards? Looking at the MSDN (msdn.microsoft.com) I think that the
combination between a custom format and then telling it to use the user's
default locale is not right, but I could be wrong.

> dc.DrawTextA( (LPCTSTR)szBuf, sizeof(szBuf), m_rectangle, DT_VCENTER |
> DT_SINGLELINE );

There is one more problem, you have a bad mixture between TCHAR and char
which will fire back sometime. In particular, if you use TCHAR strings, you
need to define string literals as _T("foo") for them to match properly.
Further, using DrawTextA with a TCHAR string is wrong, this only really
works with a char string. The fact that you applied a cast there makes me
seriously wonder whether that is not the problem. Correct code normally
works without any casts and still doesn't even produce warnings!

Another big problem here is that both functions used here expect the number
of characters used. Since TCHAR is not necessarily a single byte per
character, your code is wrong. Instead of "sizeof(szBuf)", rather use
"(sizeof szBuf)/(sizeof *szBuf)" (also note here that sizeof is not a
function and only when you use it with a type you have to put it in
brackets).

Lastly, the code *can* work with all the TCHAR/char madness, but it isn't
guaranteed to and if I were you, I would fix it now because otherwise it
probably will come back to bite you in the future. Read up on the meaning
of the UNICODE and _UNICODE macros in the MSDN or archives of this group,
this problem occurs frequently.

Uli


Re: Newbie Q - Numberfmt not display number by lakepeir

lakepeir
Wed Apr 12 12:58:40 CDT 2006


Ulrich Eckhardt wrote:
> lakepeir@yahoo.com wrote:
> > I'm trying to use the NumberFmt structure to display numbers and it
> > will not display the number. When I remove the NumberFmt structure
> > from the GetNumberFormat function, it displays the number with no
> > problem. I can't determine what I'm doing wrong.
> > Here's the code:
> >
> > CRect m_rectangle = new CRect(400,500,800,400);
>
> Huh? Are you sure this is C++ code? I think this shouldn't compile. What you
> mean is
> CRect m_rectangle(400,500,800,400);
> or maybe
> CRect m_rectangle = CRect(400,500,800,400);
>
This does compile. You use the new operator to allocate memory.
> Also note that the 'm_' prefix is typically used for member variables, not
> for locals.
>
> > TCHAR szNum[]="14555435";
> > TCHAR szBuf[20];
> > NUMBERFMT numFormat;
> > numFormat.Grouping=3;
> > numFormat.LeadingZero=10;
> > numFormat.NumDigits=1;
> > numFormat.NegativeOrder=0;
> > numFormat.lpDecimalSep = ".";
> > numFormat.lpThousandSep = ",";
> > GetNumberFormat( LOCALE_USER_DEFAULT, 0, szNum, &numFormat, szBuf,
> > sizeof(szBuf) );
>
> What is the returnvalue of GetNumberFormat()? Use ASSERT() or VERIFY() to
> make sure that things succeed. Also, what is the content of the string
> afterwards? Looking at the MSDN (msdn.microsoft.com) I think that the
> combination between a custom format and then telling it to use the user's
> default locale is not right, but I could be wrong.
>

It's hard to determine what the content string is afterward because it
never draws the string. The return value of Get NumberFormat is zero.
> > dc.DrawTextA( (LPCTSTR)szBuf, sizeof(szBuf), m_rectangle, DT_VCENTER |
> > DT_SINGLELINE );
>
> There is one more problem, you have a bad mixture between TCHAR and char
> which will fire back sometime. In particular, if you use TCHAR strings, you
> need to define string literals as _T("foo") for them to match properly.
> Further, using DrawTextA with a TCHAR string is wrong, this only really
> works with a char string. The fact that you applied a cast there makes me
> seriously wonder whether that is not the problem. Correct code normally
> works without any casts and still doesn't even produce warnings!
>
> Another big problem here is that both functions used here expect the number
> of characters used. Since TCHAR is not necessarily a single byte per
> character, your code is wrong. Instead of "sizeof(szBuf)", rather use
> "(sizeof szBuf)/(sizeof *szBuf)" (also note here that sizeof is not a
> function and only when you use it with a type you have to put it in
> brackets).
>
> Lastly, the code *can* work with all the TCHAR/char madness, but it isn't
> guaranteed to and if I were you, I would fix it now because otherwise it
> probably will come back to bite you in the future. Read up on the meaning
> of the UNICODE and _UNICODE macros in the MSDN or archives of this group,
> this problem occurs frequently.
>
> Uli

I have changed the code so that the TCHAR are char and change the
sizeof(szBuf) as suggested. It's still not drawing and here's the new
code:
CRect rectangle = new CRect(400,500,800,400);
CComVariant szNum="14555435";
char szBuf[20];
NUMBERFMT numFormat;
numFormat.Grouping=3;
numFormat.LeadingZero=10;
numFormat.NumDigits=1;
numFormat.NegativeOrder=0;
numFormat.lpDecimalSep = ".";
numFormat.lpThousandSep = ",";
CString convertstring = szNum.bstrVal;
UINT ret = GetNumberFormat( NULL, 0, convertstring, &numFormat, szBuf,
sizeof(szBuf) );
dc.DrawTextA( szBuf, (sizeof szBuf)/(sizeof *szBuf) , m_rectangle,
DT_VCENTER | DT_SINGLELINE );


Re: Newbie Q - Numberfmt not display number by Igor

Igor
Wed Apr 12 17:38:23 CDT 2006

lakepeir@yahoo.com wrote:
> Hello,
> I'm trying to use the NumberFmt structure to display numbers and it
> will not display the number. When I remove the NumberFmt structure
> from the GetNumberFormat function, it displays the number with no
> problem. I can't determine what I'm doing wrong.
> Here's the code:
>
> CRect m_rectangle = new CRect(400,500,800,400);
> TCHAR szNum[]="14555435";
> TCHAR szBuf[20];
> NUMBERFMT numFormat;
> numFormat.Grouping=3;
> numFormat.LeadingZero=10;
> numFormat.NumDigits=1;
> numFormat.NegativeOrder=0;
> numFormat.lpDecimalSep = ".";
> numFormat.lpThousandSep = ",";
> GetNumberFormat( LOCALE_USER_DEFAULT, 0, szNum, &numFormat, szBuf,
> sizeof(szBuf) );
> dc.DrawTextA( (LPCTSTR)szBuf, sizeof(szBuf), m_rectangle, DT_VCENTER
> | DT_SINGLELINE );

GetNumberFormat most likely fails, because you are setting up NUMBERFMT
structure incorrectly. Try with LeadingZero set to 0 (no leading zeros)
or 1 (use leading zeros): a value of 10 makes no sense.
--
With best wishes,
Igor Tandetnik

With sufficient thrust, pigs fly just fine. However, this is not
necessarily a good idea. It is hard to be sure where they are going to
land, and it could be dangerous sitting under them as they fly
overhead. -- RFC 1925



Re: Newbie Q - Numberfmt not display number by Ulrich

Ulrich
Thu Apr 13 03:37:42 CDT 2006

lakepeir@yahoo.com wrote:
> Ulrich Eckhardt wrote:
>> lakepeir@yahoo.com wrote:
>> > CRect m_rectangle = new CRect(400,500,800,400);
>>
>> Huh? Are you sure this is C++ code? I think this shouldn't compile. What
>> you mean is
>> CRect m_rectangle(400,500,800,400);
>> or maybe
>> CRect m_rectangle = CRect(400,500,800,400);
>>
> This does compile. You use the new operator to allocate memory.

Use the new operator to allocate *FREE STORE* memory in C++. Hence my
question what language you were using. My two lines are perfectly legal
C++.
Inspecting further, I think what happens in your code is that the 'CRect*'
decays into a 'RECT*' which is then taken by the ctor of CRect - in that
case this will be a memory leak. In general, for C++, drop the 'new' unless
you really need it, it's not the same as it is in Java, in case you have
that as a background.

> It's hard to determine what the content string is afterward because it
> never draws the string.

Use a debugger to look at the string or use OutputDebugString() or the
TRACE() macro.

Concerning the returnvalue of zero that you mentioned, it means that zero
TCHARs were written to the string, i.e. that something failed. The
documentation also gives a suggestion how to further distinguish errors,
see the MSDN.

Lastly, you still use char-strings with a TCHAR function (GetNumberFormat is
TCHAR based) which might lead to these errors. Does the code compile
without warnings and errors? In case you really mean char strings, you also
need to use GetNumberFormatA and NUMBERFMTA (if the latter exists) but I'm
not totally sure - I never used CComVariant so I can't tell for sure how
that works.

Uli


Re: Newbie Q - Numberfmt not display number by lakepeir

lakepeir
Thu Apr 13 09:04:21 CDT 2006

Thanks!! That solve the problem.
Igor Tandetnik wrote:
> lakepeir@yahoo.com wrote:
> > Hello,
> > I'm trying to use the NumberFmt structure to display numbers and it
> > will not display the number. When I remove the NumberFmt structure
> > from the GetNumberFormat function, it displays the number with no
> > problem. I can't determine what I'm doing wrong.
> > Here's the code:
> >
> > CRect m_rectangle = new CRect(400,500,800,400);
> > TCHAR szNum[]="14555435";
> > TCHAR szBuf[20];
> > NUMBERFMT numFormat;
> > numFormat.Grouping=3;
> > numFormat.LeadingZero=10;
> > numFormat.NumDigits=1;
> > numFormat.NegativeOrder=0;
> > numFormat.lpDecimalSep = ".";
> > numFormat.lpThousandSep = ",";
> > GetNumberFormat( LOCALE_USER_DEFAULT, 0, szNum, &numFormat, szBuf,
> > sizeof(szBuf) );
> > dc.DrawTextA( (LPCTSTR)szBuf, sizeof(szBuf), m_rectangle, DT_VCENTER
> > | DT_SINGLELINE );
>
> GetNumberFormat most likely fails, because you are setting up NUMBERFMT
> structure incorrectly. Try with LeadingZero set to 0 (no leading zeros)
> or 1 (use leading zeros): a value of 10 makes no sense.
> --
> With best wishes,
> Igor Tandetnik
>
> With sufficient thrust, pigs fly just fine. However, this is not
> necessarily a good idea. It is hard to be sure where they are going to
> land, and it could be dangerous sitting under them as they fly
> overhead. -- RFC 1925