|
Вопрос # 3 744/ вопрос закрыт / |
|
Доброго времени суток, уважаемые эксперты!
Мне нужно чтоб моя программа в момент запуска меняла параметры дисплея на 32bit,800*600,60Гц.
Посоветуйте самый простой метод.
Спасибо.
 |
Вопрос задал: QWERYTY (статус: Посетитель)
Вопрос отправлен: 7 февраля 2010, 01:04
Состояние вопроса: закрыт, ответов: 1.
|
Ответ #1. Отвечает эксперт: Егор
Здравствуйте, Никоноров К.С.!
Ставим две кнопки - одна будет делать нужный режим, другая - возвращать всё обратно.
В обработчик первой кнопки прописываем:
procedure TForm1.Button1Click(Sender: TObject);
var
lpDevMode: TDeviceMode;
dwFlags: DWORD;
begin
// получим информацию о текущем режиме:
EnumDisplaySettings(Nil, 0, lpDevMode);
// установим свои параметры:
lpDevMode.dmBitsPerPel:=32; // 32 бита
lpDevMode.dmPelsWidth:=800; // ширина
lpDevMode.dmPelsHeight:=800; // высота
lpDevMode.dmDisplayFrequency:=60; // частота
dwFlags:=CDS_FULLSCREEN; // изменение режима временно, запоминать не надо
// будет выдано сообщение об успешности смены режима:
case ChangeDisplaySettings(lpDevMode, dwFlags) of
DISP_CHANGE_SUCCESSFUL: ShowMessage('Изменения прошли успешно.');
DISP_CHANGE_RESTART: ShowMessage(' Необходима перезагрузка для вступления изменений в силу');
DISP_CHANGE_BADFLAGS: ShowMessage(' Передан неверный набор флагов');
DISP_CHANGE_BADPARAM: ShowMessage(' Неверные параметры.');
DISP_CHANGE_FAILED: ShowMessage(' Драйвер видеоустройства не смог установить режим');
DISP_CHANGE_BADMODE: ShowMessage(' Видеорежим не поддерживается');
DISP_CHANGE_NOTUPDATED: ShowMessage(' Windows NT/2000: Ошибка записи в реестр');
end;
end;
Вторая кнопка, которая возвращает всё "обратно":
procedure TForm1.Button2Click(Sender: TObject);
var
lpDevMode: TDeviceMode;
dwFlags: DWORD;
begin
// вернём всё обратно
// сначала получим параметры текущего режима
EnumDisplaySettings(Nil, 0, lpDevMode);
// установим флаг в 0 - т.е. выйдем из "временного режима", в который мы
// вошли, щёлкнув по предыдущей кнопке
dwFlags:=0;
ChangeDisplaySettings(lpDevMode, dwFlags);
end;
Ну и поставим на форму таймер, в который пропишем:
procedure TForm1.Timer1Timer(Sender: TObject);
begin
Button2.Click;
end;
У таймера пропишем время срабатывания что-нибудь около 30 сек.
Впрочем, таймер можно бы и не писать, но если данный режим не поддерживается, то экран может стать чёрным и поможет лишь перезагрузка компа. А так - через 30 сек всё вернётся обратно.
 |
