⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 optionsfont.c

📁 支持Unicode及Uniscribe的多语言输入的文本编辑器源码。
💻 C
📖 第 1 页 / 共 2 页
字号:
//
//	Neatpad
//	OptionsFont.c
//
//	www.catch22.net
//

#define _CRT_SECURE_NO_DEPRECATE
#define _CRT_NON_CONFORMING_SWPRINTFS
#define _WIN32_WINNT 0x501
#define STRICT

#include <windows.h>
#include <tchar.h>
#include <commctrl.h>
#include <shellapi.h>
#include "Neatpad.h"
#include "..\TextView\TextView.h"
#include "resource.h"

#include <uxtheme.h>
#include <tmschema.h>

COLORREF LightenRGB(COLORREF rgbColor, int amt);

#define MSG_UPDATE_PREVIEW (WM_USER+1)

static HFONT g_hBoldFont;
static HFONT g_hNormalFont;
static HICON g_hIcon2;			// TrueType icon
static HICON g_hIcon3;			// OpenType icon
static int	 g_nFontHeight;

static COLORREF g_crPreviewFG;
static COLORREF g_crPreviewBG;
static COLORREF g_rgbTempColourList[TXC_MAX_COLOURS];
static LONG		g_tempFontSmoothing;

COLORREF g_rgbAutoColourList[TXC_MAX_COLOURS] = 
{
	SYSCOL(COLOR_WINDOWTEXT),							// foreground
	SYSCOL(COLOR_WINDOW),								// background
	SYSCOL(COLOR_HIGHLIGHTTEXT),						// selected text
	SYSCOL(COLOR_HIGHLIGHT),							// selection
	SYSCOL(COLOR_WINDOWTEXT),							// inactive selected text
	SYSCOL(COLOR_3DFACE),								// inactive selection
	SYSCOL(COLOR_3DFACE),								// selection margin#1
	SYSCOL(COLOR_3DHIGHLIGHT),							// selection margin#2
	MIXED_SYSCOL(COLOR_3DSHADOW, COLOR_3DDKSHADOW),		// line number text
	MIXED_SYSCOL2(COLOR_3DFACE, COLOR_WINDOW),			// line number bg
	SYSCOL(COLOR_WINDOWTEXT),							// long line text
	MIXED_SYSCOL(COLOR_3DFACE, COLOR_WINDOW),			// long-line background
	SYSCOL(COLOR_WINDOWTEXT),							// current line text
	RGB(230,240,255),									// current line background
};


#ifndef ODS_NOFOCUSRECT
#define ODS_NOFOCUSRECT     0x0200
#endif

#define COLORECT_WIDTH  32
#define COLORECT_OFFSET 4

#define NUM_DEFAULT_COLOURS 17

struct _CUSTCOL
{
	COLORREF cr;
	TCHAR *szName;

} CUSTCOL[NUM_DEFAULT_COLOURS] = 
{
	{ RGB(255,255,255),	_T("Automatic") },
	{ RGB(0,0,0),		_T("Black") },
	{ RGB(255,255,255),	_T("White") },
	{ RGB(128, 0, 0),	_T("Maroon") },
	{ RGB(0, 128,0),	_T("Dark Green") },
	{ RGB(128,128,0),	_T("Olive") },
	{ RGB(0,0,128),		_T("Dark Blue") },
	{ RGB(128,0,128),	_T("Purple") },
	{ RGB(0,128,128),	_T("Aquamarine") },
	{ RGB(196,196,196),	_T("Light Grey") },
	{ RGB(128,128,128),	_T("Dark Grey") },
	{ RGB(255,0,0),		_T("Red") },
	{ RGB(0,255,0),		_T("Green") },
	{ RGB(255,255,0),	_T("Yellow") },
	{ RGB(0,0,255),		_T("Blue") },
	{ RGB(255,0,255),	_T("Magenta") },
	{ RGB(0,255,255),	_T("Cyan") },
//	{ RGB(255,255,255),	"Custom..." },
};

