Студопедия

КАТЕГОРИИ:

АвтоАвтоматизацияАрхитектураАстрономияАудитБиологияБухгалтерияВоенное делоГенетикаГеографияГеологияГосударствоДомЖурналистика и СМИИзобретательствоИностранные языкиИнформатикаИскусствоИсторияКомпьютерыКулинарияКультураЛексикологияЛитератураЛогикаМаркетингМатематикаМашиностроениеМедицинаМенеджментМеталлы и СваркаМеханикаМузыкаНаселениеОбразованиеОхрана безопасности жизниОхрана ТрудаПедагогикаПолитикаПравоПриборостроениеПрограммированиеПроизводствоПромышленностьПсихологияРадиоРегилияСвязьСоциологияСпортСтандартизацияСтроительствоТехнологииТорговляТуризмФизикаФизиологияФилософияФинансыХимияХозяйствоЦеннообразованиеЧерчениеЭкологияЭконометрикаЭкономикаЭлектроникаЮриспунденкция

Назначение низкоуровневых функций ввода консоли




Функция Описание
ReadConsoleInput Читает и удаляет входные записи из буфера ввода. Функция не возвращает управление до тех пор, пока не будут извлечены все доступные записи. После этого все доступные записи или их заданное количество пересылаются в буфер вызывающего процесса. Непрочитанные записи остаются во входном буфере до следующей операции чтения. Функция возвращает общее число прочитанных записей
PeekConsoleInput Читает записи без удаления их из входного буфера. Все заданное количество доступных записей копируются в буфер вызывающего процесса. Если доступных записей для чтения нет, функция возвращает управление немедленно. Функция возвращает общее число прочитанных записей
GetNumberOfConsoleInputEvents Позволяет получить число непрочитанных записей во входном буфере
WriteConsoleInput Помещает входные записи в буфер ввода после всех имеющихся в нем записей. Размер входного буфера увеличивается автоматически для того, чтобы внем поместились все записи. Указанные входной буфер должен иметь статус GENERIC_WRITE для того, чтобы можно было использовать эту функцию
FlushConsoleInputBuffer Удаляет все непрочитанные записи из буфера ввода. Указанные входной буфер должен иметь статус GENERIC_WRITE для того, чтобы можно было использовать эту функцию

 

Поток процесса может выполнять ожидать того момента времени, когда во входном буфере появятся доступные записи. Для иницирования операции ожидания необходимо указать дескриптор буфера ввода в вызове любой функции ожидания. Эти функции возвратят управление, когда один или несколько объектов перейдут в сигнальное состояние. Сигнальное состояние возникнет в том случае, когда во входном буфере появятся непрочитанные записи. Сигнальное состояние будет сброшено, когда входной буфер станет пустым. Если записей в буфере ввода нет, вызывающий поток войдет в эффективное состояние ожидания, которое отнимает минимум процессорного времени в ожидании наступления события, которое ожидается.

Низкоуровневые функции вывода консоли

Эти функции предоставляют прямой доступ к знакоместам дисплейного буфера. Один набор этих функций читает или записывает последовательность знакомест начиная с указанной позиции дисплейного буфера, в то время как другой набор функций позволяет читать или записывать прямоугольные блоки знакомест.

Таблица

Функции, читающие или записывающие последовательность знакомест начиная с указанной позиции дисплейного буфера

Функция Назначение
ReadConsoleOutputCharacter Читает строку Unicode или ANSI символов из дисплейного буфера
WriteConsoleOutputCharacter Записывает строку Unicode или ANSI символов в дисплейный буфер
ReadConsoleOutputAttribute Читает указанное число атрибутов цвета символов и фона из дисплейного буфера
WriteConsoleOutputAttribute Записывает указанное число атрибутов цвета символов и фона в дисплейный буфер
FillConsoleOutputCharacter Записывает единственный Unicode или ANSI символ в заданное число последовательных знакомест дисплейного буфера
FillConsoleOutputAttribute Записывает атрибут цвета символа и фона в заданное число последовательных знакомест дисплейного буфера

 

Для всех перечисленных функций, когда достигается последняя позиция строки, производится переход в первую позицию следующей строки. Когда достигается конец буфера, функции записи отбрасывают все незаписанные символы или атрибуты, а функции чтения возвращают фактическое число прочитанных символов или атрибутов.

Таблица

Функции, читающие или записывающие прямоугольные блоки знакомест начиная с указанной позиции дисплейного буфера

Функция Назначение
ReadConsoleOutput Читает символы и атрибуты цвета из указанного блока дисплейного буфера в указанный блок буфера приемника
WriteConsoleOutput Записывает символы и атрибуты цвета в указанный блок дисплейного буфера, извлекая их из указанного блока заданного буфера источника

 

