Доброго времени суток всем!
Последний год я редко обращался к своему родному языку C++, а средствами WinAPI
никогда не программировал. Несколько недель назад я взялся за интересующее меня
дело. Я уже как три года собирался заняться программированием микроконтроллеров
или портов ПК. Ещё тогда я по одной статье из журнала "Радио" за те
времена собрал схему из 8 лампочек и
популярного 8-разрядного регистра 74HC595. Прилагалась программа управления на
частично знакомом мне "Паскале". По исходному коду я уточнил, как
управляется данный регистр и запомнил это на всю жизнь (поднял свои знания из
"школьного" курса цифровой микроэлектроники). В интернете не мало
статей на русском языке, разъясняющие принципы управления этого регистра. Схему
я доработал: поставил ещё один регистр, соединя их "последовательно"
и ещё 8 "лампочек", ибо у меня уже висела гирлянда из 16 лампочек на
220В и был к ним 16-канальный тиристорный самодельный блок.
И вот, на днях я написал
программу для управления сего дела через COM порт. Несложную программу писал
весь день, попутно изучая по форумам средства WinAPI и все новые для меня
функции, а также отлаживая и доводя её до ума. И вот, свершилось чудо! Лампочки
замигали!
Ниже представлен главный
фрагмент кода консольной программы на C++ с подробными комментариями. В
файловом архиве - полный код с цветовой разметкой в word файле doc,
откомпилированный exe'шник, образцовый файл конфигурации. Разрабатывал в среде
Microsoft Visual Studio 2008. Но можно не забивать голову и компьютер тоже,
поставив простенькую и бесплатную DevC++. Вместо десятков файлов проекта в
рабочем каталоге будет вам всего три файла: файл исходного кода 1.cpp, файл
откомпилированной программы 1.exe и файл конфигурации мигания лампочек 1.txt.
При этом, для
DevC++, код немного
изменится, в двух местах всего, а работать будет также. Данный материал
расчитан на тех, кто хоть частично знаком с подобным высокоуровневым
программированием и на тех, кто знаком с идеологией работы сдвиговых регистров.
Хотя, прочитав и разобрав данный код, можно понять эту самую идеологию.
Текстовый файл конфигурации
мигания гирлянды представляет собой бинарную матрицу из 16 столбцов и
произвольным количеством строк. Программа сканирует в файле строку за строкой
и, согласно текущей строке, с зарание введённым временным интервалом
"перебирает" состояния лампочек. В комментариях я приведу пример. По
вопросам линковки и компиляции - пишите в комментариях. Теперь, фрагмент исходного
кода...
for(j=0;j<N;j++){ //пробег
по группам состояний лампочек;
TX0(hFile); //к
выводу TX
я подключил «ключ» нашего регистра;
этой функцией принудительно блокируем регистр, то есть «закрываем» его;
for(i=0;i<16;i++){ //пробег
по лампочкам и заполнение регистра;
bit=f.get(); //считываем символ из файла в переменную bit;
if(bit=='1'){ //если это символ «1»,
RTS0(hFile); //посылаем
в регистр логический «0»; очевидно, что к выводу RTS я подключил «информационный вход» нашего регистра;
посылаем не «1», а «0», так как у него этот вход инверсный;
printf("%c",S[i]); //выводим
на экран название моей лампочки из того самого массива;
}else{ //иначе, если в файле оказался символ не
«1» (в данном случае «0», но можно использовать любой символ при задании
конфигурации),
RTS1(hFile); //посылаем в регистр «1»,
printf(" "); //выводим
на экран пробел (пустоту), так как лампочка не горит;
}
//нижними двумя строчками «тактируем» регистр,
то есть посылаем импульс на соответствующий вход нашего регистра; этим
импульсом мы записываем («проталкиваем») в регистр тот бит, который был
предварительно «подготовлен» на информационном входе функцией RTS1 или RTS0; очевидно, к контакту DTR я
подключил тактирующий вход (CLK) нашего
регистра;
DTR1(hFile);
DTR0(hFile);
}
//на этой позиции кончился внутренний цикл for, который прокрутился 16 раз и наш 16-разрядный
регистр (если быть точнее, два 8-разрядных последовательно соединённых
регистра) заполнился согласно текущей j-ой строчке нашего конфигурационного файла "1.txt";
printf("\n"); //переходим
на строчку ниже;
bit=f.get(); //сканируем следующий символ из файла в bit и никуда его не используем; если файл
сконструирован «по-честному» и без обмана программы, этим мы сканируем символ
перехода на новую строку, чтобы начать забивать в регистр следующую (j+1) строчку от её начала;
TX1(hFile); //«отмыкаем»
заполненный информацией регистр, посылая на «ключ» логическую единицу; в этот
момент лампочки загораются по соответствующим состояниям регистра, которые мы
загружали выше;
Sleep(ms); //программа
«замирает» на время ms, введённое
в милисекундах при старте программы, и лампочки продолжают гореть это время;
потом программа перейдёт к считыванию следующей строки и аналогичным операциям;
}
//на этой позиции завершился внешний цикл for; нижней строкой выводим на экран нижнее
отчёркивание, информирующее о конце всего файла;
printf("\n-----------------\n\n");
}
|