Оглавление:
- Шаг 1: контакты и контакты….Почему код не работает?
- Шаг 2: Давайте «определим» некоторые пины…
- Шаг 3. PinMode ()… Как вы будете использовать свои пины…
- Шаг 4: AnalogWrite () в сравнении с PwmWrite ()… Аналоговый вывод в двух вариантах
- Шаг 5: Последовательная связь STM32
- Шаг 6: передача значения микроконтроллеру
- Шаг 7: И если я хочу ввести три цифры…. или даже больше ??
Видео: Итак, вы загружаете загрузчик STM32duino в свою «синюю таблетку» Итак, что теперь?: 7 шагов
2024 Автор: John Day | [email protected]. Последнее изменение: 2024-01-30 11:49
Если вы уже читали мои инструкции, объясняющие, как загрузить загрузчик STM32duino или любую другую подобную документацию, вы попробуете загрузить пример кода и … может вообще ничего не произойдет.
Проблема в том, что многие, если не все примеры для "Generic" STM32 не работают из коробки. Потребуются незначительные изменения, чтобы заставить работать вашу плату STM32 "Blue Pill".
Я выберу 4 примера кода, чтобы объяснить, что нужно изменить и почему. Коды: «BlinkWithoutDelay», «Fading», «Dimmer» и «AnalogInSerial».
Заметьте, я ничего не кодировал. Я просто вношу небольшие изменения в коды, созданные:
Дэвид А. Меллис и позднее модифицированный Томом Айго, Марти Боливар и некоторые случаи Скоттом Фицджеральдом
Том Айго и позднее модифицированный Брайаном Ньюболдом
Поэтому я предпочитаю сохранять имена авторов даже в кодах, которые я изменяю, сохраняя авторство.
Шаг 1: контакты и контакты…. Почему код не работает?
Давайте посмотрим на распиновку STM32 "Blue Pill". Контакты для нот обозначаются как PA1 или PC2… что-то вроде этого.
Если вы посмотрите, например, пример кода "BlinkWithoutDelay", контакт будет объявлен как "33"…. Почему?
Я подозреваю, что это потому, что г-н Марти Боливар перенес этот код для платы MAPLE.
Я думаю, что он не собирался делать код совместимым с платами "Blue Pill".
Контакты мини-платы Maple и Maple объявлены числовыми, как и Arduino, хотя они используют такие числа, как 33, 24 и некоторые подобные.
Я сказал, что код не работает? Виноват. Код компилируется без каких-либо ошибок и правильно загружается в «Blue Pill», так что, по моему мнению, он действительно работает, но с использованием вывода GPIO мы не ожидаем. Может быть, даже не доступен.
Чтобы он работал должным образом, в код необходимо внести небольшие изменения.
Шаг 2: Давайте «определим» некоторые пины…
Хорошая практика использования кода - объявлять ресурсы как легко идентифицируемые или означающие переменные или константы. Это упростит понимание кода и устранение неполадок.
Я использовал объявление выводов Arduino следующим образом:
…
const int ledPin = 13;
…"
Если я вам нравлюсь, возможно, вы спрашиваете себя: «Как я могу объявить контакты с такими именами, как PC13 ???»
Ответ: используйте оператор C. "#define".
Итак, согласно схеме распиновки, PC13 - это вывод, который есть на плате светодиода в BluePill. Чтобы использовать это, я бы объявил вот так, сразу после определения библиотеки (# include…) и перед чем-либо еще:
…
#define LedPin PC13
…"
Обратите внимание, что нет ";" окончание строки, присвоение NOR "=".
Сравните оба кода. Один из них - оригинальный пример, загруженный из IDE. Во-вторых, я немного приспособился к работе с BluePill.
Я настоятельно рекомендую объявить все контакты, которые вы собираетесь использовать в коде. Даже те, которые собираются использовать в качестве входа АЦП (подробнее об этом позже).
Это облегчит вашу жизнь.
Шаг 3. PinMode ()… Как вы будете использовать свои пины…
Прежде чем продолжить, давайте разберемся с функцией PinMode ().
Как и Arduino, выводы STM32 имеют несколько функций. Самый простой способ выбрать тот или иной - использовать оператор pinMode ().
Для Arduino доступно только 3 режима: INPUT, OUTPUT или INPUT_PULLUP.
STM32, с другой стороны, имеет много разновидностей pinMode (). Они есть:
ВЫХОД - Базовый цифровой выход: когда на контакте ВЫСОКИЙ, напряжение удерживается на уровне + 3,3 В (Vcc), а когда оно НИЗКОЕ, оно опускается на землю
OUTPUT_OPEN_DRAIN - В режиме открытого стока вывод показывает «низкий», принимая ток на землю, и «высокий», обеспечивая увеличенное сопротивление
INPUT_ANALOG - это специальный режим, когда вывод будет использоваться для аналогового (не цифрового) чтения. Позволяет выполнять преобразование АЦП по напряжению на выводе
INPUT_PULLUP - Состояние вывода в этом режиме сообщается так же, как и при INPUT, но напряжение на выводе плавно «подтягивается» до + 3,3 В
INPUT_PULLDOWN -Состояние вывода в этом режиме сообщается так же, как и с INPUT, но напряжение на выводе плавно «понижается» до 0 В
INPUT_FLOATING - синоним INPUT
PWM - это специальный режим, когда вывод будет использоваться для вывода PWM (особый случай цифрового вывода)
PWM_OPEN_DRAIN - Подобно ШИМ, за исключением того, что вместо чередования циклов НИЗКОГО и ВЫСОКОГО, напряжение на выводе состоит из чередующихся циклов НИЗКОГО и плавающего (отключенного)
(примечание: извлечено из
Я просто открываю эту скобку, потому что, когда вы начинаете создавать свой собственный код, будьте осторожны, чтобы использовать правильный pinMode () для ваших нужд.
Шаг 4: AnalogWrite () в сравнении с PwmWrite ()… Аналоговый вывод в двух вариантах
Перед использованием контактов GPIO "Blue Pill" необходимо заявить о его поведении, то есть о том, как он будет работать. Именно это и делает функция pinMode ().
Итак, давайте сосредоточимся на том, как правильно настроить аналоговый выход. Он может быть объявлен либо как режим ВЫХОДА, либо как режим ШИМ.
Таким же образом, аналоговые значения могут быть присвоены GPIO двумя способами: analogWrite () или pwmWrite (), НО, analogWrite () БУДЕТ работать, только если pinMode () = OUTPUT. С другой стороны, pwmWrite () БУДЕТ работать, только если pinMode () = PWM.
Возьмем, к примеру, PA0: это кандидат на аналоговый / ШИМ-выход.
analogWrite (): это объявляется следующим образом:
….
#define ledPin PA0
pinMode (ledPin, ВЫХОД);
analogWrite (ledPin, <число>);
……"
где число должно быть от 0 до 255, как в Arduino. Фактически, он обратно совместим с Arduino.
pwmWrite (): объявите так:
…
#define ledPin PA0
pinMode (ledPin, ШИМ);
pwmWrite (ledPin, <число.>);
…."
Число должно быть от 0 до 65535, разрешение намного выше, чем у Arduino.
На изображениях можно сравнить 2 кода. Вы также можете увидеть исходный код.
Шаг 5: Последовательная связь STM32
Посмотрим, как устроены интерфейсы USART в STM32. Да, интерфейсы во множественном числе…..
«Blue Pill» имеет 3 USART (RX / TX 1 ~ 3), и, если вы используете загрузчик, позволяющий использовать USB, он не подключен ни к одному из них.
В зависимости от того, используете вы USB или нет, вам нужно так или иначе объявить последовательный порт в вашем коде.
Случай 1: Использование USB:
Таким образом, скетчи загружаются напрямую через USB. Нет необходимости переводить перемычку BOOT0 в 1 положение и обратно в 0.
В этом случае каждый раз, когда вы объявляете «Последовательный» без индекса, это означает связь через USB.
Итак, Serial1 означает TX / RX 1 (контакты PA9 и PA10); Serial2 означает TX / RX 2 (контакты PA2 и PA3), а Serial 3 означает TX / RX 3 (контакты PA10 и PA11).
Это то, с чем мы работаем. Я представлю изменения в примерах для этого способа кодирования.
Другое дело: "Последовательный USB" инициализировать не нужно. Другими словами, «… Serial.begin (15200);» не обязательно.
Возможен вызов любой последовательной функции (Serial.read (), Serial.write () и т. Д.) Без какой-либо инициализации.
Если по какой-то причине он присутствует в коде, компилятор проигнорирует его.
Случай 2: Использование адаптера TTL seria-USB:
Таким образом, загрузчик не поддерживает обычную USB-связь STM32, поэтому для загрузки скетчей вам понадобится USB-последовательный адаптер, подключенный к TX / RX 1 (контакты PA9 и PA10).
В этом случае любое время, когда "Serial" без индекса является кодом, означает TX / RX1 (порт, используемый для загрузки кода). Итак, Serial1 относится к TX / RX 2 (контакты PA2 и PA3), а Serial2 относится к TX / RX 3 (контакты PA10 и PA11). Нет доступного Serial3.
Шаг 6: передача значения микроконтроллеру
Пример диммера - простой способ показать, как передать значение микроконтроллеру.
Предполагается, что для управления яркостью светодиода необходимо передать значение от 0 до 255.
Это НЕ будет работать должным образом в Blue Pill из-за:
- Чтобы использовать функцию pwmWrite (), pinMode () ДОЛЖЕН быть объявлен как режим PWM.
- Вы никогда не получите целое трехзначное число. Функция Serial.read () захватывает только содержимое буфера, которое является байтом. если вы наберете «100» и нажмете «ввод», только последний «0» будет захвачен из буфера. Его значение будет «48» (десятичное значение ASCII для «0»). Если намереваетесь выдать значение «100», необходимо набрать «d». Итак, правильно сказать, что он преобразует десятичное значение символа ASCII в яркость светодиода, верно ??…. Ну, что-то вроде…
- Проблема, отображение значений непосредственно из функции Serial.read () - это уловка. Почти наверняка получатся неожиданные значения. Лучший подход - это содержимое буфера хранения во временной переменной и его отображение.
Как я объяснял ранее в пункте 2, код, который я вношу изменениями, позволит ввести символ ASCII, и это будет управлять яркостью светодиода на основе его десятичного значения ASCII… например, «пробел» - это значение 32 (на самом деле это самый низкий печатаемый символ, который вы можете ввести) а «}» - возможно самый высокий (значение 126). Другие символы не печатаются, поэтому терминал не поймет, или они могут быть составными символами (например, "~" - это неработающая клавиша на моей клавиатуре и не будет работать правильно). Это означает, что этот составной символ при вводе в терминал отправит сам символ и что-то еще. Обычно непечатаемый. И будет ли этот последний код захватывать. Также имейте в виду, что ваш Терминал в этом случае НЕ должен отправлять ни «Возврат каретки», ни «Перевод строки». Вы должны обратить на это внимание, чтобы код работал правильно.
Если вы упали, это немного сбивает с толку, становится еще хуже …
Шаг 7: И если я хочу ввести три цифры…. или даже больше ??
Получить несколько символов из последовательной связи - непростая задача.
Последовательный буфер представляет собой стопку символов в байтах FIFO. Каждый раз, когда вызывается функция Serial.read (), первый отправленный символ удаляется из кучи и сохраняется где-то еще. Обычно это символьная переменная в коде. Обратите внимание: в зависимости от оборудования обычно существует тайм-аут, по которому буфер журнала может хранить информацию.
Если вы намереваетесь ввести более одной цифры через последовательный порт, вы должны будете «составлять» строку посимвольно по мере того, как они попадают в буфер UART.
Это означает циклическое чтение каждого буфера char, сохранение во временной переменной, загрузку ее в первую позицию строкового массива, переход к следующей позиции и начало заново, пока… ну, это зависит от приложения. Завершить цикл можно двумя способами:
- Использование символа «конечной метки», например «возврата каретки» или «перевода строки». Как только символ "end Mark" найден, цикл завершается.
- В качестве альтернативы, количество символов в цепочке строк может быть ограничено, как и количество интерактивных циклов. Когда он достигнет предела, скажем, 4, процедура приобретения завершится сама собой.
Давайте посмотрим на простом примере, как это сделать:
- Установите "конечный" символ, например '\ n' (это означает ASCII-символ перевода строки).
- цикл между тем, как Serial.available () истинен
- сохранение Serial.read () приводит к временной переменной типа char. Помните: как только Serial.read () действительно "читает" буфер, он становится чистым и в него загружается следующий символ.
- увеличить строковую переменную с помощью этого символа
- Если последний символ - "конец", выйти из цикла.
Обычно процедура получения массива последовательных символов выглядит как рисунок.
Он был основан на обширной адаптации оригинального кода Дэвида А. Меллиса.
Не стесняйтесь использовать и протестировать его. Помните: значения ДОЛЖНЫ быть введены в трехзначном формате.
На этом пока что. Я не буду вдаваться в дополнительные подробности последовательной связи. Это слишком сложно, чтобы описывать здесь, и оно заслуживает отдельного Intructables.
Я надеюсь, что это поможет вам использовать примеры в Blue Pill и даст вам некоторое представление о том, насколько правильный код для этой маленькой доски.
Увидимся в других инструкциях.
Рекомендуемые:
Записать загрузчик на плату клонирования Arduino Nano 3.0: 11 шагов
Записать загрузчик на плату клонирования Arduino Nano 3.0: недавно вы купили на AliExpress клон Arduino Nano 3.0, который поставлялся без загрузчика. Я уверен, что есть много других людей, которые находятся в такой же ситуации, что и я, и, возможно, сначала немного испугались! Не волнуйтесь, в этой инструкции
КАК ЗАПИСАТЬ ЗАГРУЗЧИК В ATMEGA328 с помощью Arduino Uno: 5 шагов
КАК ЗАПИСАТЬ ЗАГРУЗЧИК В ATMEGA328 с помощью Arduino Uno: сначала посмотрите видеоурок
Детектор уровня коксовой машины - теперь с речью!: 6 шагов (с изображениями)
Детектор уровня коксовой машины - теперь с речью !: Этот проект представляет собой ремикс моего детектора уровня коксовой машины (https://www.instructables.com/id/Coke-Machine-Can-Level-Detector/) с новыми датчиками , и добавление разговорного звука! После того, как я сделал свой первый детектор уровня, я добавил пьезозуммер к g
Электрофотография - теперь с добавлением Кирлиан !: 6 шагов (с изображениями)
Электрофотография - теперь с добавлением Кирлиан! Еще в мае я опубликовал слайд-шоу на эту тему. Изображения, созданные в этом слайд-шоу, были для проекта альтернативной фотографии в моем классе Advanced Photography. В этом семестре я второй раз беру Advanced Photo, а это значит, что я
Итак, вы хотите построить гигантского робота: 19 шагов (с изображениями)
Итак, вы хотите построить гигантского робота. Вы говорите, что хотите построить гигантского робота? Какова твоя цель? Мировое господство? Твоя девушка не принесет тебе пива? Как бы то ни было, вот как начать создавать робота самому. Цель этого робота заключалась в создании сценической опоры для м