Отправляет email-рассылки с помощью сервиса Sendsay
  Все выпуски  

RFpro.ru: Программирование на C / C++


Хостинг портала RFpro.ru:
Московский хостер
Профессиональный ХОСТИНГ на базе Linux x64 и Windows x64

РАССЫЛКИ ПОРТАЛА RFPRO.RU

Лучшие эксперты по данной тематике

Асмик Гаряка
Статус: Советник
Рейтинг: 10653
∙ повысить рейтинг »
Коцюрбенко Алексей aka Жерар
Статус: Советник
Рейтинг: 3992
∙ повысить рейтинг »
CradleA
Статус: Бакалавр
Рейтинг: 2060
∙ повысить рейтинг »

/ КОМПЬЮТЕРЫ И СОФТ / Программирование / C/C++

Номер выпуска:1796
Дата выхода:17.10.2013, 20:00
Администратор рассылки:Киселёва Алёна aka Verena (Академик)
Подписчиков / экспертов:68 / 55
Вопросов / ответов:1 / 1

Консультация # 187566: Уважаемые эксперты! Пожалуйста, ответьте на вопрос: Как разработать функцию, организующую вывод в заданное место экрана окна заданных размеров. Окно должно "проявляться" из отдельных частей (последовательность "проявления" частей - случайная, размеры частей - произвольны, но процесс "проявления" должен занимать не м...


Консультация # 187566:

Уважаемые эксперты! Пожалуйста, ответьте на вопрос:
Как разработать функцию, организующую вывод в заданное место экрана окна заданных размеров. Окно должно "проявляться" из отдельных частей (последовательность "проявления" частей - случайная, размеры частей - произвольны, но процесс "проявления" должен занимать не менее 10 этапов) c замедлением по времени. После нажатия <enter> окно должно также постепенно исчезать. И исходник скиньте, пожалуйста.

Дата отправки: 09.10.2013, 19:31
Вопрос задал: Быков Евгений Андреевич (1-й класс)
Всего ответов: 1
Страница онлайн-консультации »


Консультирует Зенченко Константин Николаевич (Модератор):

Здравствуйте, Быков Евгений Андреевич!

Если нельзя подключать библиотеки - не будем.
Смотрите код(ТС++ 3.00; Win XP):

Код :
#define maxCount 13

//глобальные переменные
char far *VM=(char far*)0x0B8000000;//адрес начала физического адреса видеобуфера
char far *v;//переменная для работы с видеобуфером
int  attr;//переменная для атрибутов
int  x_L=5,y_L=5,x_R=55,y_R=12;//размеры окна

//подпрограмма получения кода нажатой клавиши
//return a - скен-код нажатой клавиши,и не важно сколько клавиш нажато одновременно
char GetAnyKey(){
  char a;
  asm xor	ax,ax//читаем символ с клавиатуры
  asm int	0x16//функция БИОС
  asm mov	a,ah//запоминаем скен-код
  return a;
  };//GetAnyKey

//подпрограмма рисования фона
// _x - левый верхний угол окна
// _y - см. выше
// d_x- размер по горизонтали
// d_y - размер по вертикали
void OutXYbg(int _x,int _y,int d_x,int d_y){
  int i,j;
  for(i=_y;i<d_y;i++){//цикл по вертикали
    v=VM+2*(i*80+_x);// физический адрес адресуемой памяти
    for(j=_x;j<d_x;j++){//цикл по горизонтали
      v++;//значение пропускаем
      *v++=attr;//записываем атрибут позиции
      };//for j
    };//for i
  };

//подпрограмма вывода символа в нужную позицию
// _x -коорджинаты позиции
// _y - см. выше
// z - выводимый символ
void OutXYchar(int _x,int _y,char z){
  v=VM+2*(80*_y+_x);//считаем физический адрес
  *v++=z;//записываем символ
  *v=attr;//устанавливаем атрибуты
  };//OutXYchar

//подпрограмма вывода несколько символов в одну линию
// _x - координаты начала вывода
// _y - см. выше
// _z - количество символов
// z - выводимый символ
// _d - приращение для следующей позиции
void OutXYline(int _x,int _y,int _z,char z,int _d){
  for(int i=0;i<=_z;i++){
    v=VM + 2*(80*_y + i*_d + _x);// !!! обратите внимание на приращение, как изменяется позиция  !!!
    *v++=z;//записываем символ
    *v=attr;//и его атрибуты
    };//for i
  };//OutXYline

//подпроогрвамма вывода строки на экран в нужную позицию
// _x - координаты верхнего-левого угла
// _y - см. выше
// _z - количество строк в линии
// s - выводимая строка
void OutXYstr(int _x,int _y,int _z,char *s){
  int i=0;
  while(*s){//пока не закончилась строка
    v=VM + 2*(80*(_y+(i / _z))+_x + (i % _z));//считаем физический  адрес
    *v++=*s++;//записываем символ и переходим к следующему
    *v=attr;//устанавливаем атрибут
    i++;//счетчик символов в строке
    };//while
  };//OutXYStr

//подпроограмма задержки
// z - количество итераций z*z
void TimeOut(int z){
  int x,y;
  x=z;
  while(x>0){//внешний цикл
    y=z;
    while(y>0){//внутренний цикл
      y--;};//while y>0
    x--;
    };//while x>0
  };//TimeOut