Ответ отправил: Егор (статус: 10-ый класс)
Время отправки: 7 февраля 2010, 14:14
Оценка за ответ: 5
|
Мини-форум вопроса
Всего сообщений: 24; последнее сообщение — 8 февраля 2010, 18:18; участников в обсуждении: 5.
Страницы: [1] [2] [Следующая »]
|
Егор (статус: 10-ый класс), 7 февраля 2010, 08:32 [#1]:
а погуглить не пробовал?
Опасайтесь багов в приведенном выше коде; я только доказал корректность, но не запускал его.
— Donald E. Knuth.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 10:04 [#2]:
Конечно гуглил, и нашол что это можно сделать при помощи ChahgeDisplaySettings, также нашол что первый параметр кол-во бит на пиксель второй и третий задают кол-во точек по горизонтали вертикали четвёртый частоту.
Я в этом деле новичёк, читал обучающие статьи, но на деле возникают ошибки. Книги покупать я не буду(принципиально), считаю что всё можно найти в сети. Всем спасибо за советы из разряда погугли или купи книги, есть ещё добрые люди которые могут помочь полезным советом.
Господа, просто напишите как это сделать без лишней морально-психологической нагрузки.
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
Егор (статус: 10-ый класс), 7 февраля 2010, 10:48 [#3]:
так я не понял тогда, в чём проблема?
Опасайтесь багов в приведенном выше коде; я только доказал корректность, но не запускал его.
— Donald E. Knuth.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 11:01 [#4]:
Егор, брат мой, спасибо за непосильную помощ! Ставлю тебе плюс в репутацию за внимание, потраченное время и что не маловажно беспокойство за чужие проблемы. Это очень важный момент, особенно в наши дни. После осознания что есть такие люди жить хочется.
Мир тебе брат, и мир во всём мире!
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
Егор (статус: 10-ый класс), 7 февраля 2010, 11:26 [#5]:
эпс... что это было? ))
не, я на самом деле не понял, если честно.
решена проблема или нет?
если нет, то не стоит воспринимать мои слова как издёвку и посыл на... на гугл 
я вижу, что нужная функция была найдена. вроде бы как проблема решена. но, с учётом фразы "Я в этом деле новичёк", я подозреваю, что просто знать имя функции может быть недостаточно. потому я и задаю уточняющий вопрос - в чём проблема?
1) знаем имя функции, но не знаем, как её использовать
2) знаем, как использовать, но есть ошибки и компилятор не даёт компилировать
3) программа компилируется, но разрешение не меняется
и т.д.
проблема решена или нет?
Опасайтесь багов в приведенном выше коде; я только доказал корректность, но не запускал его.
— Donald E. Knuth.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 13:02 [#6]:
Егор согласен с тобой, без подробного описания сложно врубиться в проблему.
Создаю я форму перехожу в инспектор объектов выбираю события(Events) нахожу там когда создаётся(OnCreate) кликаю дважды и переношусь в редактор кода в позицию:
procedure TForm1.FormCreate(Sender: TObject);
begin
end;
end.
Я пишу:
procedure TForm1.FormCreate(Sender: TObject);
begin
ChangeDisplaySettings(32,800,600,60);
end;
end.
когда я пытаюсь запустить(F9) останавливается на первой запятой.
Вопросс по прежнему: КАК ЗАДАТЬ ЭТИ ПАРАМЕТРЫ(МОЖЕТ НУЖНО ЧТОТО ОБЪЯВИТЬ). УКАЖИТЕ ГДЕ Я НЕДОПОНЯЛ
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
Вадим К (статус: Академик), 7 февраля 2010, 13:47 [#7]:
а функция ChangeDisplaySettings существует? если да, то как объявлена?
Галочка "подтверждения прочтения" - вселенское зло.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 13:47 [#8]:
И вот так пробовал:
procedure TForm1.FormCreate(Sender: TObject);
var a,b,c,d:Word;
begin
a:=32;
b:=800;
c:=600;
d:=60;
ChangeDisplaySettings(a,b,c,d);
end;
end.
Но как вы наверное понимаете я бы сюда не писал еслиб прокатило
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 13:57 [#9]:
Здравствуйте Вадим! Благодарен что уделили время.
Я так понимаю существует при нажатии F9 на ней не останавливается, останавливается на первой запятой после первого параметра 32.
О чём это может говорить?
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
Егор (статус: 10-ый класс), 7 февраля 2010, 14:03 [#10]:
кхм...
ну. не так надо ею пользоваться, не так 
по ссылке http://www.delphisources.ru/pages/faq/base/get_set_video_modes.html есть хорошее описание того, как это делается.
в нашем случае функции нужно передавать не четыре параметра, а всего два. причём первый из них - структура.
Опасайтесь багов в приведенном выше коде; я только доказал корректность, но не запускал его.
— Donald E. Knuth.
|
|
Егор (статус: 10-ый класс), 7 февраля 2010, 14:06 [#11]:
а вообще, нужно писать, какую же ошибку выдаёт дельфи, а выдаёт она следующее:
[Error] Unit1.pas(39): Types of actual and formal var parameters must be identical
то бишь нужны параметры, которые можно передать не как параметр-значение, а как параметр-переменная. Впрочем, вы это уже исправили.
[Error] Unit1.pas(39): Too many actual parameters
а вот тут уже понятнее - слишком много параметров, должно быть поменьше
сейчас ответ будет
Опасайтесь багов в приведенном выше коде; я только доказал корректность, но не запускал его.
— Donald E. Knuth.
|
|
Ерёмин А.А. (статус: *Администратор), 7 февраля 2010, 14:22 [#12]:
Цитата (QWERYTY):
Ставлю тебе плюс в репутацию за внимание, потраченное время и что не маловажно беспокойство за чужие проблемы.
Если бы вы ещё и комментарий нормальный написали, а не
Цитата:
чвкарпячкувеп
, то плюс бы остался у Егора.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 15:12 [#14]:
Вот это уже близко! А теперь упростим задачу.
1. Мне известен режим который поддерживает видеоадаптер, по этому НЕ НУЖНО ПОЛУЧАТЬ никаких списков с режимами.
2. Никаких кнопок создавать тоже НЕ НУЖНО, ибо нажимать никто ничего не будет. Событие должно произойти именно в момент запуска, а не нажатия на кнопки.
3 Для упрощения конечной программы НЕ НУЖНО сохранять текущий видеорежим, и соответственно востанавливать его.
4. И вообще не нужно никаких лишних наворотов, диалоговых окон и оповещений. Всё что нужно поменять разрешение при старте.
Я думал что такие люди как вы делают это на раз,два,три.
К сожалению в школе нам преподавали бейсик, если бы Pascal наверное всё пошло проще.
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 15:15 [#15]:
Егор когда я пытался повысить твой рейтинг то меня попросили ввести комент, я посчитал это морокой(маловажным) и ввёл "чвкарпячкувеп".
Если бы знал что балл не зачтут так не делал
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
Егор (статус: 10-ый класс), 7 февраля 2010, 15:31 [#16]:
ну тогда безжалостно режем мой супер-пупер красивый, лаконичный и изумительный ответ
)))))))))))))))))
var
lpDevMode: TDeviceMode;
dwFlags: DWORD;
begin
// получим информацию о текущем режиме - это нужно для заполнения структуры:
EnumDisplaySettings(Nil, 0, lpDevMode);
// установим свои параметры:
lpDevMode.dmBitsPerPel:=32; // 32 бита
lpDevMode.dmPelsWidth:=800; // ширина
lpDevMode.dmPelsHeight:=600; // высота
lpDevMode.dmDisplayFrequency:=60; // частота
dwFlags:=CDS_UPDATEREGISTRY; // изменение режима надо запомнить в реестре
ChangeDisplaySettings(lpDevMode, dwFlags); // уф! ну наконец-то меняем режим! :)))
end;
Здесь CDS_CDS_UPDATEREGISTRY означает, что экран будет переключен немедленно и это разрешение будет запомнено в реестре, т.е. после перезагрузки режим останется тем же (32 х 800х600 х 60Гц).
Можно ещё использовать:
* CDS_FULLSCREEN - Установка видеорежима временна. После перезагрузки всё вернётся обратно
* CDS_GLOBAL - Видеорежим будет изменен для всех пользователей данной машины. Иначе видеорежим меняется только для текущего пользователя. Используется вместе с флагом CDS_UPDATEREGISTRY, т.е. так:
dwFlags:=CDS_GLOBAL or CDS_UPDATEREGISTRY;
* CDS_SET_PRIMARY - Видеорежим становится первичным. Что значит - не знаю и проверять желания нет. 
* CDS_RESET - Параметры видеорежима будут изменены, даже если совпадают с текущими.
* CDS_NORESET - Изменения будут записаны в реестр, но вступят в силу после перезагрузки. Используется с флагом CDS_UPDATEREGISTRY, т.е. так:
dwFlags:=CDS_NORESET or CDS_UPDATEREGISTRY;
Опасайтесь багов в приведенном выше коде; я только доказал корректность, но не запускал его.
— Donald E. Knuth.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 16:15 [#17]:
Егор я догадался сделать то что ты советуешь(отрезать код), и взял вот так:
procedure TForm1.FormCreate(Sender: TObject);
var
lpDevMode: TDeviceMode;
dwFlags: DWORD;
begin
lpDevMode.dmBitsPerPel:=32;
lpDevMode.dmPelsWidth:=800;
lpDevMode.dmPelsHeight:=600;
lpDevMode.dmDisplayFrequency:=60;
dwFlags:=CDS_FULLSCREEN;
ChangeDisplaySettings(lpDevMode, dwFlags)
end;
end.
кроме вот этого: EnumDisplaySettings(Nil, 0, lpDevMode);
посчитав что это в моём случае лишнее. Запуск происходит, но разрешение не меняется.
Это воистину тяжкое бремя!
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 16:29 [#18]:
Как ты советуешь тоже не пашет, ругается вот на эхтой строке:
dwFlags:=CDS_CDS_UPDATEREGISTRY;
пишет Undeclared identifier:'CDS_CDS_UPDATEREGISTRY'
Истина гдето рядом...
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
|
Interventor (статус: Посетитель), 7 февраля 2010, 18:23 [#19]:
Попробовал код эксперта Егор так сказать "на себе", прописав коды в события формы OnCreate и OnDestroy соответственно. При включении программы разрешение меняется, т.е. код работает. При закрытии формы обнаружился косяк нехилой величины, а именно: разрешение сбросилось в какое-то очень маленькое значение ("на глазок" (т.к. окно свойств экрана не помещалось в сам экран) в WQVGA — 400х240). Не знаю в чем косяк, но код скопирован полностью. Пришлось в OnDestroy скопировать код для OnCreate изменив значение разрешения.
|
|
QWERYTY (статус: Посетитель), 7 февраля 2010, 19:18 [#20]:
Здравствуйте Interventor, везёт вам. Я вообще запустить не могу. Вот содержимое Unit1.pas:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs;
type
TForm1 = class(TForm)
procedure FormCreate(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
procedure TForm1.FormCreate(Sender: TObject);
var
lpDevMode: TDeviceMode;
dwFlags: DWORD;
begin
EnumDisplaySettings(Nil, 0, lpDevMode);
lpDevMode.dmBitsPerPel:=32;
lpDevMode.dmPelsWidth:=800;
lpDevMode.dmPelsHeight:=600;
lpDevMode.dmDisplayFrequency:=60;
dwFlags:=CDS_CDS_RESET;
ChangeDisplaySettings(lpDevMode, dwFlags);
end;
end.
и пишет Undeclared identifier:'CDS_CDS_RESET'
Отличается ли от вашего, и если да то где?
Истина гдето рядом...
ВЕРИТЬ ВО ВНЕЗЕМНЫЕ ЦИВИЛИЗАЦИИ НЕ ОЗНАЧАЕТ ВЕРИТЬ В ИНОПЛАНЕТЯН.
|
Страницы: [1] [2] [Следующая »]
Чтобы оставлять сообщения в мини-форумах, Вы должны авторизироваться на сайте.
|