воскресенье, 12 мая 2019 г.

Бесполезная коробка на ATmega328P


Бесполезная коробка на ATmega328P

Последнее время у меня в блоге одни микроконтроллеры, программаторы и загрузчики. Надо бы отвлечься и написать о чем-то, что можно собрать своими руками. Думаю, "бесполезная коробка" отлично подойдет для этого: эта забавная поделка обязательно понравится и ребенку, и взрослому, а сделать ее под силу каждому.

Необходимые компоненты

Для сборки бесполезной коробки потребуются:
  • Собственно коробочка. Ее можно сделать из дерева или фанеры.
  • Микроконтроллер ATmega328P. Можно использовать и Ардуино, но она будет значительно быстрее сажать батарею.
  • Тумблер.
  • Два сервопривода. Я использую самые дешевые SG90.
  • Батарейки/аккумулятор. Нам нужно 5-6 вольт.
  • Полевой транзистор (у меня под рукой только IRF540, он вполне подходит).
  • Сопротивление в несколько кОм, номинал особой роли не играет.

Прежде чем перейти к описанию изготовления бесполезной коробки я приведу несколько соображений, которых я придерживался. Во-первых, не хотелось бы устанавливать в такой игрушке дополнительный выключатель для управления ее питанием. То есть коробка должна быть всегда включена и готова к работе. Значит нужно позаботиться об энергосбережении в режиме ожидания. Поэтому желательно использовать именно отдельный микроконтроллер, а не Ардуино, так как он позволяет добиться значительного снижения энергопотребления. Я решил использовать ATmega328P с тактированием от внутреннего RC-генератора 8МГц. В режиме сна он потребляет менее 1мкА. Если вы планируете использовать Ардуино, то я бы порекомендовал Pro Mini 8MHz, из нее нужно выпаять светодиод-индикатор питания и запитать ее через пин 5V (в обход стабилизатора).

Если Ардуино / микроконтроллер можно перевести в режим энергосбережения, то картину портят сервоприводы: даже в режиме простоя они потребляют несколько миллиампер. Здесь-то и пригодится транзистор, с его помощью можно отключать питание сервоприводов пока микроконтроллер спит. Полевой транзистор удобен тем, что он управляется не током, а напряжением, потому весьма экономичен. Но, думаю, для этой задачи можно подобрать и биполярный транзистор.

Изготовление коробки

Для изготовления коробки подойдет фанера 6мм. Мне приятнее работать с деревом, поэтому я выстрогал дощечку указанной толщины из осины. Размеры коробки прикиньте сами, чтобы внутри уместились все компоненты. Главное требование: ширина коробки должна быть достаточной для размещения в ней сервопривода, чтобы его рычаг находился на одном уровне с тумблером, то есть посередине ширины коробки. Остальные размеры на ваше усмотрение.

Детали я выпилил на лобзиковом станке:

Изготовление бесполезной коробки
Детали для сборки бесполезной коробки

Рычаг, который выключает тумблер, я склеил из трех отдельных частей. Если делать его из фанеры, то он может быть и цельным. Чтобы определиться с размерами и формой рычага я установил тумблер в обрезке доски и приклеил к ней сервопривод на двусторонний скотч. Затем, соединив детали будущего рычага струбцинами, подобрал подходящую форму, чтобы он свободно поворачивался и доставал до тумблера:

Изготовление рычага для бесполезной коробки
Выбор подходящей формы для рычага

Готовый рычаг для выключения тумблера

Другой рычаг должен поднимать крышку, с его изготовлением нет ничего сложного. Можно было бы обойтись и пластиковым рычагом, что идет в комплекте с SG90, но он для этого коротковат.

Сами сервоприводы отлично держатся в коробке на двустороннем скотче.

Отдельно можно упомянуть о креплении рычагов к сервоприводам. К сервам хорошо подходят штатные пластиковые рычаги. Остается только соединить их с деревянными деталями. Я рассматривал разные варианты их соединения, в итоге остановился на следующем: в деревянной рейке просверлил отверстие для вала сервопривода и вырезал углубление по форме пластикового рычага. Вклеил в это углубление рычаг, сверху приклеил вторую рейку. Пластиковый рычаг оказался внутри деревянной "оправы". После высыхания клея я довел рычаг до ума на шлифовальном станке:


