Промышленное производство
Промышленный Интернет вещей | Промышленные материалы | Техническое обслуживание и ремонт оборудования | Промышленное программирование |
home  MfgRobots >> Промышленное производство >  >> Manufacturing Technology >> Производственный процесс

Монстр в коробке

Компоненты и расходные материалы

Деревянный ящик / ящик
× 1
Arduino UNO
× 1
Adafruit Wave Shield
× 1
4-канальный релейный модуль SainSmart
× 1
Двигатель стеклоочистителя
× 1
Красные светодиодные рождественские огни (100)
× 1
Дымовая машина
× 1
Активный усилитель / динамик
× 1

Об этом проекте

*** ОБНОВЛЕНО до версии 4 ***

Недавно я переписал код Arduino для этого проекта. Вот краткое изложение изменений:

  • Главный цикл теперь реализован как конечный автомат.
  • Все время теперь основано на оценке времени события и текущего времени.

- время больше не зависит от кадров

- разрешено удаление delay () в основном цикле

- устраняет проблему "порт занят" при подключении к Arduino IDE

  • Реле теперь используют нормально открытые, а не нормально закрытые соединения *** Обновите свои релейные соединения !!! ***
  • Добавлен светодиод обнаружения движения.
  • Добавлен индикатор готовности к пробуждению.
  • Добавлен индикатор паузы.
  • Удален переключатель триггера действия.
  • Добавлена ​​возможность добавлять дополнительное время к Red Lights &Smoke

- позволяет этим эффектам работать немного дольше, чем у баунсера крышки

  • Добавлено много комментариев.

Вы найдете весь последний код здесь, на github

Монстр в коробке

Я люблю реквизит на Хэллоуин, я видела и читала о каком-то замечательном монстре в коробке построил в прошлом году и решил, что должен построить свою собственную. Идея довольно проста:создать иллюзию, что какой-то контейнер содержит опасного монстра, который находится на грани побега. Иллюзию можно создать с помощью любой комбинации движения, звука, света, дыма и, конечно же, неожиданности.

Что в коробке!?!?

Вам нужна коробка, достаточно большая, чтобы в ней могло поместиться что-то большое и пугающее. Это также добавляет иллюзии, если ящик кажется старым, сильно изношенным и, возможно, достаточно сильным, чтобы удержать монстра в страхе. Сначала я искал что-то в благотворительных магазинах и в Интернете, но никогда не покупал что-то, что мне нравилось, поэтому я создал свое собственное. Это было не очень сложно.

Я использовал 15 6-футовых пикетов для сосновых заборов от Home Depot, чтобы сделать коробку размером примерно 3 фута x 2,5 фута x 2,5 фута. Я отрезал всю доску по длине настольной пилой и собрал коробку, используя пневматический гвоздезабиватель 18 калибра. Похоже, это сработало, но позже я понял, что стержни были недостаточно прочными, чтобы удерживать коробку вместе из-за всех ударов и отскоков, которые она будет делать. Чтобы укрепить коробку, я позже скрутил ее 1-дюймовыми шурупами для гипсокартона (изнутри наружу, чтобы они не были видны).

После постройки я состарил дерево с помощью черного чая, уксуса и стальной ваты. Затем я украсил его трафаретами и этикетками, которые нашел в Интернете и / или создал и распечатал.

Brainzzzzz !!!

Опора имеет 2 рабочих состояния:«Спящий» и «Пробуждение». Во время сна ящик относительно спокоен и издает только храп и легкое рычание. Монстр просыпается, когда злоумышленник срабатывает с датчиком движения. Когда монстр просыпается, монстр рычит, вдыхает дым, отскакивает от крышки, а внутренняя часть коробки светится красным.

Я использовал Arduino Uno вместе с WaveShield и релейным модулем, чтобы управлять поведением этой опоры. WaveShield загружен небольшой коллекцией звуков сна и рев. Датчик движения PIR обеспечивает вход в Arduino для переключения коробки между «спящим» и «бодрствующим» режимами. В режиме ожидания Arduino активирует релейные каналы для запуска двигателя крышки, красных огней и дымогенератора. и воспроизвести звуки на WaveShield. Еще одна функция, которую я добавил, - это кнопка паузы. Это позволило мне временно заставить монстра замолчать, когда к нему подходят младшие дети.

