Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Низкоуровневое программирование > Win Api
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 20.10.2022, 13:08   #21
apofioz
Форумчанин
 
Регистрация: 22.01.2014
Сообщений: 313
По умолчанию

Цитата:
Сообщение от Алексей1153 Посмотреть сообщение
менять нужно только lfHeight - инкрементом/декрементом
Значит я не до конца понимаю, что нужно делать. А почему ширина не меняется? Как тогда подогнать размер при создании окна, если мы знаем только заданный размер окна, действовать так же?
apofioz вне форума Ответить с цитированием
Старый 20.10.2022, 13:33   #22
Алексей1153
фрилансер
Форумчанин
 
Регистрация: 11.10.2019
Сообщений: 947
По умолчанию

apofioz, прицепи проект. Если будет время - я поковыряюсь. Гадать не хочется
Алексей1153 вне форума Ответить с цитированием
Старый 20.10.2022, 13:55   #23
apofioz
Форумчанин
 
Регистрация: 22.01.2014
Сообщений: 313
По умолчанию

Цитата:
Сообщение от Алексей1153 Посмотреть сообщение
прицепи проект. Если будет время - я поковыряюсь. Гадать не хочется
Нет пока что никакого проекта, есть то что я выложил, в принципе это почти весь проект, если не считать вывод в WM_PAINT. Мне нужно самому разобраться..., Если вы предлагаете изменять высоту, то как это отражается на ширине символа. К тому же две строки одна на Русском, вторая на английском, как тут высоту подсчитать? Сложить результаты вызовов функции GetTextExtentPoint32() и далее по вышеописанной схеме?
apofioz вне форума Ответить с цитированием
Старый 20.10.2022, 14:55   #24
Алексей1153
фрилансер
Форумчанин
 
Регистрация: 11.10.2019
Сообщений: 947
По умолчанию

apofioz, описание lfWidth - то есть, просто обнуляем его и всё

Цитата:
Сообщение от apofioz Посмотреть сообщение
Сложить результаты вызовов функции GetTextExtentPoint32
если это две разные строки - то да, сложить. Каждую строку нужно рассчитывать "вручную"
Алексей1153 вне форума Ответить с цитированием
Старый 21.10.2022, 08:38   #25
apofioz
Форумчанин
 
Регистрация: 22.01.2014
Сообщений: 313
По умолчанию

Цитата:
Сообщение от Алексей1153 Посмотреть сообщение
если это две разные строки - то да, сложить. Каждую строку нужно рассчитывать "вручную"
Дума, что можно сказать и так, что они разные, если одна на кириллице, а другая на латинице. Пока что ничего хорошего не вышло, но текст отображается полностью в окне, только окно слишком широкое, а по высоте вторая строка частично уходит за нижнюю границу.)
Интересно, а как узнать, в какую строну окно изменилось уменьшилось или увеличилось? Я сравниваю структуры примерно так:
Код:
if (rcNewWnd.right < rcWnd.right || rcNewWnd.bottom < rcWnd.bottom)
		{
			for (; ; --i)
			{
				if (i <= rcNewWnd.bottom)
					break;
			}
		}
else
{ .... }
стоит ли так делать или есть другой менее ресурсозатратный способ?
apofioz вне форума Ответить с цитированием
Старый 21.10.2022, 09:09   #26
Алексей1153
фрилансер
Форумчанин
 
Регистрация: 11.10.2019
Сообщений: 947
По умолчанию

Цитата:
Сообщение от apofioz Посмотреть сообщение
Интересно, а как узнать, в какую строну окно изменилось уменьшилось или увеличилось
в WM_SIZING есть инфа, за какой край тащат

Цитата:
Сообщение от apofioz Посмотреть сообщение
менее ресурсозатратный способ
тут нет никаких затрат, сообщение WM_SIZING вызывается нечасто
Но для перфекциониста могу предложить использовать дихотомию (бинарный поиск) заместо инкремента Но смысла нету в этом
Алексей1153 вне форума Ответить с цитированием
Старый 21.10.2022, 09:54   #27
apofioz
Форумчанин
 
Регистрация: 22.01.2014
Сообщений: 313
По умолчанию