Петли для крышки я купил на Aliexress, у нас таких маленьких я не нашел. Чтобы крышка всегда была прикрыта, ее нужно подтянуть пружиной или резинкой:

Бесполезная коробка Крышка
Резинка удерживает крышку в закрытом состоянии

И, наконец, дно коробки я посадил на винты. Гайки под них установлены по углам коробки. Можно использовать вместо них маленькие гвозди, кому как нравится.

Дно коробки прикручивается винтами
Внутри игрушки

Схема и питание коробки

Нам нужно управлять работой двух сервоприводов и отслеживать состояние тумблера. Для этого подключим их к микроконтроллеру по следующей схеме:

Схема бесполезной коробки на ATmega328P
Схема бесполезной коробки на ATmega328P

Как уже отмечалось, в моей коробке работает микроконтроллер ATmega328P. Я развел и вытравил под него плату (мои схема и разводка доступны в EasyEDA по ссылке: https://easyeda.com/VladimirTsibrov/uselessbox-on-atmega328p), сделал разъемы для подключения сервоприводов, питания и тумблера, а также вывел пины RX, TX и Reset. Подключившись к ним, можно заливать скетчи в микроконтроллер, не извлекая его из платы.

Эта же схема для тех, кто предпочитает Ардуино и схемы fritzing:

Схема для Ардуино

Отслеживать переключения тумблера удобно при помощи внешнего прерывания, поэтому он подключен к пину 2. Для управления сервоприводами нужны выводы, поддерживающие PWM, а для управления их питанием подойдет любой вывод. Я использовал пины 9, 10 и A5 для удобства разводки платы. Вы можете выбрать другие, внеся соответствующие изменения в скетч.

Для питания подойдут 4 "пальчиковые" батарейки. Учтите, что 6 вольт - это максимально допустимое напряжение для AVR микроконтроллеров, превышать его нельзя. А даташит и вовсе не рекомендует допускать длительную работу микроконтроллера при напряжении питания 6В. В режиме сна моя коробка потребляет около 0,2мкА. Я установил в нее щелочные батарейки, думаю, их хватит надолго.

Алгоритм работы и скетч

Алгоритм работы коробки можно описать примерно так:

1. В течение нескольких секунд ожидаем переключения тумблера. Дождавшись, переходим к пункту 4.
2. По истечении времени ожидания отключаем питание сервоприводов и переводим микроконтроллер в спящий режим.
3. Выход из спящего режима возможен по внешнему прерыванию. Таким образом при переключении тумблера микроконтроллер проснется, включит питание сервоприводов и мы снова окажемся на пункте 1.
4. Необходимо переключить тумблер.
4.1 Если микроконтроллер только что вышел из сна, то переключаем тумблер без эффектов. Так незнакомый с коробкой человек сразу поймет ее смысл. Возвращаемся к пункту 1.
4.2 Если это уже не первое переключение тумблера игроком после пробуждения микроконтроллера, то:
4.2.1 разнообразим поведение коробки эффектами (приоткрыть, похлопать крышкой и т.п.), после чего возвращаемся к пункту 4;
4.2.2 или переключим тумблер и вернемся к пункту 1.
5. Опять же чтобы разнообразить поведение коробки, после каждого переключения тумблера засекается время реакции игрока. Если игрок несколько раз подряд переключает тумблер за короткий промежуток времени, то рычаг не убирается, крышка не закрывается, а коробка переключает тумблер без эффектов. Это происходит до тех пор, пока игрок не сбавит темп.

Скетч, реализующий описанное поведение, можно скачать здесь. Разумеется, нужно будет самостоятельно подобрать позиции для сервоприводов и вписать их в скетч.

А вот и видео с получившейся игрушкой:


39 комментариев:

  1. Хорошая иммитация поведения) Позабавила)

    ОтветитьУдалить
  2. надо еще динамик с очень распространенной русской фразой ...

    ОтветитьУдалить
  3. Почему бы не сделать, чтобы по тумблеру выключенный микроконтроллер включался, а потом, по истечении некоторого времени, если его не тормошат, обрубал себе питание,

    ОтветитьУдалить
    Ответы
    1. Да, можно и так. Я уже не помню, почему решил переводить МК в сон.

      Удалить
    2. Я сделал вот так, на 1-м сервомоторе:

      https://www.youtube.com/watch?v=Ko5oXMeLiYQ

      -------------------------------------------

      Прошивку для Ардуино хотел сюда скинуть, но она не поместилась в сообщении.

      Удалить
    3. Добрій день! перевел свой проект с ардуино нано на атмега328. Скетч оставил без изменений и все вроде бі работает, но мк время от времени зависает. Ві сталкивались в своем проекте с данной проблемой или мк работает нормально?

      Удалить
    4. Добрый день!
      У меня всё нормально, зависаний не было.
      Какие у вас частота МК и напряжение питания? Последнее не занижено?

      Удалить
    5. частота 16мгц от внешнего кварца, а напряжение - от 3.7в аккумулятора. МК не только подвисает, но даже иногда перезагружается

      Удалить
    6. 3.7 мало для 16МГц. Попробуйте запитать от трех пальчиковых, посмотрите, будет ли перезагружаться.

      Удалить
    7. Запитывал через вывод 5в ардуино, все тоже самое. Может в самом скетче дело, но он только 30% памяти мк занимает. Вроде не перегружен. Наверно попробую поработать с портами через регистр, может ускорится и перестанет тормозить

      Удалить
    8. Кстати, а подключение вывода RST (я подключал к Vcc напрямую без резистора 10к либо вообще не подключал) может влиять на подтормаживание и внезапную перезагрузку?

      Удалить
    9. Reset подтянут к Vcc внутренним резистором. Подтяжка хоть и слабая, но здесь не тот случай, чтобы её не хватало. Дело не в нём.

      Могу предположить, что у вас МК без загрузчика и коробка не успевает отключить себя за 1 секунду, перезагружается и не может вернуться в рабочий режим. Если 1 секунды реально не хватает для выключения тумблера, то можно увеличить до 2 в строке:
      wdt_enable(WDTO_1S); // На случай зависания в цикле установим WDT на 1с
      поправьте на WDTO_2S

      А вообще нужно добавить в самом начале функции setup такую строчку:
      MCUSR = 0

      Удалить
    10. Если, например, включить тумблер и держать его, то коробка не сможет его выключить. Вот чтобы коробка не насиловала сервопривод, пытаясь выключить тумблер, я и добавил ограничение по времени в 1с. Если не успели, то МК перезагрузится и попробует выключить его еще раз. Как-то так.

      Удалить
    11. Ну так моё предположение верное? Если да, то смысл в следующем.
      Как я и сказал, на переключение тумблера отводится 1с, чтобы не портить сервомоторчик, если ему мешают. Если в 1 секунду не уложились, то сторожевой таймер генерирует сигнал сброса. При этом в MCUSR устанавливается флаг WDRF, который сигнализирует о том, что источником сброса был сторожевой таймер. Пока мы этот флаг не сбросим, WDT нельзя будет остановить (кстати в прошлом комментарии я забыл сказать, что его нужно остановить) и он будет продолжать работать, генерируя сигнал сброса снова и снова.
      Таким образом сначала нужно сбросить флаг WDRF, записав 0 в MCUSR, затем выключить WDT. Для этого добавляем в setup следующий код:
      MCUSR = 0;
      wdt_disable();

      В платах Ардуино это за нас делает загрузчик, поэтому на Нано всё было нормально.

      Удалить
    12. поменял delay() на _delay_ms() и уменьшил время паузы - сразу помогло

      Удалить
  4. Этот комментарий был удален автором.

    ОтветитьУдалить
  5. Этот комментарий был удален автором.

    ОтветитьУдалить
  6. По ряду причин мне проще использовать ардуино целиком. Правильно ли я понимаю, что питание на ардуино также можно подать после транзистора? А тумблер может подавать отпирающий импульс. После включения ардуино "защёлкнет" транзистор на необходимое время. Таким образом, во время работы устройства мы получим повышенный расход энергии, но во время простоя расход будет нулевым. Также хочу спросить: будет ли ардуино работать от трёх батареек и какой ток у сервопривода 9g?

    ОтветитьУдалить
    Ответы
    1. Добрый день!
      Отключать питание Ардуино можно, но вряд ли получится обойтись одним транзистором. Я бы посоветовал открывать Ардуиной биполярный транзистор, а он бы уже открывал мосфет. Как раз планирую посвятить этому вопросу следующую статью.
      Ардуино может работать и от 4.5В, только подавать их надо не на Vin или DC-разъем, а на пин 5V. А вот с сервоприводом лучше потестировать, хватит ли ему силы переключить тумблер. С четырьмя батарейками он это делает уверенно и есть запас на случай разряда батареек.

      Удалить
    2. Тут у меня сказывается недостаток знаний в электротехнике. Понимаю, что имеется в виду, но не понимаю - зачем. Почему нельзя с ардуино включать мосфет напрямую, а тумблер развязать через диод?
      Я имею в виду, что с тумблера сигнал приходит на сигнальный вход и через диод на затвор транзистора. На затвор также приходит сигнал с управляющего выхода. Диод обеспечит развязку между управляющим выходом и сигнальным входом.

      Удалить
  7. Здравствуйте Владимир
    Почему то в скетче нет реакции на шаговый двигатель крышки.
    Шаговый от руки работает, а крышка молчит, как партизан

    ОтветитьУдалить
  8. Пробовал другие скетчи от других авторов, там второй двигатель работает с крышкой, пины одинаковые 9 и 10
    В чем может быть проблема?

    ОтветитьУдалить
    Ответы
    1. Добрый день!
      Создайте пустой скетч и попробуйте управлять каждым из сервомоторов. Только не забудьте сначала запитать их, открыв полевой транзистор:
      pinMode(A5, OUTPUT);
      digitalWrite(A5, HIGH);

      Удалить
  9. Спасибо за ответ
    Что значит-пустой скетч?

    ОтветитьУдалить
  10. Прописывать библиотеки или нет ?

    ОтветитьУдалить
    Ответы
    1. Странные вопросы.
      Пустой скетч - значит в нём не должно быть ничего, кроме того, что я указал: управление сервомоторами и подача на них питания. Просто пошевелите ими. Если не заработает, значит неправильно подключили.

      Удалить
  11. А так ли уж нужен R1? Да, я знаю, что его обычно ставят для защиты выхода Arduino. Но неужели выход Arduino не способен зарядить/разрядить емкость в пару тысяч пикофарад (емкость затвора обычно не больше)?

    ОтветитьУдалить
  12. Забавное устройство. Собрался повторить. Но при компиляции скетча обнаружил что код весьма компактный и может уместиться даже в mega8, правда при компиляции выяснилось, что код написан под микроконтроллеры мega168,328 с буквой P в обозначении. Компиляция для другой платформы приводит к ошибке в 174-175 строках (MCUCR = bit (BODS) | bit (BODSE); MCUCR = bit (BODS);. Если же её закоментить, то скетч получается нерабочий. буду экспериментировать дальше, так как mega8 ещё есть а mega328p уже нет.

    ОтветитьУдалить
    Ответы
    1. Добрый день!
      Да, отключение BOD доступно именно для 168PA/328P. Но это не должно влиять на работоспособность, по идее можно и закомментировать. Как проявляется, что скетч становится нерабочим?

      Удалить
  13. Сейчас ещё раз перепроверил и я был не прав. И ATMega8 вполне себе работает. При замыкании PD2 на GND Появляется высокий уровень на PA5 и импульсы на PD9, PD10. Возможно сначала были допущены ошибки при компиляции или при конфигурации фузе бит. Так как для упрощения использую ATMega8 c тактированием от внутреннего генератора 8 МГц.

    ОтветитьУдалить
  14. Захотелось собрать .. .

    возник такой вопрос - в схеме не указан тумблер - на 4ю ногу как я понял он и на землю подключен ?

    ОтветитьУдалить
  15. Здравствуйте, какие размеры коробки и толщина дерева?

    ОтветитьУдалить
  16. Этот комментарий был удален автором.

    ОтветитьУдалить
  17. Добрый день!
    содрал схему на пиранья pro mini, закрузил скетч. Но ничего не работает. Сопротивление поставил на 1 кОм 0,5Вт его достаточно?

    ОтветитьУдалить