//подпрограмма получения случайного значения
// z - макимальное значение, т.е. 0..z-1
int GetRnd(int z){
  int gr;
  v=(char far*)0x0040006C;//адрес системого времени
  gr=*v;//считываем значение
  return gr % z;//возвращаем остаток от милисекунды деленные на размер
  };

//подпрограмма рисования частей окна
void Draw(){
  int i,j;
  j=GetRnd(maxCount);//получаем начальное значение изменений
  i=maxCount+1;//количество частей окна
  while(i>=0){
    i--;//уменьшаем итерацию
    j+=3;//получаем псевдослучайное число
    j%=maxCount;//в нужном диапазоне значений
    //  !!! коментарии case хх первоначальные значения - нужно будет изменить !!!
    switch(j){
      //левый верхний угол
      case  0:{OutXYchar(x_L,y_L,0xC9);
	       break;};//case 0
      //правый верхний угол
      case  1:{OutXYchar(x_R,y_L,0xBB);
	       break;};//case 4
      //правый нижний угол
      case  2:{OutXYchar(x_R,y_R,0xBC);
	       break;};//case 6
      //левый нижний угол
      case  3:{OutXYchar(x_L,y_R,0xC8);
	       break;};//case 8
      //левая верхняя горизонталь
      case  4:{OutXYline(x_L+1,y_L,15,0xCD,1);
	       break;};//case 1
      //правая верхняя горизонталь
      case  5:{OutXYline(x_L+36,y_L,13,0xCD,1);
	       break;};//case 3
      //нижняя горизонталь
      case  6:{OutXYline(x_L+1,y_R,48,0xCD,1);
	       break;};//case 7
      //горизонталь квази 3D-изображения
      case  7:{OutXYline(x_L+1,y_R+1,49,0xDB,1);
	       break;};//case 12
      //левая вертикаль
      case  8:{OutXYline(x_L,y_L+1,5,0xBA,80);
	       break;};//case 9
      //правая вертикаль
      case  9:{OutXYline(x_R,y_L+1,5,0xBA,80);
	       break;};//case 5
      //вертикаль квази 3D-изображения
      case 10:{OutXYline(x_R+1,y_L+1,7,0xDB,80);
	       break;};//case 11
      //имя выводимого окна
      case 11:{OutXYstr(x_L+17,y_L,30,"-= С п р а в к а =-");
	       break;};//case 2
      //фон выводимого окна
      case 12:{OutXYbg(x_L+1,y_L+1,x_R,y_R);
	       break;};//case 10
      };//switch
      TimeOut(30000);
    };//while
//дополнительная опция - вывод текста в окно :)))
  if(attr!=0){OutXYstr(x_L+1,y_L+1,49,
"Окно должно 'проявляться' из отдельных частей (последовательность 'проявления' частей - случайная, размеры частей - произвольныe, но процесс 'проявления' должен занимать не менее 10 этапов) c замедлением по времени. После нажатия <enter> окно должно также постепенно исчезать.");
    };
  };//Draw

//основная функция задания
void MyFuncMain(){
  attr=0x1f;//синий фон + белый текст
  Draw();//выводим
  do{}while(GetAnyKey()!=0x1c);//цикл ожидания клавиши "ВВОД"
  attr=0x0;// всё черное
  Draw();//выводим, т.е. стираем.
  };//MyFuncMain

//основная процедура
void main(void)
  {
//устанавливаем видео режим
  asm mov ax,0x03;
  asm int 0x10;
//адресуем переменную на видео-буфер
  v=VM;
  for(int i=0;i<2*(80*24);i++){*v++=0x0;}//стираем всё
//вызываем основную функцию задания
  MyFuncMain();
//финальное сообщение и ожидание клавиши
  attr=13;
  OutXYstr(10,10,50,"press any key ...");
  GetAnyKey();
  }//main


В программе релаизована псевдослучайная последовательность т.к. ожидать нормального распределения значений при таком генераторе и диапазоне - трудно, появляются не предскаазуемые задержки и т.п..

Код выше в кодировке ср1251, для DOS нужна ср866. Всё находится в прилагаемом архиве(*.срр + *.ехе +*.obj):q187566.zip (10.0 кб)
ps:вопросы задавайте в минифорум.
Удачи!

Консультировал: Зенченко Константин Николаевич (Модератор)
Дата отправки: 12.10.2013, 04:13

5
нет комментария
-----
Дата оценки: 12.10.2013, 17:24

Рейтинг ответа:

НЕ одобряю 0 одобряю!


Оценить выпуск | Задать вопрос экспертам

главная страница  |  стать участником  |  получить консультацию
техническая поддержка  |  восстановить логин/пароль

Дорогой читатель!
Команда портала RFPRO.RU благодарит Вас за то, что Вы пользуетесь нашими услугами. Вы только что прочли очередной выпуск рассылки. Мы старались. Пожалуйста, оцените его. Если совет помог Вам, если Вам понравился ответ, Вы можете поблагодарить автора - для этого в каждом ответе есть специальные ссылки. Вы можете оставить отзыв о работе портале. Нам очень важно знать Ваше мнение. Вы можете поближе познакомиться с жизнью портала, посетив наш форум, почитав журнал, который издают наши эксперты. Если у Вас есть желание помочь людям, поделиться своими знаниями, Вы можете зарегистрироваться экспертом. Заходите - у нас интересно!
МЫ РАБОТАЕМ ДЛЯ ВАС!



В избранное