Цитата:
Сообщение от Алексей1153 Посмотреть сообщение
в WM_SIZING есть инфа,
Это я знаю, но потащив за этот самый края я могу вверх-вниз, влево-вправо соответственно, я об этом.


Цитата:
Сообщение от Алексей1153 Посмотреть сообщение
тут нет никаких затрат, сообщение WM_SIZING вызывается нечасто
Тогда ладно, поинтересовался. Тогда вернусь к тому с чего начал, вот то, что я написал:
Код:
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
	static int cxClient, cyClient, cxChar, cyChar, cxStep;
	static bool bOut = true;
	static LOGFONT lf;
	static TEXTMETRIC tm;
	static RECT rcWnd;
	switch (msg)
	{
	case WM_CREATE:
	{
		_tcscpy_s(lf.lfFaceName, 32, TEXT("Times New Roman Cyr"));
		lf.lfWeight = FW_NORMAL;
		lf.lfCharSet = DEFAULT_CHARSET;
		lf.lfOutPrecision = OUT_DEFAULT_PRECIS;
		lf.lfClipPrecision = CLIP_DEFAULT_PRECIS;
		lf.lfQuality = DEFAULT_QUALITY;
		lf.lfPitchAndFamily = DEFAULT_PITCH;

		//cxStep = GetSystemMetrics(SM_CXBORDER) * 2;
		
		RECT rcClient;

		SIZE iTextRus = { };
		SIZE iTextEng = { };

		GetClientRect(hwnd, &rcClient);
		GetWindowRect(hwnd, &rcWnd);

		HDC hdc = GetDC(hwnd);

		GetTextExtentPoint32(hdc, szTextRus, _tcslen(szTextRus), &iTextRus);
		GetTextExtentPoint32(hdc, szTextEng, _tcslen(szTextEng), &iTextEng);
		int right = 0, i = iTextRus.cy + iTextEng.cy;
		if (i < rcClient.bottom)
		{
			for (; ; ++i)
			{
				if (i >= rcClient.bottom)
					break;
			}
		}
		else if (i > rcClient.bottom)
		{
			for (; ; --i)
			{
				if (i <= rcClient.bottom)
					break;
			}
		}
		
		ReleaseDC(hwnd, hdc);

		rcClient.right;
		rcClient.bottom = i;
		rcClient.left = rcWnd.left;
		rcClient.top = rcWnd.top;

		const UINT dpi = GetDpiForWindow(hwnd);
		AdjustWindowRectExForDpi(&rcClient, WS_OVERLAPPEDWINDOW, FALSE, 0, dpi);
		rcWnd = rcClient;
		SetWindowPos(hwnd, 0, 0, 0, rcClient.right, rcClient.bottom,
			SWP_NOMOVE | SWP_NOOWNERZORDER);
		
		return 0;
	}
	case WM_SIZING:
	{
		RECT rcNewWnd = *(LPRECT)lParam;
	
		SIZE iTextRus = { };
		SIZE iTextEng = { };
		int dip = 0, i;
		HDC hdc = GetDC(hwnd);
		GetTextExtentPoint32(hdc, szTextRus, lstrlen(szTextRus), &iTextRus);
		GetTextExtentPoint32(hdc, szTextEng, lstrlen(szTextEng), &iTextEng);
		//dip = GetDeviceCaps(hdc, LOGPIXELSY);
		ReleaseDC(hwnd, hdc);
		i = iTextRus.cy + iTextEng.cy;
		if (rcNewWnd.right < rcWnd.right || rcNewWnd.bottom < rcWnd.bottom)
		{
			for (; ; --i)
			{
				if (i <= rcNewWnd.bottom)
					break;
			}
		}
		else
		{
			for (; ; ++i)
			{
				if (i >= rcNewWnd.bottom)
					break;
			}
		}
		rcWnd = rcNewWnd;
		lf.lfWidth = 0;
		lf.lfHeight = -(i / 2);
		break;
	}
	case WM_PAINT:
	{
		PAINTSTRUCT ps;
		HDC hdc = BeginPaint(hwnd, &ps);
		HFONT hFont = CreateFontIndirect(&lf);
		HFONT hOldFont = (HFONT)SelectObject(hdc, hFont);
		GetTextMetrics(hdc, &tm);
		cxChar = tm.tmAveCharWidth;
		cyChar = tm.tmHeight + tm.tmExternalLeading;
        //Первоначально нужно вывести двестроки одна под другой.
		//Далее нужно увеличить букву 'А' так чтобы она стала одной //буквой А для обеих строк.
		//Решил делать так, хотя, думаю, есть более интересный метод
		if (bOut)
		{
			TextOut(hdc, 0, 0, szTextRus, _tcslen(szTextRus));
			TextOut(hdc, 0, cyChar-80, szTextEng, _tcslen(szTextEng));
			bOut = false;
			
		}
		else
		{
			LONG lfOld = lf.lfHeight;
			lf.lfHeight = -(lf.lfHeight * 2); //Новый размер для А
			lf.lfWidth = 0; //как вы и советовали
			//Возможно не нужно постоянно перерегистрировать 
			//шрифт, не знаю.
			HFONT hFont = CreateFontIndirect(&lf);
			HFONT hOldFont = (HFONT)SelectObject(hdc, hFont);
			COLORREF crOldColor = SetTextColor(hdc, RGB(255, 0, 0));
			TextOut(hdc, 0, 0, &szTextRus[0], 1);
			
			SelectObject(hdc, hOldFont);
			DeleteObject(hFont);

			lf.lfHeight = lfOld;
			lf.lfWidth = lfOldW;
            //Здесь вывожу строки с заданным цветом, но без первой //буквы А
			hFont = CreateFontIndirect(&lf);
			hOldFont = (HFONT)SelectObject(hdc, hFont);
			SetTextColor(hdc, RGB(0, 0, 255));
			TextOut(hdc, cxChar, 0, &szTextRus[1], _tcslen(szTextRus) - 1);
			SetTextColor(hdc, RGB(0, 255, 0));
			TextOut(hdc, cxChar, cyChar, &szTextEng[1], _tcslen(szTextEng) - 1);
			SelectObject(hdc, hOldFont);
			DeleteObject(hFont);
			SetTextColor(hdc, crOldColor);
		}

		//SetTextAlign(hdc, taOldAlign);
		SelectObject(hdc, hOldFont);
		DeleteObject(hFont);

		EndPaint(hwnd, &ps);
		return 0;
	}
	case WM_DESTROY:
		PostQuitMessage(0);
		return 0;
	}
	return DefWindowProc(hwnd, msg, wParam, lParam);
}
apofioz вне форума Ответить с цитированием
Старый 21.10.2022, 10:19   #28
Алексей1153
фрилансер
Форумчанин
 