//
//	Convert from logical-units to point-sizes
//
int LogicalToPoints(int nLogicalSize)
{
	HDC hdc      = GetDC(0);
	int size     = MulDiv(nLogicalSize, 72, GetDeviceCaps(hdc, LOGPIXELSY));

	ReleaseDC(0, hdc);

	return size;
}

DWORD GetCurrentComboData(HWND hwnd, UINT uCtrl)
{
	int idx = SendDlgItemMessage(hwnd, uCtrl, CB_GETCURSEL, 0, 0);
	return    SendDlgItemMessage(hwnd, uCtrl, CB_GETITEMDATA, idx == -1 ? 0 : idx, 0);
}

DWORD GetCurrentListData(HWND hwnd, UINT uCtrl)
{
	int idx = SendDlgItemMessage(hwnd, uCtrl, LB_GETCURSEL, 0, 0);
	return    SendDlgItemMessage(hwnd, uCtrl, LB_GETITEMDATA, idx == -1 ? 0 : idx, 0);
}

DWORD AddComboStringWithData(HWND hwnd, UINT uCtrl, TCHAR *szText, DWORD data)
{
	int idx = SendDlgItemMessage(hwnd, uCtrl, CB_ADDSTRING, 0, (LONG)szText);
	return    SendDlgItemMessage(hwnd, uCtrl, CB_SETITEMDATA, idx, data);
}

//
//	Font-enumeration callback
//
int CALLBACK EnumFontNames(ENUMLOGFONTEX *lpelfe, NEWTEXTMETRICEX *lpntme, DWORD FontType, LPARAM lParam)
{
	HWND hwndCombo = (HWND)lParam;
	TCHAR *pszName  = lpelfe->elfLogFont.lfFaceName;

		if(pszName[0] == '@')
			return 1;
	
	// make sure font doesn't already exist in our list
	if(SendMessage(hwndCombo, CB_FINDSTRING, 0, (LPARAM)pszName) == CB_ERR)
	{
		int		idx;
		BOOL	fFixed;
		int		fTrueType;		// 0 = normal, 1 = TrueType, 2 = OpenType

		// add the font
		idx = SendMessage(hwndCombo, CB_ADDSTRING, 0, (LPARAM)pszName);

		// record the font's attributes (Fixedwidth and Truetype)
		fFixed		= (lpelfe->elfLogFont.lfPitchAndFamily & FIXED_PITCH) ? TRUE : FALSE;
		fTrueType	= (lpelfe->elfLogFont.lfOutPrecision == OUT_STROKE_PRECIS) ? TRUE : FALSE;
		fTrueType	= (lpntme->ntmTm.ntmFlags & NTM_TT_OPENTYPE) ? 2 : fTrueType;
			
		// store this information in the list-item's userdata area
		SendMessage(hwndCombo, CB_SETITEMDATA, idx, MAKEWPARAM(fFixed, fTrueType));
	}

	return 1;
}

//
//	Initialize the font-list by enumeration all system fonts
//
void FillFontComboList(HWND hwndCombo)
{
	HDC		hdc = GetDC(hwndCombo);
	LOGFONT lf;
	int		idx;

	SendMessage(hwndCombo, WM_SETFONT, (WPARAM)g_hNormalFont, 0);

	lf.lfCharSet			= ANSI_CHARSET;	// DEFAULT_CHARSET;
	lf.lfFaceName[0]		= '\0';			// all fonts
	lf.lfPitchAndFamily		= 0;

	// store the list of fonts in the combo
	EnumFontFamiliesEx(hdc, &lf, (FONTENUMPROC)EnumFontNames, (LPARAM)hwndCombo, 0);

	ReleaseDC(hwndCombo, hdc);

	// select current font in list
	idx = SendMessage(hwndCombo, CB_FINDSTRING, 0, (LPARAM)g_szFontName);
	SendMessage(hwndCombo, CB_SETCURSEL, idx, 0);
}

