610 lines
14 KiB
C
610 lines
14 KiB
C
/*++
|
|
|
|
Copyright (c) 1992 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
dbcs.c
|
|
|
|
Abstract:
|
|
|
|
This module contains the code for console DBCS font dialog
|
|
|
|
Author:
|
|
|
|
kazum Feb-27-1995
|
|
|
|
Revision History:
|
|
|
|
--*/
|
|
|
|
#include "precomp.h"
|
|
#pragma hdrstop
|
|
|
|
|
|
#if defined(FE_SB)
|
|
|
|
SINGLE_LIST_ENTRY gTTFontList; // This list contain TTFONTLIST data.
|
|
|
|
|
|
UINT OEMCP;
|
|
BOOL gfFESystem;
|
|
|
|
|
|
WORD
|
|
ConvertStringToDec(
|
|
LPTSTR lpch,
|
|
LPTSTR *endptr
|
|
)
|
|
{
|
|
TCHAR ch;
|
|
WORD val = 0;
|
|
|
|
while ( (ch=*lpch) != TEXT('\0'))
|
|
{
|
|
if (TEXT('0') <= ch && ch <= TEXT('9'))
|
|
val = (val * 10) + (ch - TEXT('0'));
|
|
else
|
|
break;
|
|
|
|
lpch++;
|
|
}
|
|
|
|
if (endptr)
|
|
*endptr = lpch;
|
|
return val;
|
|
}
|
|
|
|
WORD
|
|
ConvertStringToHex(
|
|
LPTSTR lpch,
|
|
LPTSTR *endptr
|
|
)
|
|
{
|
|
TCHAR ch;
|
|
WORD val = 0;
|
|
|
|
while ( (ch=*lpch) != TEXT('\0'))
|
|
{
|
|
if (TEXT('0') <= ch && ch <= TEXT('9'))
|
|
val = (val << 4) + (ch - TEXT('0'));
|
|
else if (TEXT('A') <= ch && ch <= TEXT('F'))
|
|
val = (val << 4) + (ch - TEXT('A') + 10);
|
|
else if (TEXT('a') <= ch && ch <= TEXT('f'))
|
|
val = (val << 4) + (ch - TEXT('a') + 10);
|
|
else
|
|
break;
|
|
|
|
lpch++;
|
|
}
|
|
|
|
if (endptr)
|
|
*endptr = lpch;
|
|
return val;
|
|
}
|
|
|
|
|
|
NTSTATUS
|
|
MakeAltRasterFont(
|
|
UINT CodePage,
|
|
COORD *AltFontSize,
|
|
BYTE *AltFontFamily,
|
|
ULONG *AltFontIndex,
|
|
LPTSTR AltFaceName
|
|
)
|
|
{
|
|
DWORD i;
|
|
DWORD Find;
|
|
ULONG FontIndex;
|
|
COORD FontSize = FontInfo[DefaultFontIndex].Size;
|
|
COORD FontDelta;
|
|
BOOL fDbcsCharSet = IS_ANY_DBCS_CHARSET( CodePageToCharSet( CodePage ) );
|
|
|
|
FontIndex = 0;
|
|
Find = (DWORD)-1;
|
|
for (i=0; i < NumberOfFonts; i++)
|
|
{
|
|
if (!TM_IS_TT_FONT(FontInfo[i].Family) &&
|
|
IS_ANY_DBCS_CHARSET(FontInfo[i].tmCharSet) == fDbcsCharSet
|
|
)
|
|
{
|
|
FontDelta.X = (SHORT)abs(FontSize.X - FontInfo[i].Size.X);
|
|
FontDelta.Y = (SHORT)abs(FontSize.Y - FontInfo[i].Size.Y);
|
|
if (Find > (DWORD)(FontDelta.X + FontDelta.Y))
|
|
{
|
|
Find = (DWORD)(FontDelta.X + FontDelta.Y);
|
|
FontIndex = i;
|
|
}
|
|
}
|
|
}
|
|
|
|
*AltFontIndex = FontIndex;
|
|
_tcscpy(AltFaceName, FontInfo[*AltFontIndex].FaceName);
|
|
*AltFontSize = FontInfo[*AltFontIndex].Size;
|
|
*AltFontFamily = FontInfo[*AltFontIndex].Family;
|
|
|
|
DBGFONTS(("MakeAltRasterFont : AltFontIndex = %ld\n", *AltFontIndex));
|
|
|
|
return STATUS_SUCCESS;
|
|
}
|
|
|
|
NTSTATUS
|
|
InitializeDbcsMisc(
|
|
VOID
|
|
)
|
|
{
|
|
HANDLE hkRegistry = NULL;
|
|
NTSTATUS Status;
|
|
WCHAR awchValue[ 512 ];
|
|
WCHAR awchData[ 512 ];
|
|
DWORD dwIndex;
|
|
LPWSTR pwsz;
|
|
|
|
gTTFontList.Next = NULL;
|
|
|
|
Status = MyRegOpenKey(NULL,
|
|
MACHINE_REGISTRY_CONSOLE_TTFONT,
|
|
&hkRegistry);
|
|
if (!NT_SUCCESS( Status )) {
|
|
DBGPRINT(("CONSRV: NtOpenKey failed %ws\n", MACHINE_REGISTRY_CONSOLE));
|
|
}
|
|
else {
|
|
LPTTFONTLIST pTTFontList;
|
|
|
|
for( dwIndex = 0; ; dwIndex++) {
|
|
Status = MyRegEnumValue(hkRegistry,
|
|
dwIndex,
|
|
sizeof(awchValue), (LPWSTR)&awchValue,
|
|
sizeof(awchData), (PBYTE)&awchData);
|
|
if (!NT_SUCCESS( Status )) {
|
|
break;
|
|
}
|
|
|
|
pTTFontList = LocalAlloc(LPTR, sizeof(TTFONTLIST));
|
|
if (pTTFontList == NULL) {
|
|
break;
|
|
}
|
|
|
|
pTTFontList->List.Next = NULL;
|
|
pTTFontList->CodePage = ConvertStringToDec(awchValue, NULL);
|
|
pwsz = awchData;
|
|
if (*pwsz == BOLD_MARK) {
|
|
pTTFontList->fDisableBold = TRUE;
|
|
pwsz++;
|
|
}
|
|
else
|
|
pTTFontList->fDisableBold = FALSE;
|
|
_tcscpy(pTTFontList->FaceName1, pwsz);
|
|
|
|
pwsz += _tcslen(pwsz) + 1;
|
|
if (*pwsz == BOLD_MARK) {
|
|
pTTFontList->fDisableBold = TRUE;
|
|
pwsz++;
|
|
}
|
|
_tcscpy(pTTFontList->FaceName2, pwsz);
|
|
|
|
PushEntryList(&gTTFontList, &(pTTFontList->List));
|
|
}
|
|
|
|
NtClose(hkRegistry);
|
|
}
|
|
|
|
ASSERT(OEMCP != 0); // OEMCP must be initialized so far by CPL_INIT
|
|
ASSERT(IsFarEastCP(OEMCP) == gfFESystem);
|
|
|
|
return STATUS_SUCCESS;
|
|
}
|
|
|
|
BYTE
|
|
CodePageToCharSet(
|
|
UINT CodePage
|
|
)
|
|
{
|
|
CHARSETINFO csi;
|
|
|
|
if (!TranslateCharsetInfo((DWORD *)IntToPtr(CodePage), &csi, TCI_SRCCODEPAGE))
|
|
csi.ciCharset = OEM_CHARSET;
|
|
|
|
return (BYTE)csi.ciCharset;
|
|
}
|
|
|
|
LPTTFONTLIST
|
|
SearchTTFont(
|
|
LPTSTR ptszFace,
|
|
BOOL fCodePage,
|
|
UINT CodePage
|
|
)
|
|
{
|
|
PSINGLE_LIST_ENTRY pTemp = gTTFontList.Next;
|
|
|
|
if (ptszFace) {
|
|
while (pTemp != NULL) {
|
|
LPTTFONTLIST pTTFontList = (LPTTFONTLIST)pTemp;
|
|
|
|
if (wcscmp(ptszFace, pTTFontList->FaceName1) == 0 ||
|
|
wcscmp(ptszFace, pTTFontList->FaceName2) == 0 ) {
|
|
if (fCodePage)
|
|
if (pTTFontList->CodePage == CodePage )
|
|
return pTTFontList;
|
|
else
|
|
return NULL;
|
|
else
|
|
return pTTFontList;
|
|
}
|
|
|
|
pTemp = pTemp->Next;
|
|
}
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
BOOL
|
|
IsAvailableTTFont(
|
|
LPTSTR ptszFace
|
|
)
|
|
{
|
|
if (SearchTTFont(ptszFace, FALSE, 0))
|
|
return TRUE;
|
|
else
|
|
return FALSE;
|
|
}
|
|
|
|
BOOL
|
|
IsAvailableTTFontCP(
|
|
LPTSTR ptszFace,
|
|
UINT CodePage
|
|
)
|
|
{
|
|
if (SearchTTFont(ptszFace, TRUE, CodePage))
|
|
return TRUE;
|
|
else
|
|
return FALSE;
|
|
}
|
|
|
|
BOOL
|
|
IsDisableBoldTTFont(
|
|
LPTSTR ptszFace
|
|
)
|
|
{
|
|
LPTTFONTLIST pTTFontList;
|
|
|
|
pTTFontList = SearchTTFont(ptszFace, FALSE, 0);
|
|
if (pTTFontList != NULL)
|
|
return pTTFontList->fDisableBold;
|
|
else
|
|
return FALSE;
|
|
}
|
|
|
|
LPTSTR
|
|
GetAltFaceName(
|
|
LPTSTR ptszFace
|
|
)
|
|
{
|
|
LPTTFONTLIST pTTFontList;
|
|
|
|
pTTFontList = SearchTTFont(ptszFace, FALSE, 0);
|
|
if (pTTFontList != NULL) {
|
|
if (wcscmp(ptszFace, pTTFontList->FaceName1) == 0) {
|
|
return pTTFontList->FaceName2;
|
|
}
|
|
if (wcscmp(ptszFace, pTTFontList->FaceName2) == 0) {
|
|
return pTTFontList->FaceName1;
|
|
}
|
|
return NULL;
|
|
}
|
|
else
|
|
return NULL;
|
|
}
|
|
|
|
NTSTATUS
|
|
DestroyDbcsMisc(
|
|
VOID
|
|
)
|
|
{
|
|
while (gTTFontList.Next != NULL) {
|
|
LPTTFONTLIST pTTFontList = (LPTTFONTLIST)PopEntryList(&gTTFontList);
|
|
|
|
if (pTTFontList != NULL)
|
|
LocalFree(pTTFontList);
|
|
}
|
|
|
|
return STATUS_SUCCESS;
|
|
}
|
|
|
|
typedef struct _LC_List {
|
|
struct _LC_List* Next;
|
|
BOOL FindFlag;
|
|
TCHAR LC_String[9];
|
|
} LC_List, *PLC_List;
|
|
|
|
static PLC_List LocaleList = NULL;
|
|
|
|
BOOL CALLBACK
|
|
EnumProc(
|
|
LPTSTR LC_String
|
|
)
|
|
{
|
|
PLC_List TmpList;
|
|
|
|
if (_tcslen(LC_String) <= (sizeof(LocaleList->LC_String)/sizeof(TCHAR))-1)
|
|
{
|
|
TmpList = (PLC_List)&LocaleList;
|
|
|
|
while(TmpList->Next != NULL)
|
|
TmpList = TmpList->Next;
|
|
|
|
TmpList->Next = LocalAlloc(LPTR, sizeof(LC_List));
|
|
if (TmpList->Next != NULL)
|
|
{
|
|
TmpList = TmpList->Next;
|
|
_tcscpy(TmpList->LC_String, LC_String);
|
|
}
|
|
}
|
|
return TRUE;
|
|
}
|
|
|
|
|
|
int
|
|
LanguageListCreate(
|
|
HWND hDlg,
|
|
UINT CodePage
|
|
)
|
|
|
|
/*++
|
|
|
|
Initializes the Language list by enumerating all Locale Information.
|
|
|
|
Returns
|
|
--*/
|
|
|
|
{
|
|
HWND hWndLanguageCombo;
|
|
HANDLE hkRegistry = NULL;
|
|
NTSTATUS Status;
|
|
WCHAR awchValue[ 512 ];
|
|
WCHAR awchData[ 512 ];
|
|
DWORD dwIndex;
|
|
PLC_List TmpList;
|
|
WORD LangID;
|
|
LCID Locale;
|
|
int cchData;
|
|
LONG lListIndex;
|
|
UINT cp;
|
|
BOOL fRet;
|
|
CPINFOEX cpinfo;
|
|
|
|
/*
|
|
* Enumrate system locale information
|
|
*/
|
|
EnumSystemLocales( EnumProc, CP_INSTALLED );
|
|
|
|
/*
|
|
* Enumrate registory key
|
|
*/
|
|
Status = MyRegOpenKey(NULL,
|
|
MACHINE_REGISTRY_CONSOLE_NLS,
|
|
&hkRegistry);
|
|
if (!NT_SUCCESS( Status )) {
|
|
DBGPRINT(("CONSRV: NtOpenKey failed %ws\n", MACHINE_REGISTRY_CONSOLE));
|
|
}
|
|
else {
|
|
for( dwIndex = 0; ; dwIndex++)
|
|
{
|
|
Status = MyRegEnumValue(hkRegistry,
|
|
dwIndex,
|
|
sizeof(awchValue), (LPWSTR)&awchValue,
|
|
sizeof(awchData), (PBYTE)&awchData);
|
|
if (!NT_SUCCESS( Status ))
|
|
{
|
|
break;
|
|
}
|
|
|
|
TmpList = (PLC_List)&LocaleList;
|
|
while(TmpList->Next != NULL)
|
|
{
|
|
TmpList = TmpList->Next;
|
|
if (_tcscmp(awchValue, TmpList->LC_String) == 0)
|
|
{
|
|
TmpList->FindFlag = TRUE;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
NtClose(hkRegistry);
|
|
|
|
}
|
|
|
|
/*
|
|
* Create ComboBox items
|
|
*/
|
|
hWndLanguageCombo = GetDlgItem(hDlg, IDD_LANGUAGELIST);
|
|
SendMessage(hWndLanguageCombo, CB_RESETCONTENT, 0, 0L);
|
|
|
|
TmpList = (PLC_List)&LocaleList;
|
|
while(TmpList->Next != NULL)
|
|
{
|
|
TmpList = TmpList->Next;
|
|
|
|
if (TmpList->FindFlag)
|
|
{
|
|
LangID = ConvertStringToHex(TmpList->LC_String, NULL);
|
|
Locale = MAKELCID( LangID, SORT_DEFAULT );
|
|
|
|
cchData = GetLocaleInfo(Locale, LOCALE_IDEFAULTCODEPAGE,
|
|
awchData, sizeof(awchData)/sizeof(TCHAR));
|
|
if (cchData)
|
|
{
|
|
awchData[cchData] = TEXT('\0');
|
|
cp = ConvertStringToDec(awchData, NULL);
|
|
|
|
if ( (IS_ANY_DBCS_CHARSET(CodePageToCharSet(cp)) && GetOEMCP() == cp) ||
|
|
(!IS_ANY_DBCS_CHARSET(CodePageToCharSet(cp))) ) {
|
|
|
|
fRet = GetCPInfoEx(cp, 0, &cpinfo);
|
|
if (fRet) {
|
|
lListIndex = (LONG)SendMessage(hWndLanguageCombo, CB_ADDSTRING, 0, (LPARAM)cpinfo.CodePageName);
|
|
SendMessage(hWndLanguageCombo, CB_SETITEMDATA, (DWORD)lListIndex, cp);
|
|
|
|
if (CodePage == cp) {
|
|
SendMessage(hWndLanguageCombo, CB_SETCURSEL, lListIndex, 0L);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
{
|
|
PLC_List Tmp;
|
|
|
|
TmpList = (PLC_List)&LocaleList;
|
|
while(TmpList->Next != NULL)
|
|
{
|
|
Tmp = TmpList;
|
|
TmpList = TmpList->Next;
|
|
|
|
if (Tmp != (PLC_List)&LocaleList)
|
|
LocalFree(Tmp);
|
|
}
|
|
|
|
LocaleList = NULL;
|
|
}
|
|
|
|
|
|
/*
|
|
* Get the LocaleIndex from the currently selected item.
|
|
* (i will be LB_ERR if no currently selected item).
|
|
*/
|
|
lListIndex = (LONG)SendMessage(hWndLanguageCombo, CB_GETCURSEL, 0, 0L);
|
|
return (LONG)SendMessage(hWndLanguageCombo, CB_GETITEMDATA, lListIndex, 0L);
|
|
}
|
|
|
|
|
|
// v-HirShi Nov.20.1996
|
|
int
|
|
LanguageDisplay(
|
|
HWND hDlg,
|
|
UINT CodePage
|
|
)
|
|
|
|
/*++
|
|
|
|
Display the Language .
|
|
|
|
Returns
|
|
--*/
|
|
|
|
{
|
|
HWND hWndLanguageDisp;
|
|
HANDLE hkRegistry = NULL;
|
|
NTSTATUS Status;
|
|
WCHAR awchValue[ 512 ];
|
|
WCHAR awchData[ 512 ];
|
|
DWORD dwIndex;
|
|
PLC_List TmpList;
|
|
WORD LangID;
|
|
LCID Locale;
|
|
int cchData;
|
|
LONG lListIndex;
|
|
UINT cp;
|
|
BOOL fRet;
|
|
CPINFOEX cpinfo;
|
|
|
|
/*
|
|
* Enumrate system locale information
|
|
*/
|
|
EnumSystemLocales( EnumProc, CP_INSTALLED );
|
|
|
|
/*
|
|
* Enumrate registory key
|
|
*/
|
|
Status = MyRegOpenKey(NULL,
|
|
MACHINE_REGISTRY_CONSOLE_NLS,
|
|
&hkRegistry);
|
|
if (!NT_SUCCESS( Status )) {
|
|
DBGPRINT(("CONSRV: NtOpenKey failed %ws\n", MACHINE_REGISTRY_CONSOLE));
|
|
}
|
|
else {
|
|
for( dwIndex = 0; ; dwIndex++)
|
|
{
|
|
Status = MyRegEnumValue(hkRegistry,
|
|
dwIndex,
|
|
sizeof(awchValue), (LPWSTR)&awchValue,
|
|
sizeof(awchData), (PBYTE)&awchData);
|
|
if (!NT_SUCCESS( Status ))
|
|
{
|
|
break;
|
|
}
|
|
|
|
TmpList = (PLC_List)&LocaleList;
|
|
while(TmpList->Next != NULL)
|
|
{
|
|
TmpList = TmpList->Next;
|
|
if (_tcscmp(awchValue, TmpList->LC_String) == 0)
|
|
{
|
|
TmpList->FindFlag = TRUE;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
NtClose(hkRegistry);
|
|
|
|
}
|
|
|
|
/*
|
|
* Display Language
|
|
*/
|
|
|
|
TmpList = (PLC_List)&LocaleList;
|
|
while(TmpList->Next != NULL)
|
|
{
|
|
TmpList = TmpList->Next;
|
|
|
|
if (TmpList->FindFlag)
|
|
{
|
|
LangID = ConvertStringToHex(TmpList->LC_String, NULL);
|
|
Locale = MAKELCID( LangID, SORT_DEFAULT );
|
|
|
|
cchData = GetLocaleInfo(Locale, LOCALE_IDEFAULTCODEPAGE,
|
|
awchData, sizeof(awchData)/sizeof(TCHAR));
|
|
if (cchData)
|
|
{
|
|
awchData[cchData] = TEXT('\0');
|
|
cp = ConvertStringToDec(awchData, NULL);
|
|
|
|
fRet = GetCPInfoEx(cp, 0, &cpinfo);
|
|
if (fRet) {
|
|
if (CodePage == cp) {
|
|
hWndLanguageDisp = GetDlgItem(hDlg, IDD_LANGUAGE);
|
|
SetWindowText(hWndLanguageDisp, cpinfo.CodePageName);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
{
|
|
PLC_List Tmp;
|
|
|
|
TmpList = (PLC_List)&LocaleList;
|
|
while(TmpList->Next != NULL)
|
|
{
|
|
Tmp = TmpList;
|
|
TmpList = TmpList->Next;
|
|
|
|
if (Tmp != (PLC_List)&LocaleList)
|
|
LocalFree(Tmp);
|
|
}
|
|
|
|
LocaleList = NULL;
|
|
}
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
|
|
#endif // FE_SB
|