Регистрация: 11.10.2019
Сообщений: 947
По умолчанию

apofioz, прицепи проект в ZIP, если хочется помощи.

навскидку, есть утечка хендлов
HFONT hFont = CreateFontIndirect(&lf);
-всё время новый создаётся, нигде не освобождается
Алексей1153 вне форума Ответить с цитированием
Старый 21.10.2022, 10:33   #29
Алексей1153
фрилансер
Форумчанин
 
Регистрация: 11.10.2019
Сообщений: 947
По умолчанию

а, нет, освобождается. Сорри )
Алексей1153 вне форума Ответить с цитированием
Старый 21.10.2022, 10:37   #30
apofioz
Форумчанин
 
Регистрация: 22.01.2014
Сообщений: 313
По умолчанию

Цитата:
Сообщение от Алексей1153 Посмотреть сообщение
прицепи проект в ZIP, если хочется помощи.
Это и есть весь проект.
Prog.rar
apofioz вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Win API 32. Открытие окна при нажатии на строку листбокса Dark_Tarakan Помощь студентам 0 20.10.2016 20:52
Открытие окна при нажатии на строку листбокса Dark_Tarakan Win Api 0 19.10.2016 18:16
подгон компонентов под размер окна brutalis Qt и кроссплатформенное программирование С/С++ 1 22.09.2013 11:42
Как считать строку из диалогового окна (не консольного) Elloriane Общие вопросы C/C++ 6 06.03.2013 21:59
Подгон текста по размеру Jakethefish JavaScript, Ajax 1 07.03.2011 15:05