/*
//
//	Could be used to fill a ListView with a list
//	of file-types and their associated icons
//
void FillFileTypeList(HWND hwnd)
{
	LVITEM lvi = { LVIF_TEXT|LVIF_IMAGE };
	SHFILEINFO shfi = { 0 };
	HIMAGELIST hImgList;
	int i;

	char *lookup[] = 
	{
		".asm", ".c", ".cpp", ".cs", ".js", 0
	};

	for(i = 0; lookup[i]; i++)
	{
		ZeroMemory(&shfi, sizeof(shfi));
		hImgList = (HIMAGELIST)SHGetFileInfo(lookup[i], FILE_ATTRIBUTE_NORMAL, &shfi, sizeof(shfi),  
			SHGFI_TYPENAME|SHGFI_ICON |SHGFI_USEFILEATTRIBUTES|SHGFI_SMALLICON|SHGFI_SYSICONINDEX);

		ListView_SetImageList(hwnd, hImgList, LVSIL_SMALL);

		lvi.iItem		= 0;
		lvi.iSubItem	= 0;
		lvi.pszText		= shfi.szTypeName;//lookup[i];
		lvi.iImage		= shfi.iIcon;
	
		ListView_InsertItem(hwnd, &lvi);
	}
}*/

void SetComboItemHeight(HWND hwndCombo, int nMinHeight)
{
	TEXTMETRIC	tm;
	HDC			hdc	 = GetDC(hwndCombo);
	HANDLE		hold = SelectObject(hdc, g_hNormalFont);
	
	// item height must fit the font+smallicon height
	GetTextMetrics(hdc, &tm);
	nMinHeight = max(tm.tmHeight, nMinHeight);

	SelectObject(hdc, hold);
	ReleaseDC(hwndCombo, hdc);

	SendMessage(hwndCombo, CB_SETITEMHEIGHT, -1, nMinHeight);
	SendMessage(hwndCombo, CB_SETITEMHEIGHT, 0, nMinHeight);
}

//
//	Draw a colour rectangle with border
//
void PaintFrameRect(HDC hdc, RECT *rect, COLORREF border, COLORREF fill)
{
	HBRUSH   hbrFill	= CreateSolidBrush(fill);
	HBRUSH   hbrBorder	= CreateSolidBrush(border);

	FrameRect(hdc, rect, hbrBorder);
	InflateRect(rect, -1, -1);
	FillRect(hdc, rect,  hbrFill);
	InflateRect(rect, 1, 1);

	DeleteObject(hbrFill);
	DeleteObject(hbrBorder);
}

void DrawItem_DefaultColours(DRAWITEMSTRUCT *dis)
{
	if(dis->itemState & ODS_DISABLED)
	{
		SetTextColor(dis->hDC, GetSysColor(COLOR_3DSHADOW));
		SetBkColor(dis->hDC,   GetSysColor(COLOR_3DFACE));
	}
	else
	{
		if((dis->itemState & ODS_SELECTED))
		{
			SetTextColor(dis->hDC,  GetSysColor(COLOR_HIGHLIGHTTEXT));
			SetBkColor(dis->hDC,	GetSysColor(COLOR_HIGHLIGHT));
		}
		else
		{
			SetTextColor(dis->hDC, GetSysColor(COLOR_WINDOWTEXT));
			SetBkColor(dis->hDC,   GetSysColor(COLOR_WINDOW));
		}
	}
}