Эти функции трактуют буферы – дисплейный, приемник или источник – как двумерные массивы структур CHAR_INFO, которые содержат символы и атрибуты цвета для каждого знакоместа (ячейки). Функции оперируют с шириной и высотой (в знакоместах) буферов и указатель буфера трактуется как указатель на начальный элемент (0,0) двумерного массива. Эти функции используют структуру SMALL_RECT для указания прямоугольника при доступе к дисплейному буферу и координат верхней левой ячейки буфера источника или приемника для указания позиции соответствующего прямоугольника в этих буферах.

Эти функции автоматически отсекают указанный прямоугольник дисплейного буфера для того, чтобы «вписаться» в границы дисплейного буфера. Например, если прямоугольник имеет координаты нижнего правого угла (100, 50) – позиция 100, строка 50 – а дисплейный буфер имеет ширину всего 80 позиций, координаты отсекаются до (79,50). Подобным образом, этот усеченный прямоугольник может быть опять усечен для того, чтобы «вписаться» в границы буфера источника или приемника.

На приведенном ниже рисунке показана операция чтения с помощью функции ReadConsoleOutput(), при которой первое отсечение происходит при чтении из дисплейного буфера и второе – при записи прочитанного блока в буфер приемник. Функция возвращает действительные размеры скопированного прямоугольника.

 

 

 Рис. 1. Операции отсечения при чтении и записи прямоугольного блока

 


Кодовые страницы в консольных приложениях

Для получения информации об установленной в системе кодовой странице (CP – code page) или ее установке предназначены следующие функции: GetConsoleCP(), SetConsoleCP(), SetConsoleOutputCP() и GetConsoleOutputCP(). Естественно, что функции, имя которых начинается со слова Get, используются для получения информации об установленной кодовой странице, а функции, имя которых начинается с Set – для установки кодовой страницы.

Функция SetConsoleCP() устанавливает кодовую страницу, используемую при вводе символов. Консоль использует установленную кодовую страницу для трансляции ввода с клавиатуры в соответствующее значение символа:

BOOL SetConsoleCP(UINT wCodePageID);

 

Параметр:

wCodePageID – идентификатор кодовой страницы. Идентификаторы (номера) кодовых страниц, доступных на локальном компьютере, хранятся в реестре под ключом

HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Nls\CodePage

 

Если функция выполнена успешно, она возвращает ненулевое значение (true); в противном случае возвращаемое значение нулевое (false). Для получения дополнительной информации об ошибке вызовите функцию GetLastError().

Для установки кодовой страницы, используемой при выводе символов на монитор, используется функция:

BOOL SetConsoleOutputCP(UINT  wCodePageID);

 

Параметр этой функции и возвращаемое значение аналогичны функции SetConsoleCP().

В качестве иллюстрации названных функций и проблемы использования символов кириллицы в консольных приложениях приведем фрагмент программного кода консольного приложения:

cout<<GetConsoleOutputCP()<<endl // вывод 866

<<GetConsoleCP()<<endl;  // вывод 866

char Temp[200];

cin>>Temp;           // ввод Украина

cout<<Temp<<endl;  // вывод Украина

cout<<"Русский"<<endl; // вывод ╨єёёъшщ

strcpy(Temp,"Русский"); // засылаем слово "Русский" в переменную Temp

char Res[200];

CharToOemA(Temp,Res); /* преобразуем текст, содержащийся в Temp,

из кодировки Windows в кодировку MS DOS

(из 1251 в 866) */

cout<<Res<<endl;  // вывод Русский

 

Как видно из приведенного фрагмента, непосредственный вывод символов кириллицы (cout<<"Русский";) на консоль не дает желаемого результата, так как символы константы, как и текст программы, сохраняются в кодировке Windows, а не MS DOS. Для проверки этого факта можете воспользоваться каким-либо редактором, который позволяет переключаться между кодировками, например, оболочкой Far, и просмотреть текст программы с символами кириллицы.

 

Пример консольного приложения ColorRusConsole

Готовое к выполнению приложение – файл ColorRusConsole.ехе. Листинг главного файла программы приведен ниже. Приложение скомпоновано без использования CLR и для набора символов ANSI.