Это Алииииииве!

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

Я купил подержанный мотор стеклоочистителя на местной свалке металлолома за 15 долларов. Это было забавно. Я вошел и попросил мотор. Парень за стойкой спросил, «какой марки и модели автомобиль», когда я сказал «мне все равно», его голова немного наклонилась в сторону, и он посмотрел на меня немного сбоку. После того, как я объяснил, чем я занимаюсь, он захотел построить такой :)

Эти двигатели, независимо от марки / модели, работают от 12 вольт, вращаются с разумной скоростью и обладают большим крутящим моментом:идеально! Примечание. Когда вы его получите, убедитесь, что в нем есть старые жгуты проводов, так вам будет намного проще прикрепить к нему провод. также убедитесь, что у него есть шатун и смещенная стойка. Если главная опора двигателя - единственное физическое соединение, которое вам нужно работать с кулачком, скорее всего, соскользнет.

Установите мотор где-нибудь внутри коробки. Ставлю свой на одну из боковых стенок. Помните, что к нему будет подключен большой вращающийся кулачок, и он должен иметь возможность свободно вращаться и очищаться от любых предметов, особенно проводов, которые вы собираетесь положить в коробку. На YouTube есть несколько хороших руководств по работе с этими двигателями.

Я вырезал кулачок диаметром 12 дюймов из куска полуслойной древесины. сначала я вырезал идеальный круг. Я установил его на двигатель и использовал его, чтобы определить необходимую высоту двигателя в коробке. Я хотел, чтобы крышка приподнялась примерно на 2 дюйма. После подгонки я использовал лобзик, чтобы произвольно вырезать «зубья» на кулачке, изо всех сил стараясь сохранить их произвольную ширину и глубину.

Наконец, я прикрепил ролик к нижней стороне крышки, используя 2 металлических L-образных кронштейна, 1-дюймовую нейлоновую прокладку и болт с квадратным подголовком. Ролик расположен прямо над кулачком, так что он движется по зубцам кулачка.

Я использовал шину 12 В источника питания ATX для питания двигателя через реле, управляемое Arduino. Да, для того, чтобы все выстроить в линию, действительно требуется немного проб и ошибок. После повторного позиционирования ролика один или два раза ... трижды хорошо ... все выровнялось, и крышка начала подпрыгивать, как и планировалось!

Дыхание огня:дым и свет

Я использовал дешевый дымогенератор мощностью 400 Вт для создания дымовых эффектов. Из коробки это было радиоуправляемое. Чтобы управлять им с помощью Arduino, я открыл приемник и припаял две выводные линии к контактным площадкам спусковой кнопки. Это предоставило мне линии, которые я подключил к релейному каналу, управляемому Arduino. Это был простой прием, которому я научился, просмотрев несколько видеороликов на YouTube. Я также добавил старый шланг для пылесоса, чтобы дым выходил струей прямо из-под крышки. Мне понравился визуальный эффект, он помог уменьшить конденсацию пара на электронике внутри коробки.

Для фонарей я просто отрезал удлинитель для легких нагрузок и подключил его к релейному каналу. Связанная с ним цепочка из 100 красных светодиодов может затем включаться и выключаться Arduino.

Используйте свой внешний голос

WaveShield имеет 1/8 дюймовое гнездо для наушников, а также выход, а также 2 контакта ввода-вывода для прямого подключения. Я использовал патч-аккорд 1/8 дюйма для подключения к усилителю бас-гитары мощностью 30 Вт, который я позаимствовал из моей репетиционной комнаты. Подойдет любое количество динамиков с усилителем, включая динамики ПК. Но использование чего-то с солидным низким уровнем определенно является плюсом.

Закрепи это

Я купила пластиковые цепочки в магазине на Хэллоуин и напечатала висячий замок на 3D-принтере. Обертывание ими ящика добавило глубины и ощущения иллюзии.

Хэллоуин !!!

Поставьте ящик во дворе и спрячьте датчик движения в ближайшем кусте. Я использовал длинный провод динамика для подключения датчика, чтобы я мог поэкспериментировать с расположением так, чтобы монстр просыпался, когда кто-то приближался (около 5 футов) к ящику.

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

Подойдя к подъездной дорожке, любители уловок замечают рычащий ящик:одни с любопытством, другие на самом деле его боялись. Когда они приблизились и чудовище ожило, они вскакивали, и некоторые даже аплодировали. Это был огромный успех.

Улучшения

Мне надоело искать способы спрятать датчик движения в кустах, поэтому я приклеил его горячим клеем к животу пластиковой крысы, которую я мог бы разместить где-нибудь на подъездной дорожке или под ближайшим кустом. Я также установил телефонный разъем RJ11 на задней части коробки, чтобы я мог подключить датчик движения крысы с помощью телефонной веревки длиной 50 футов, что намного лучше, чем две жилы провода динамика, которые я использовал ранее.

Вы заметите, что я также добавил к этой новой пластине переключатель и несколько светодиодных индикаторов. Переключатель ПРИОСТАНОВЛЯЕТ все функции на приставке, не выключая его. Мой главный аварийный выключатель - это удлинитель внутри, и к нему трудно получить доступ, плюс он использует только сигнальное напряжение (5 В) на этом внешнем переключателе. Этот переключатель отлично подходит для остановки монстра для молодых любителей трюков и других, которые хотят заглянуть внутрь в ночь на Хэллоуин.

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

Будущее

Есть несколько вещей, которые я хочу добавить в будущем. Может быть, пульт дистанционного управления, чтобы я мог приостановить или вызвать монстра на расстоянии. Я также добавлю некоторую обратную связь к подъемнику крышки, чтобы Arduino мог «знать», когда крышка открыта или закрыта. Несколько раз атлет останавливался на высокой точке цикла, которая делала «внутренности» коробки видимыми до следующего цикла пробуждения. Наконец, я могу подключить внешнее освещение / стробоскопы к Arduino, чтобы позволить им управлять с помощью программы и / или брелока дистанционного управления.

Репозиторий GitHub

Вы найдете последний код и схемы подключения Здесь, на GitHub

Код

  • Набросок "Монстр в коробке"
  • MonsterSounds.h
  • MonsterSounds.ino
Набросок "Монстр в коробке" C / C ++
 / * Используемые контакты Wave Shield:2, 3, 4, 5, 10, 11, 12 и 13 Контакты 13, 12, 11 всегда используются SD-картой (это единственные контакты, которые имеют высокоскоростной SPI интерфейс). Затем есть еще 5 контактов, используемых для связи с ЦАП и SD-картой, но их можно настроить для подключения к любому контакту Arduino. Однако по умолчанию библиотека настроена на использование контактов 10 (для SD-карты) и контактов 2, 3, 4 и 5 для ЦАП. Для переключения этих выводов требуется изменение библиотеки - на выводы ссылаются их «аппаратные» имена выводов (например, PORTD и т. Д.), А не выводы arduino. Это означает, что доступны контакты 6, 7, 8, 9 и 6 аналоговых входов (также известные как цифровые входы / выходы 14-20). Https://learn.adafruit.com/adafruit-wave-shield-audio- shield-for-arduino / faq * / # include "MonsterSounds.h" #define RESERVED_00 0 // Зарезервировано для последовательного RX # define RESERVED_01 1 // Зарезервировано для Serial TX # define RESERVED_02 2 // Зарезервировано для Wave Shield #define RESERVED_03 3 // Зарезервировано для волнового экрана # define RESERVED_04 4 // Зарезервировано для волнового экрана # define RESERVED_05 5 // Зарезервировано для волнового экрана # define FOG_MACHINE 6 // Подключите цифровой вывод на Arduino к модулю реле # define RED_LEDS 7 // Подключите цифровой вывод на Arduino к релейному модулю # define LID_BOUNCER 8 // Подключите цифровой вывод на Arduino к релейному модулю #define RESERVED_09 9 // Подключите цифровой вывод на Arduino к релейному модулю # define RESERVED_10 10 // Зарезервировано для Wave Shield #define RESERVED_11 11 // Зарезервировано для Wave Shield #define RESERVED_12 12 // Зарезервировано для Wave Shield #define RESERVED_13 13 // Зарезервировано для Wave Shield #define PIR_SENSOR A 0 // Вход PIR # define MOTION_LED A1 // Светодиод:загорается при обнаружении движения (независимо от состояния паузы / сна / пробуждения) #define PAUSED_LED A2 // Светодиод:загорается, когда система приостановлена ​​# define READY_LED A3 // Светодиод:загорается когда монстр находится в состоянии READY_TO_WAKE #define PAUSE_BUTTON A4 // Вход переключателя паузы # define DEBUG_BUTTON A5 // Вход переключателя отладки // Настройки таймера эффектов - в секундах (ИЗМЕНИТЬ) #define WAKE_DELAY 30 // Минимальное время между 'пробуждением' событий в секундах # define WAKE_DELAY_DEBUG 10 // переопределение WAKE_DELAY при включении переключателя DEGUB # define SLEEP_SOUND_DELAY 1 // количество секунд ожидания между попыткой сработать следующий звук "сна" #define WAKE_MIN 3 // минимальное время пробуждения in Seconds #define WAKE_MAX 5 // Максимальное количество времени "бодрствования" в секундах #define RED_LIGHT_EXTRA_TIME 1 // Позволяет красным светам работать немного дольше, чем шезлонг крышки, при желании # define SMOKE_EXTRA_TIME 2 // Позволяет дыму выходить при желании немного длиннее, чем крышка крышки // Эффекты Таймеры Настройки - в миллисекундах (не редактирует ЭТ) #define WAKE_DELAY_MILLIS WAKE_DELAY * 1000 # определить WAKE_DELAY_DEBUG_MILLIS WAKE_DELAY_DEBUG * 1000 # определить SLEEP_SOUND_DELAY_MILLIS SLEEP_SOUND_DELAY * 1000 #define WAKE_MIN_MILLIS WAKE_MIN * 1000 # определить WAKE_MAX_MILLIS WAKE_MAX * 1000 # определить RED_LIGHT_EXTRA_TIME_MILLIS RED_LIGHT_EXTRA_TIME * 1000 # определяют SMOKE_EXTRA_TIME_MILLIS SMOKE_EXTRA_TIME * 1000MonsterSound звуки; статическое беззнаковое долгое времяSinceLastSnore =0; статическое беззнаковое долгое время wakeAllowedTimer =0; статическое беззнаковое длинное lidBounceTimer =0; статическое беззнаковое длинное время lidBounceDuration =0; статическое беззнаковое длинное время SmokeTimer =0; статическое беззнаковое длинное статическое длительное время =0; redLightTimer =0; static unsigned long redLightDuration =0; enum States {STATE_INITIALIZE, // Только при запуске setup () и в первый раз в loop () STATE_PAUSED, // Отключить все звуки и эффекты STATE_SLEEPING, // Нет эффектов, звуки сна , не позволяет запускать пробуждение STATE_READY_TO_WAKE, // Нет эффекты, звуки сна, позволяют активировать бодрствование STATE_AWAKE}; // Запускает эффекты и звуки пробуждения монстра State state =STATE_INITIALIZE; void setup () {// инициализирует последовательную связь:Serial.begin (9600); // Устанавливаем все контакты реле pinMode (LID_BOUNCER, OUTPUT); pinMode (RED_LEDS, ВЫХОД); pinMode (FOG_MACHINE, ВЫХОД); pinMode (PAUSED_LED, ВЫХОД); pinMode (MOTION_LED, ВЫХОД); pinMode (READY_LED, ВЫХОД); // Принудительное отключение всех эффектов stopAllEffects (); pinMode (PIR_SENSOR, INPUT); pinMode (PAUSE_BUTTON, INPUT_PULLUP); pinMode (DEBUG_BUTTON, INPUT_PULLUP); звуки.initialize (); // Звуки монстров звуки.playSystemReady (); задержка (1000); Serial.println (); Serial.print («*** Система готова ***»); Serial.println (); } / * * ПРИМЕЧАНИЕ. Все кнопки используют подтягивания, поэтому НИЗКИЙ означает, что кнопка НАЖАТА. * Помните, что подтягивание означает, что логика переключения инвертирована. * Он становится ВЫСОКИМ, когда он открыт, и НИЗКИМ, когда он нажимается. * * Датчик движения PIR НЕ ведет себя подобным образом. * // * * Основной цикл обработки * - Управляет конечным автоматом монстра * / void loop () {boolean pauseSwitchClosed =digitalRead (PAUSE_BUTTON) ==LOW; логическое motionDetected =digitalRead (PIR_SENSOR) ==HIGH; digitalWrite (MOTION_LED, digitalRead (PIR_SENSOR)); переключатель (состояние) {case STATE_INITIALIZE:if (pauseSwitchClosed) {goToPause (); } еще {goToSleep (); } ломать; case STATE_PAUSED:если (! pauseSwitchClosed) {goToSleep (); digitalWrite (PAUSED_LED, LOW); } else {digitalWrite (PAUSED_LED, HIGH); } ломать; case STATE_SLEEPING:если (pauseSwitchClosed) {goToPause (); } иначе, если (isAllowedToWake ()) {goToReadyToWake (); } еще {processSleeping (); } ломать; case STATE_READY_TO_WAKE:если (pauseSwitchClosed) {goToPause (); digitalWrite (READY_LED, LOW); } иначе, если (motionDetected) {goToAwake (); digitalWrite (READY_LED, LOW); } еще {processSleeping (); } ломать; case STATE_AWAKE:если (pauseSwitchClosed) {goToPause (); } иначе, если (processAwakeAnimation ()) {goToSleep (); } // processAwakeAnimation () возвращает истину, когда все анимации полностью завершены break; по умолчанию:Serial.println («НЕИЗВЕСТНОЕ СОСТОЯНИЕ»); ломать; // Мы никогда сюда не доберемся}} / * * Переход в состояние паузы * / inline void goToPause () {Serial.println ("PAUSED"); состояние =STATE_PAUSED; stopAllEffects (); Sounds.stopAll ();} / * * Переход в состояние сна * / inline void goToSleep () {Serial.println ("GOING TO SLEEP"); состояние =STATE_SLEEPING; wakeAllowedTimer =millis ();} / * * Переход в состояние готовности к пробуждению * Это особый случай состояния сна * / inline void goToReadyToWake () {Serial.println ("READY TO WAKE"); состояние =STATE_READY_TO_WAKE; } / * * Переход в состояние пробуждения * - разбудить монстра и обработать эффекты и звуки * / inline void goToAwake () {Serial.println ("AWAKE"); состояние =STATE_AWAKE; wakeMonster ();} / * * обработать цикл активности SLEEP * - Запустить звуки сна * - Обновить таймер сна * / inline void processSleeping () {if ((millis () - timeSinceLastSnore)> SLEEP_SOUND_DELAY_MILLIS) {Sound.playSnore ( ); timeSinceLastSnore =millis (); }} / * * Определяет, разрешено ли монстру просыпаться в это время. * - Проверьте переключатель отладки, если он закрыт, мы используем более короткий таймер разрешенного пробуждения * - Монстр должен спать в течение заранее определенного минимального времени, прежде чем он может быть разбужен * - Загорается светодиод, когда он готов к пробуждению * / inline boolean isAllowedToWake ( ) {логическое isDebug =digitalRead (DEBUG_BUTTON) ==LOW; беззнаковый длинный requiredDelay =WAKE_DELAY_MILLIS; если (isDebug) {requiredDelay =WAKE_DELAY_DEBUG_MILLIS; } логическое isAllowed =(millis () - wakeAllowedTimer)> requiredDelay; если (isAllowed) {digitalWrite (READY_LED, HIGH); } return isAllowed;} / * * Wake Monster * Запускает анимацию пробуждения * Воспроизводит звуки пробуждения * * Вызовите это ОДИН РАЗ, чтобы запустить состояние пробуждения. * / void wakeMonster () {int activityDuration =random (WAKE_MIN_MILLIS, WAKE_MAX_MILLIS); // это как долго монстр будет активен Serial.print ("wake duration:"); Serial.print (activityDuration); Serial.println ("мс"); bounceLid (activityDuration); flashRedLight (activityDuration + RED_LIGHT_EXTRA_TIME_MILLIS); activateSmoke (activityDuration + SMOKE_EXTRA_TIME_MILLIS); Sounds.playRoar ();} / * * Управляет ходом анимации ПРОБУЖДЕНИЯ * Вызов этого КАЖДОГО ЦИКЛА во время состояния ПРОБУЖДЕНИЯ. * Возвращает ИСТИНА, когда все анимации завершены * / boolean processAwakeAnimation () {printTimersToLog (); логическое done1 =false; логическое done2 ​​=false; логическое done3 =false; если (millis () - lidBounceTimer> lidBounceDuration) {bounceLid (0); done1 =true; } если (millis () - redLightTimer> redLightDuration) {flashRedLight (0); done2 ​​=true; } если (millis () - smokeTimer> smokeDuration) {activateSmoke (0); done3 =true; } return done1 &&done2 ​​&&done3;} / * * Управление эффектом:подпрыгивание крышки коробки * - дирация - это количество миллисекунд, в течение которых должен выполняться эффект * - длительность 0 означает, что эффект должен быть остановлен * / inline void bounceLid (unsigned большая продолжительность) {if (duration <=0) {energizeRelay (LID_BOUNCER); lidBounceDuration =0; } else {// запускаем подпрыгивание крышки de_energizeRelay (LID_BOUNCER); lidBounceTimer =millis (); lidBounceDuration =продолжительность; }} / * * Управление эффектом:мигание красным светом * - дирация - это количество миллисекунд, в течение которых эффект должен выполняться * - длительность 0 означает, что эффект должен быть остановлен * / inline void flashRedLight (unsigned long duration) {if (duration <=0) {energizeRelay (RED_LEDS); redLightDuration =0; } else {// запускаем мигание света de_energizeRelay (RED_LEDS); redLightTimer =миллис (); redLightDuration =продолжительность; }} / * * Start / Stop Effect:Activate Smoke * - дирация - это количество миллисекунд, в течение которых должен выполняться эффект * - длительность 0 означает, что эффект должен быть остановлен * / inline void activateSmoke (unsigned long duration) {// ' нажмите кнопку «дыма» // продолжительность должна быть фиксированным периодом времени, необходимым для того, чтобы машина отреагировала на действие // установить тайм-аут для остановки после продолжительности if (duration <=0) {energizeRelay (FOG_MACHINE); SmokeDuration =0; } else {// запускаем мигание света de_energizeRelay (FOG_MACHINE); SmokeTimer =миллис (); SmokeDuration =продолжительность; }} / * * Остановить все эффекты * - Это эффективно выключает монстра * / inline void stopAllEffects () {bounceLid (0); flashRedLight (0); activateSmoke (0);} / * * Печатает таймеры анимации пробуждения в журнал один раз в секунду * / inline void printTimersToLog () {static unsigned long timeofLastTimerLog =0; if (millis () - timeofLastTimerLog> =1000) {Serial.print ("крышка:"); Serial.print ((millis () - lidBounceTimer)> lidBounceDuration? 0:(lidBounceDuration - (millis () - lidBounceTimer))); Serial.print ("свет:"); Serial.print ((millis () - redLightTimer)> redLightDuration? 0:(redLightDuration - (millis () - redLightTimer))); Serial.print ("дым:"); Serial.println ((millis () - smokeTimer)> smokeDuration? 0:(smokeDuration - (millis () - smokeTimer))); timeofLastTimerLog =миллис (); }} / * * Реле включения * Устанавливает нормально открытый (NO) терминал в OPEN * Нормально закрытый становится закрытым * / inline void energizeRelay (int channel) {digitalWrite (channel, HIGH); } / * * Реле обесточивания * Устанавливает нормально разомкнутую (NO) клемму в положение ЗАКРЫТО. * Обычно закрытый становится ОТКРЫТЫМ * / inline void de_energizeRelay (int channel) {digitalWrite (channel, LOW); } 
MonsterSounds.h C / C ++
Заголовок Arduino для библиотеки звуков монстров
 / * ПРИМЕЧАНИЕ О ПИН-кодах ARDUINO * Контакты 13, 12, 11 всегда используются SD-картой (это единственные контакты, которые имеют высокоскоростной интерфейс SPI). * Кроме того, есть еще 5 контактов, используемых для связи с ЦАП и SD-картой, но их можно настроить для подключения к любому контакту Arduino. * Однако по умолчанию библиотека настроена на использование контактов 10 (для SD-карты) и контактов 2, 3, 4 и 5 для ЦАП. * Для переключения этих контактов требуется изменение библиотеки - на контакты ссылаются их «аппаратные» имена контактов (например, PORTD и т. Д.), А не по контактам Arduino. * Это означает, что доступны контакты 6, 7, 8, 9 и 6 аналоговых входов (также известные как цифровые входы / выходы 14-20). * * / #include  #include  #include  #include  static const char roar0 [] ="ROAR0000.wav"; static const char roar1 [] ="ROAR0001.wav"; static const char roar2 [] ="ROAR0002.wav"; static const char * const roarSounds [] ={roar0, roar1, roar2}; static const char sleep0 [] ="SNORE000.wav"; static const char sleep1 [] ="SNORE001.wav"; static const char sleep2 [] ="SNORE002.wav"; static const char * const sleepSounds [] ={sleep0, sleep1, sleep2}; int previousRoarSound =-1; класс MonsterSounds {частный:карта SdReader; // Этот объект содержит информацию о карте FatVolume vol; // Содержит информацию о разделе на карте FatReader root; // Содержит информацию о корневом каталоге тома FatReader file; // Этот объект представляет файл WAV для фразы WaveHC wave; // Одиночный волновой объект - одновременно воспроизводится только один звук void playfile (char * name); общедоступные:void initialize (); void playSystemReady (); void playRoar (); void playSnore (); void stopAll ();}; 
MonsterSounds.ino C / C ++
Код Arduino для библиотеки звуков монстров
 / * ПРИМЕЧАНИЕ О ПИН-кодах ARDUINO * Контакты 13, 12, 11 всегда используются SD-картой (это единственные контакты, которые имеют высокоскоростной интерфейс SPI). * Кроме того, есть еще 5 контактов, используемых для связи с ЦАП и SD-картой, но их можно настроить для подключения к любому контакту Arduino. * Однако по умолчанию библиотека настроена на использование контактов 10 (для SD-карты) и контактов 2, 3, 4 и 5 для ЦАП. * Для переключения этих контактов требуется изменение библиотеки - на контакты ссылаются их «аппаратные» имена контактов (например, PORTD и т. Д.), А не по контактам Arduino. * Это означает, что доступны контакты 6, 7, 8, 9 и 6 аналоговых входов (также известные как цифровые входы / выходы 14-20). * * / void MonsterSounds ::initialize () {Serial.println ("Инициализация звуков ..."); if (! card.init ()) Serial.println (F ("Ошибка инициализации карты!")); if (! vol.init (card)) Serial.println (F («Нет раздела!»)); если (! root.openRoot (vol)) Serial.println (F («Не удалось открыть каталог»)); Serial.println (F ("Файлы найдены:")); root.ls (); randomSeed (analogRead (0));} void MonsterSounds ::playSystemReady () {this-> playfile ("WELCOME0.WAV");} void MonsterSounds ::playRoar () {int index =random (3); // 0, 1, 2 while (index ==previousRoarSound) {index =random (3); } previousRoarSound =index; this-> playfile (roarSounds [index]);} void MonsterSounds ::playSnore () {if (! wave.isplaying) // Не прерывайте существующий звук храпом {int index =random (3); // 0, 1, 2 this-> playfile (sleepSounds [index]); }} void MonsterSounds ::stopAll () {wave.stop (); // Остановить любой проигрываемый в данный момент WAV} // --------------------------------------- ---------------------------- // playfile () // Открыть и начать воспроизведение WAV-файла // ------ -------------------------------------------------- ----------- void MonsterSounds ::playfile (char * name) {PgmPrint ("Воспроизведение звука:"); Serial.println (имя); if (wave.isplaying) {// уже что-то играет, так что прекратите! wave.stop (); // останавливаем его} if (! file.open (root, name)) {PgmPrintln ("Файл не найден"); возвращение; } if (! wave.create (файл)) {PgmPrintln ("Недействительный WAV"); возвращение; } // хорошо, пора играть! wave.play ();} 

Изготовленные на заказ детали и корпуса

monstersounds_7vLZD3NU4t.zip

Схема


Производственный процесс

  1. Машина ЭЭГ
  2. Коробка сока
  3. Торговый автомат
  4. Сменить машину
  5. Швейная машина
  6. Колготки
  7. Сделайте машинку для письма домашнего задания дома
  8. Giftduino - идеальная подарочная коробка для Arduino
  9. Ультразвуковой левитационный аппарат с использованием ARDUINO
  10. Погодное окно Arduino + ESP