//
//	Fontlist owner-draw 
//
BOOL FontCombo_DrawItem(HWND hwnd, DRAWITEMSTRUCT *dis)
{
	TCHAR		szText[100];
	
	BOOL		fFixed		= LOWORD(dis->itemData);
	BOOL		fTrueType	= HIWORD(dis->itemData);

	TEXTMETRIC	tm;
	int			xpos, ypos;
	HANDLE		hOldFont;

	if(dis->itemAction & ODA_FOCUS && !(dis->itemState & ODS_NOFOCUSRECT))
	{
		DrawFocusRect(dis->hDC, &dis->rcItem);
		return TRUE;
	}

	/*{
		HTHEME hTheme = 	OpenThemeData(hwnd, L"combobox");
		RECT rc;
		HDC hdc=GetDC(GetParent(hwnd));
		CopyRect(&rc, &dis->rcItem);
		InflateRect(&rc, 3, 3);
		//GetClientRect(hwnd, &rc);
		//rc.bottom = rc.top + 22;

		//DrawThemeBackground(
		//	hTheme, 
		//	dis->hDC, 
		//	4,//CP_DROPDOWNBUTTON, 
		//	CBXS_HOT,//CBXS_NORMAL, 
		//	&rc, 
		//	&rc);

		CloseThemeData(hTheme);
		ReleaseDC(GetParent(hwnd),hdc);
		return TRUE;
	}*/

	//
	//	Get the item text
	//
	if(dis->itemID == -1)
		SendMessage(dis->hwndItem, WM_GETTEXT, 0, (LONG)szText);
	else
		SendMessage(dis->hwndItem, CB_GETLBTEXT, dis->itemID, (LONG)szText);
	
	//
	//	Set text colour and background based on current state
	//
	DrawItem_DefaultColours(dis);

	// set the font: BOLD for fixed-width, NORMAL for 'normal'
	hOldFont = SelectObject(dis->hDC, fFixed ? g_hBoldFont : g_hNormalFont);
	GetTextMetrics(dis->hDC, &tm);

	ypos = dis->rcItem.top  + (dis->rcItem.bottom-dis->rcItem.top-tm.tmHeight)/2;
	xpos = dis->rcItem.left + 20;
	
	// draw the text
	ExtTextOut(dis->hDC, xpos, ypos,
		ETO_CLIPPED|ETO_OPAQUE, &dis->rcItem, szText, _tcslen(szText), 0);

	// draw a 'TT' icon if the font is TRUETYPE
	if(fTrueType)
		DrawIconEx(dis->hDC, dis->rcItem.left+2, dis->rcItem.top, g_hIcon2,16, 16, 0, 0, DI_NORMAL);
	//else if(fTrueType == 2)
	//	DrawIconEx(dis->hDC, dis->rcItem.left+2, dis->rcItem.top, g_hIcon3,16, 16, 0, 0, DI_NORMAL);

	SelectObject(dis->hDC, hOldFont);

	// draw the focus rectangle
	if((dis->itemState & ODS_FOCUS) && !(dis->itemState & ODS_NOFOCUSRECT))
	{
		DrawFocusRect(dis->hDC, &dis->rcItem);
	}

	return TRUE;
}

//
//	Combobox must have the CBS_HASSTRINGS style set!!
//	
BOOL ColourCombo_DrawItem(HWND hwnd, UINT uCtrlId, DRAWITEMSTRUCT *dis, BOOL fSelectImage)
{
	RECT		rect	= dis->rcItem;
	int			boxsize = (dis->rcItem.bottom - dis->rcItem.top) - 4;			
	int			xpos;
	int			ypos;
	TEXTMETRIC	tm;
	TCHAR		szText[80];
	HANDLE		hOldFont;
	
	if(!fSelectImage)
		rect.left += boxsize + 4;

	if(dis->itemAction & ODA_FOCUS && !(dis->itemState & ODS_NOFOCUSRECT))
	{
		DrawFocusRect(dis->hDC, &rect);
		return TRUE;
	}
	
	//
	//	Get the item text
	//
	if(dis->itemID == -1)
		SendMessage(dis->hwndItem, WM_GETTEXT, 0, (LONG)szText);
	else
		SendMessage(dis->hwndItem, CB_GETLBTEXT, dis->itemID, (LONG)szText);
	
	//
	//	Set text colour and background based on current state
	//
	DrawItem_DefaultColours(dis);
	
	//
	//	Draw the text (centered vertically)
	//	
	hOldFont = SelectObject(dis->hDC, g_hNormalFont);

	GetTextMetrics(dis->hDC, &tm);
	ypos = dis->rcItem.top  + (dis->rcItem.bottom - dis->rcItem.top - tm.tmHeight) / 2;
	xpos = dis->rcItem.left + boxsize + 4 + 4;
	
	ExtTextOut(dis->hDC, xpos, ypos, 
		ETO_CLIPPED|ETO_OPAQUE, &rect, szText, lstrlen(szText), 0);
	
	if((dis->itemState & ODS_FOCUS) && !(dis->itemState & ODS_NOFOCUSRECT))
	{
		DrawFocusRect(dis->hDC, &rect);
	}
	
	// 
	//	Paint the colour rectangle
	//	
	rect = dis->rcItem;
	InflateRect(&rect, -2, -2);
	rect.right = rect.left + boxsize;
	
	if(dis->itemState & ODS_DISABLED)
		PaintFrameRect(dis->hDC, &rect, GetSysColor(COLOR_3DSHADOW), GetSysColor(COLOR_3DFACE));
	else
		PaintFrameRect(dis->hDC, &rect, RGB(0,0,0), REALIZE_SYSCOL(dis->itemData));
	
	
	return TRUE;
}

