|
I think you need to multilangue on your program and codeproject has some articles about it.
|
|
|
|
|
Please look at the posting guidelines again, especially the use of the pre tag to make code readable.
Before I gave up reading your code, I noticed at least one error.
You call default DefaultFontInit, then use m_hFont. But in defualt font init, you fill m_LogFont, and create hFont - so m_hFont is not inialised. I gave up after that.
For further diagnosis, please initialise all your variable to NULL, single step through, and check the state of variables as you use them / as you expect them to change. This will show things that you expect to happen not-happen. And vice versa.
Iain.
|
|
|
|
|
Hello again, I am sorry for not placing the code in the <pre></pre> tags, so the following are the code again in tags first tag section are the C code again. Second tag section are the VB code again.
<pre>
#include <windows.h>
#include <stdio.h>
#include <tchar.h>
HFONT m_hFont;
LOGFONT m_LogFont;
_TCHAR m_szSection[256];
_TCHAR m_szEntry[256];
void DefaultFontInit();
HFONT CreateFontLocal();
long
__stdcall
CodeProjectDrawText(
long lWindowDC,
_TCHAR *lpszFontName,
long lFontSize,
_TCHAR *lpszMultiByteText,
long X,
long Y)
{
long nFontHeight = 0;
long nLen = 0;
long nStatus = 0;
_tcscpy(m_szSection, _T("Settings"));
_tcscpy(m_szEntry, _T("Font"));
nFontHeight = - MulDiv (lFontSize, GetDeviceCaps (GetDC (0), LOGPIXELSY), 72);
DefaultFontInit(lpszFontName, nFontHeight);
SelectObject(lWindowDC,m_hFont);
nLen = _tcslen(lpszMultiByteText);
nStatus = TextOut(lWindowDC, X, Y, &lpszMultiByteText, nLen);
return (0);
}
void DefaultFontInit(_TCHAR *lpszFontName, long nFontHeight)
{
HFONT hFont;
// define the logical parameters for the default font
//m_LogFont.lfHeight = -11; // size 8
m_LogFont.lfHeight = nFontHeight;
m_LogFont.lfWidth = 0;
m_LogFont.lfEscapement = 0;
m_LogFont.lfOrientation = 0;
m_LogFont.lfWeight = FW_NORMAL;
m_LogFont.lfItalic = 0;
m_LogFont.lfUnderline = 0;
m_LogFont.lfStrikeOut = 0;
m_LogFont.lfCharSet = 0;
m_LogFont.lfOutPrecision = OUT_STRING_PRECIS;
m_LogFont.lfClipPrecision = CLIP_STROKE_PRECIS;
m_LogFont.lfQuality = DEFAULT_QUALITY;
m_LogFont.lfPitchAndFamily = FF_SWISS | VARIABLE_PITCH;
//_tcscpy(m_LogFont.lfFaceName, _T("Lucida Sans Unicode"));
_tcscpy(m_LogFont.lfFaceName, lpszFontName);
// create the associated font
hFont = CreateFontLocal();
}
HFONT CreateFontLocal()
{
HFONT hFont = CreateFontIndirect(&m_LogFont);
if (hFont == NULL)
{
// GetLastError(); can be used to understand why the font was not created
MessageBox(0, _T("Impossible to create font\n"), _T("My Sample"), 0);
}
// don't forget to delete the current font
if (m_hFont != NULL)
{
DeleteObject(m_hFont);
}
// store the font (event if the creation has failed)
m_hFont = hFont;
return hFont;
}
</pre>
<pre>
Private Const FW_NORMAL = 400
Private Const DEFAULT_CHARSET = 1
Private Const OUT_DEFAULT_PRECIS = 0
Private Const CLIP_DEFAULT_PRECIS = 0
Private Const DEFAULT_QUALITY = 0
Private Const VARIABLE_PITCH = 2
Private Const FF_SWISS = 32 ' Variable stroke width, sans-serifed.
Private Const GCS_RESULTSTR = &H800
Private Const GCS_RESULTREADSTR = &H200
Private Const GCS_COMPSTR = &H8
Private Const GCS_COMPREADSTR = &H1
Private Const SCS_SETSTR = (GCS_COMPREADSTR Or GCS_COMPSTR)
Private Declare Function GetDC Lib "user32" (ByVal hwnd As Long) As Long
Private Declare Function CodeProjectDrawText Lib "CodeProjectSample.dll" ( _
ByVal lWindowDc As Long, _
ByVal szFontName As String, _
ByVal szFontSize As Long, _
ByVal lstrText As String, _
ByVal x As Long, _
ByVal y As Long) _
As Long
Private Declare Function GetDeviceCaps Lib "gdi32" (ByVal hdc As Long, ByVal nIndex As Long) As Long
Private Declare Function ImmGetContext Lib "imm32.dll" (ByVal hwnd As Long) As Long
Private Declare Function ImmGetOpenStatus Lib "imm32.dll" (ByVal himc As Long) As Long
Private Declare Function ImmGetCompositionString Lib "imm32.dll" Alias "ImmGetCompositionStringA" (ByVal himc As Long, ByVal dw As Long, lpv As Any, ByVal dw2 As Long) As Long
Private Declare Function ImmReleaseContext Lib "imm32.dll" (ByVal hwnd As Long, ByVal himc As Long) As Long
Private Declare Function MulDiv Lib "kernel32" (ByVal nNumber As Long, ByVal nNumerator As Long, ByVal nDenominator As Long) As Long
Private Declare Function CreateFont Lib "gdi32" Alias "CreateFontA" (ByVal H As Long, ByVal W As Long, ByVal E As Long, ByVal O As Long, ByVal W As Long, ByVal I As Long, ByVal u As Long, ByVal S As Long, ByVal C As Long, ByVal OP As Long, ByVal CP As Long, ByVal Q As Long, ByVal PAF As Long, ByVal F As String) As Long
Private Declare Function TextOutW Lib "gdi32" (ByVal hdc As Long, ByVal x As Long, ByVal y As Long, ByVal lpString As Long, ByVal nCount As Long) As Long
Private Declare Function SelectObject Lib "gdi32" (ByVal hdc As Long, ByVal hObject As Long) As Long
Private lngMouseDownX As Long
Private lngMouseDownY As Long
Private strFontName As String
Private lngFontSize As Long
Private mstrMarkupText As String
Private Sub Form_Load()
lngFontSize = 20
strFontName = "ËÎÌå"
lngMouseDownX = 50
lngMouseDownY = 150
End Sub
Private Sub Text1_Change()
Dim hct As Long
Dim ll As Long
Dim len5 As Long
Dim str5() As Byte
Dim hwnd As Long
Dim GetCompositionResult As String
hwnd = Screen.ActiveForm.hwnd
GetCompositionResult = ""
hct = ImmGetContext(hwnd)
If hct = 0 Then
Exit Sub
End If
'Get the size of the result string
ll = ImmGetCompositionString(hct, GCS_RESULTSTR, vbNullString, 0)
If ll = 0 Then
'Call DrawMarkupText(Me.hDC, strFontName, lngFontSize, KeyCode, lngMouseDownX, lngMouseDownY)
ElseIf ll > 0 Then
'lstrText = ""
ReDim str5(0 To ll - 1)
len5 = ImmGetCompositionString(hct, GCS_RESULTSTR, str5(0), ll)
GetCompositionResult = StrConv(str5, vbUnicode)
End If
ImmReleaseContext hwnd, hct
Debug.Print "'" & GetCompositionResult & "'"
Call CodeProjectDrawText(Me.hdc, strFontName, lngFontSize, GetCompositionResult, lngMouseDownX, lngMouseDownY)
End Sub
</pre>
So my logic is that VB is basically an exe application that just contains a textbox on a form. It then calls "CodeProjectDrawText()" function which is written in C code (an C dll) to draw Chinese character on the VB form. So the key is that my TextOut() api in C code is actually drawing the Chinese character out. Just a note, please don't get confused with the TextOut() api being just ASCII, it is really unicode TextOutW(). In my C project settings, the unicode flag is already set, so during TextOut() it is actually calling the TextOutW() instead of just TextOut().
I have tried by calling the same TextOutW()function in VB (writting this whole small app in VB instead of C)and it works fine, but because this drawing feature has to be in C code, I can't do this in VB
Thank you very much Iain for your suggestions, Your suggestions for "m_hFont is not inialised" makes sense, so I changed the order of the code just a little by moving the "_tcscpy(m_LogFont.lfFaceName, lpszFontName);" after "hFont = CreateFontLocal();" call... but my result is still the same.
I actually stepped through the code couple time already I monitored all the variables such as "lpszMultiByteText", "lpszFontName" and so on... all seems to be correct right before the TextOut()api. Well at least in memory they seem to be correct. When I watched the 2 variables in memory stack they all appear to be correct. I mean I see my selected font name, Chinese text that I entered. But after TextOut() I see other wrong Chinese character or garbage being displayed. So somewhere fonts or code page is still not sinked up. Anyway thanks for all the good imput guys!
Tian
|
|
|
|
|
Hello,
I'm looking for a way to check if a DLL is currently registered. I've found code to register one, namely regsvr32 in a shellexecute, or just using LoadLibrary, but nothing to find out if my DLL is already registered.
I could search the registry, but for time reasons I'd like to avoid this. Registering the DLL each time the application starts isn't an option because the user's machine permissions aren't known and have a good chance of being very strict.
Any suggestions are greatly appreciated.
|
|
|
|
|
Simply try to call CoGetClassObject passing the CLSID of your class object.
If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler.
-- Alfonso the Wise, 13th Century King of Castile.
This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong.
-- Iain Clarke
[My articles]
|
|
|
|
|
My project is C#, and i am using pinvoke for LookupPrivilegeValue.
For my test part i have enum all possible privleges on LookupPrivilegeValue.
When it came to SE_DEBUG_NAME, my Kaspersky Internet Security said:
"Project Name" belongs to group 'Low Restricted' is trying to set debug privileges.
I didn't even used AdjustTokenPrivileges
And I have API that was denied to run due to restriction, now it works. When i read SDK, this shoudnt happend. I am using XP SP3
|
|
|
|
|
When creating Doc/View MDI apps to have a file extension using the wizard, Visual C++ 6.0 and 2008 apps reuse the existing application when double clicking on multiple data files with the apps associated file association. The results appear the same for both "%1" and "/dde" appended to the end of the "command" key in the registry file association entry for the "open" verb for that file type.
However, the same type of app created using Visual C++ 2003 does not always behave "correctly" (assumes double clicking a document should open in the applcation instance or in a new instance if the applcation wasn't already running)
When the registry entry for the open verb contains the following text in the "command" keys default text...
"%1" works when double clicking document without app running. Fails with app running.
"/dde" does not open document when double clicking without app running (I get an instance of the app in task manager but I can't interact with the app on the desktop). Fails with app running.
Does anyone know what the trick is to get the file verbs and/or dde commands working with a Visual C++ 2003 Doc/View MDI application?
***************************************
Update:
It turns out I didn't have Visual Studio 2003, Service Pack 1 installed on this box I'm compiling with. This issue was specifically addressed as the OnDDEExecute() not getting handled correctly.
Stupid me.
modified on Friday, November 7, 2008 2:14 PM
|
|
|
|
|
Hallo
I am facing a problem that how can i disable a button in a MFC SDI application.
Thanks
Munna
|
|
|
|
|
What's your problem than using EnableWindow( FALSE )?
|
|
|
|
|
Call EnableWindow function of the CButton class.
Saurabh
|
|
|
|
|
Like this:
GetDlgItem(IDC_BUTTON1)->EnableWindow(FALSE);
|
|
|
|
|
I'm gonna use "LoadKeyboardLayout()" function. As you know, one of it's parameters is "LPCTSTR pwszKLID", that's a Pointer to the buffer that specifies the name of the input locale identifier to load. But all I've got is a variable of type HKL that's set to a specified language identifier.
I wonder how can I get a string acording to that "language identifier"?
Thank you masters!
modified on Friday, November 7, 2008 7:14 AM
|
|
|
|
|
Possibly this will help [^].
If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler.
-- Alfonso the Wise, 13th Century King of Castile.
This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong.
-- Iain Clarke
[My articles]
|
|
|
|
|
I wonder what could I we do without CPallini!
|
|
|
|
|
i have 1 menu n under that 2 menu item are there, whatever menu item i will select, for that menuitem a check mark should be displayed.for this i have done like:
pCmdUI->SetCheck(TRUE); for both menu items.
but it is not working.
thanks in advance
best regards,
anjali
|
|
|
|
|
Add the handler for WM_INITMENUPOPUP in your dialog class and copy the following code in that function.
CWnd::OnInitMenuPopup(pPopupMenu, nIndex, bSysMenu);
ASSERT(pPopupMenu != NULL);
CCmdUI state;
state.m_pMenu = pPopupMenu;
ASSERT(state.m_pOther == NULL);
ASSERT(state.m_pParentMenu == NULL);
HMENU hParentMenu;
if(AfxGetThreadState()->m_hTrackingMenu == pPopupMenu->m_hMenu)
state.m_pParentMenu = pPopupMenu;
else if((hParentMenu = ::GetMenu(m_hWnd)) != NULL)
{
CWnd* pParent = this;
if(pParent != NULL && (hParentMenu = ::GetMenu(pParent->m_hWnd)) != NULL)
{
int nIndexMax = ::GetMenuItemCount(hParentMenu);
for (int nIndex = 0; nIndex < nIndexMax; nIndex++)
{
if(::GetSubMenu(hParentMenu, nIndex) == pPopupMenu->m_hMenu)
{
state.m_pParentMenu = CMenu::FromHandle(hParentMenu);
break;
}
}
}
}
state.m_nIndexMax = pPopupMenu->GetMenuItemCount();
for(state.m_nIndex = 0; state.m_nIndex < state.m_nIndexMax; state.m_nIndex++)
{
state.m_nID = pPopupMenu->GetMenuItemID(state.m_nIndex);
if(state.m_nID == 0)
continue;
ASSERT(state.m_pOther == NULL);
ASSERT(state.m_pMenu != NULL);
if(state.m_nID == (UINT)-1)
{
state.m_pSubMenu = pPopupMenu->GetSubMenu(state.m_nIndex);
if(state.m_pSubMenu == NULL ||
(state.m_nID = state.m_pSubMenu->GetMenuItemID(0)) == 0 ||
state.m_nID == (UINT)-1)
{
continue;
}
state.DoUpdate(this, TRUE);
}
else
{
state.m_pSubMenu = NULL;
state.DoUpdate(this, FALSE);
}
UINT nCount = pPopupMenu->GetMenuItemCount();
if(nCount < state.m_nIndexMax)
{
state.m_nIndex -= (state.m_nIndexMax - nCount);
while(state.m_nIndex < nCount &&
pPopupMenu->GetMenuItemID(state.m_nIndex) == state.m_nID)
{
state.m_nIndex++;
}
}
state.m_nIndexMax = nCount;
}
-Saurabh
|
|
|
|
|
Command enablers don't get called for dialogs by default.
You can enable them by adding a handler for the undocumented
WM_KICKIDLE message, something like this:
ON_MESSAGE(WM_KICKIDLE,&CMyDlg::OnKickIdle)
...
LRESULT CMyDlg::OnKickIdle(WPARAM wp, LPARAM lp)
{
UpdateDialogControls(this, TRUE);
return 0;
}
WM_KICKIDLE for Updating MFC Dialog Controls[^]
Mark
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|
|
In general, (not just what you said here) using the undocumented functions, is ideal?
Could you please share your opinion regarding this?
|
|
|
|
|
I personally don't use undocumented system messages or functions.
In this case, it's part of MFC, which we all have the source code for.
WM_KICKIDLE has been around a long time and it's pretty unlikely it will
go away. Maybe they'll even document it some day
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|
|
Thank you for your reply
|
|
|
|
|
Hallo
I want to create a new view or a popup window against a button click and want to draw somthing at new window.
Thanks
Munna
|
|
|
|
|
When I compiled the following very simple "c" code in Release mode, VC++ 6.0 compiler is giving the INTERNAL COMPILER ERROR error. Can anybody tell me why this happens.
/*test.c*/
void main()
{
__int64 a=0, b=0;
do
{
int c = a-b ? a-b : 0;
b = c;
}while(b);
}
Thanks
Shino
|
|
|
|
|
Do you get any different result if you change the file's extension to CPP?
"Love people and use things, not love things and use people." - Unknown
"The brick walls are there for a reason...to stop the people who don't want it badly enough." - Randy Pausch
|
|
|
|
|
No problem. But still compiler is showing the same error.
|
|
|
|
|
What compiler are you using? Other than a C4244 warning, I compiled it just fine with VS6. Have you read this?
"Love people and use things, not love things and use people." - Unknown
"The brick walls are there for a reason...to stop the people who don't want it badly enough." - Randy Pausch
|
|
|
|
|