//============================================================               // очистка всего дисплейного буфера (по умолчанию в нем 300 строк) //============================================================    for (coord1.X = 0; coord1.X<80; coord1.X++)               for (coord1.Y = 0; coord1.Y<300; coord1.Y++)               {      WORD wColors = 0x70;               // изменение атрибутов цвета               WriteConsoleOutputCharacter(hStdout," ",1,coord1,&cWritten);   WriteConsoleOutputAttribute(hStdout,&wColors,1,coord1,&cWritten);               }    coord2.Y = 0; coord2.X = 20;    MyText="Убедитесь, что ВЕСЬ дисплейный буфер очищен"               " (потащите за полосу скроллинга)";    WriteConsoleOutputCharacter(hStdout,Rus(MyText),strlen(MyText),                                   coord2,&cWritten);         _getch();

Русифицировать (консольное) приложение можно и путем вызова функции setlocale(LC_ALL,"rus");, которая, упрощенно говоря, устанавливает русский язык в качестве языка ввода/вывода. Эту функцию достаточно вызвать один раз при запуске программы на выполнение – проще всего в начале функции _tmain().

Использование графики в консольных приложениях

 

/* Иллюстрация использования функций графики в окне консольного приложения.

Этот пример еще раз указывает на отличие консольного приложения от

приложения MS DOS: MS DOS поддерживает или текстовый режим или графический,

но не два одновременно.

 

В приведенном ниже простеньком консольном приложении использован, с доработками,

текст программы неизвестного автора (MansMI)

http://www.cyberforum.ru/c-beginners/thread1124744.html

 

Для понимания приведенного ниже кода надо почитать литературу о графике Windows,

например, работу:

 

Круглински Д., Уингоу С., Шеферд Дж. Программирование на Microsoft Visual C++ для

профессионалов/Пер. с англ. – СПб:Питер; М.: Издательско-торговый дом "Русская

редакция", 2000. - 864с.

 

@Овсянник В.Н. 2014, ХАИ, к-105

*/

 

#include "stdafx.h"

#include <math.h>

#include <windows.h>

#include <conio.h>

 

#define M_PI 3.14159265359

 using namespace std;

int main()

{  

double sumang=0, dang=0, ang, r;

RECT rc;

int i, n, x0, y0;

const char Escape=27;

char ch=0;

POINT *arr=0;

/* Создаем красное (pred) и черное (pblack) перья*/

HPEN pred=CreatePen(PS_SOLID, 2, RGB(255,0,0));

  HPEN pblack=CreatePen(PS_SOLID, 2, RGB(0,0,0));

/* Получаем дескриптор окна hwnd*/

HWND hwnd = GetForegroundWindow();

/* Получаем указатель на контекст устройства*/

HDC hdc = GetDC(hwnd);

setlocale(LC_ALL,"rus");

GetClientRect(hwnd, &rc);

x0=(int)(rc.right - rc.left)/2;

y0=(int)(rc.bottom - rc.top)/2+10;

r=y0-20;

 

cout<<"Введи число вершин многоугольника[>=2]>";

cin>>n;

cout<<"Escape -выход, L-вращать против час. стрелки, R-вращать по час. стрелке"<<endl;

ang=M_PI*2/n;

 

arr=new POINT[n+1];

do

   for(i=0; i<=n; i++)

   {

       arr[i].x=x0+(int)(r*cos(M_PI/2+i*ang+sumang));

       arr[i].y=y0-(int)(r*sin(M_PI/2+i*ang+sumang));

   }

   SelectObject(hdc, pred);

   Polyline(hdc, arr, n+1);

   Sleep(100);

   SelectObject(hdc, pblack);

   Polyline(hdc, arr, n+1);

   if(_kbhit())

   {

       if(!(ch=_getch())) ch=_getch();

       if((ch=='L')||(ch=='l')) dang=M_PI/36;

       if((ch=='R')||(ch=='r')) dang=-M_PI/36;

   }

   sumang+=dang;

}while(ch!=Escape);

delete arr;

return 0;

}

Результат работы приложения может выглядеть так:

 

или так:

 



Изменение заголовка окна приложения и его прятание

void main()

{

  if (!AfxWinInit(::GetModuleHandle(NULL), NULL, ::GetCommandLine(), 0))

  {

              _tprintf(_T("Fatal Error: MFC initialization failed\n"));

              return;

  }

  HWND wnd=GetConsoleWindow();

  ShowWindow (wnd,SW_HIDE); // Скрываем окно консоли

  SetWindowTextW(wnd, L"Format");

// AfxMessageBox(L"Форматирование диска С: завершено",

//                                   MB_OK|MB_ICONINFORMATION);

  MessageBox(wnd,L"Форматирование диска С: завершено", L"Format",

MB_OK|MB_ICONINFORMATION);

}


 










Последнее изменение этой страницы: 2018-04-12; просмотров: 412.

stydopedya.ru не претендует на авторское право материалов, которые вылажены, но предоставляет бесплатный доступ к ним. В случае нарушения авторского права или персональных данных напишите сюда...