int CALLBACK EnumFontSizes(ENUMLOGFONTEX *lpelfe, NEWTEXTMETRICEX *lpntme, DWORD FontType, LPARAM lParam)
{
	static int ttsizes[] = { 8, 9, 10, 11, 12, 14, 16, 18, 20, 22, 24, 26, 28, 36, 48, 72 };
	TCHAR ach[100];

	BOOL fTrueType = (lpelfe->elfLogFont.lfOutPrecision == OUT_STROKE_PRECIS) ? TRUE : FALSE;

	HWND hwndCombo = (HWND)lParam;
	int  i, count, idx;

	if(fTrueType)
	{
		for(i = 0; i < (sizeof(ttsizes) / sizeof(ttsizes[0])); i++)
		{
			_stprintf(ach, _T("%d"), ttsizes[i]);
			idx = SendMessage(hwndCombo, CB_ADDSTRING, 0, (LPARAM)ach);
			SendMessage(hwndCombo, CB_SETITEMDATA, idx, ttsizes[i]);
			//nFontSizes[i] = ttsizes[i];
		}
		//nNumFontSizes = i;
		return 0;
	}
	else
	{
		int size = LogicalToPoints(lpntme->ntmTm.tmHeight);
		_stprintf(ach, _T("%d"), size);

		count = SendMessage(hwndCombo, CB_GETCOUNT, 0, 0);

		for(i = 0; i < count; i++)
		{
			if(SendMessage(hwndCombo, CB_GETITEMDATA, 0, 0) == size)
				break;
		}
		
		if(i >= count)
		{
			idx = SendMessage(hwndCombo, CB_ADDSTRING, 0, (LPARAM)ach);
			SendMessage(hwndCombo, CB_SETITEMDATA, idx, size);
		}

		return 1;	
	}

	return 1;
}


void InitSizeList(HWND hwnd)
{
	LOGFONT lf = { 0 };
	HDC hdc = GetDC(hwnd);
	
	// get current font size
	int cursize = GetDlgItemInt(hwnd, IDC_SIZELIST, 0, 0);
		
	int item   = SendDlgItemMessage(hwnd, IDC_FONTLIST, CB_GETCURSEL, 0, 0);
	int i, count, nearest = 0;

	lf.lfCharSet		= DEFAULT_CHARSET;
	lf.lfPitchAndFamily = 0;
	SendDlgItemMessage(hwnd, IDC_FONTLIST, CB_GETLBTEXT, item, (LPARAM)lf.lfFaceName);

	// empty list
	SendDlgItemMessage(hwnd, IDC_SIZELIST, CB_RESETCONTENT, 0, 0);

	// enumerate font sizes
	EnumFontFamiliesEx(hdc, &lf, (FONTENUMPROC)EnumFontSizes, (LONG)GetDlgItem(hwnd, IDC_SIZELIST), 0);

	// set selection to first item
	count = SendDlgItemMessage(hwnd, IDC_SIZELIST, CB_GETCOUNT, 0, 0);
	
	for(i = 0; i < count; i++)
	{
		int n = SendDlgItemMessage(hwnd, IDC_SIZELIST, CB_GETITEMDATA, i, 0);

		if(n <= cursize) 
			nearest = i;
	}

	SendDlgItemMessage(hwnd, IDC_SIZELIST, CB_SETCURSEL, nearest, 0);

	ReleaseDC(hwnd, hdc);
}

static WNDPROC  oldPreviewProc;
static HFONT	g_hPreviewFont;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -