Добрый день
подскажите простой вопрос как одновременно изменить состояние скажем 10 портов
вот так напрмер это можно записать?
digitalWrite((5,6,7,8,9,10), LOW);
И второй вопрос,
Мне нужно 2 раза в день на время 20-60 секунд включить 1 нагрузку.
А вот время это уже подбирается методом "полевых испытаний", поэтому решил прописать в лоб все порты по очереди на разный интервал.
014 | pinMode(13,OUTPUT); } |
020 | digitalWrite(13, HIGH); |
021 | digitalWrite(12, HIGH); |
022 | digitalWrite(11, HIGH); |
023 | digitalWrite(10, HIGH); |
024 | digitalWrite(9, HIGH); |
025 | digitalWrite(8, HIGH); |
026 | digitalWrite(7, HIGH); |
027 | digitalWrite(6, HIGH); |
028 | digitalWrite(5, HIGH); |
029 | digitalWrite(4, HIGH); |
030 | digitalWrite(3, HIGH); |
031 | digitalWrite(2, HIGH); |
036 | digitalWrite(13, LOW); |
038 | digitalWrite(12, LOW); |
040 | digitalWrite(11, LOW); |
042 | digitalWrite(10, LOW); |
044 | digitalWrite(9, LOW); |
046 | digitalWrite(8, LOW); |
048 | digitalWrite(7, LOW); |
050 | digitalWrite(6, LOW); |
052 | digitalWrite(5, LOW); |
054 | digitalWrite(4, LOW); |
056 | digitalWrite(3, LOW); |
058 | digitalWrite(2, LOW); |
061 | digitalWrite(13, HIGH); |
062 | digitalWrite(12, HIGH); |
063 | digitalWrite(11, HIGH); |
064 | digitalWrite(10, HIGH); |
065 | digitalWrite(9, HIGH); |
066 | digitalWrite(8, HIGH); |
067 | digitalWrite(7, HIGH); |
068 | digitalWrite(6, HIGH); |
069 | digitalWrite(5, HIGH); |
070 | digitalWrite(4, HIGH); |
071 | digitalWrite(3, HIGH); |
072 | digitalWrite(2, HIGH); |
079 | digitalWrite(13, LOW); |
081 | digitalWrite(12, LOW); |
083 | digitalWrite(11, LOW); |
085 | digitalWrite(10, LOW); |
087 | digitalWrite(9, LOW); |
089 | digitalWrite(8, LOW); |
091 | digitalWrite(7, LOW); |
093 | digitalWrite(6, LOW); |
095 | digitalWrite(5, LOW); |
097 | digitalWrite(4, LOW); |
099 | digitalWrite(3, LOW); |
101 | digitalWrite(2, LOW); |
104 | digitalWrite(13, HIGH); |
105 | digitalWrite(12, HIGH); |
106 | digitalWrite(11, HIGH); |
107 | digitalWrite(10, HIGH); |
108 | digitalWrite(9, HIGH); |
109 | digitalWrite(8, HIGH); |
110 | digitalWrite(7, HIGH); |
111 | digitalWrite(6, HIGH); |
112 | digitalWrite(5, HIGH); |
113 | digitalWrite(4, HIGH); |
114 | digitalWrite(3, HIGH); |
115 | digitalWrite(2, HIGH); |
вот так пока выглядит код (секунды то я поправлю до нужных величин), писарь я еще тот...
http://arduino.ru/Tutorial/Upravlenie_portami_cherez_registry
Это для начала. Астальное в литературе и примерах..
http://arduino.ru/Tutorial/Upravlenie_portami_cherez_registry
Это для начала. Астальное в литературе и примерах..
Это сложно для начинающего. Тем более что ему не нужно СТРОГО одновременно.) Проще в цикле:
1
const
byte
key[] = {9,10,11,12,14,15,16,17,18,19};
2
3
for
(
byte
i = 0; i <
sizeof
(key); i++){
4
pinMode(key[i], INPUT_PULLUP);
подскажите простой вопрос как одновременно изменить состояние скажем 10 портов
Видимо, имелось в виду "пинов".
Ответ: никак, от слова "совсем никак".
Одновременно можно менять только те пины, которые на одном порте сидят (а таких не более 8-ми по определению). Если это устраивает, то Вам уже дади ссылку. Ну и библиотека есть.
Это для начала. Астальное в литературе и примерах..
Это сложно для начинающего. Тем более что ему не нужно СТРОГО одновременно.) Проще в цикле:
[/quote]
Какой же он начинающий? Четыре года на сайте.
4 года не срок... Тут вон люди регистрируются чтобы курсовую нахаляву заполучить, не справляются, идут в армию... там ещё на второй год пару раз остаются и всё, четыре года пролетели как миг ;)
Вернувшись к теме .... управлять регистрами прямыми командами не сложно. Один раз разобраться с двоичным счётом пинов в порту и расположением самих портов.
Проблема в другом. Во время отладки и перераспределения пинов гораздо труднее пересчитать обращение в регистр и ничего не забыть.
Опять же некоторые библиотеки уже прописаны с определёнными пинами прописаны.
Сложно перенести скетч на другой МК.
Но в приведённом автором скетче конечно же регистрами управлять само проситься.
Моё мнение: Если все пины одновременно надо включать - выключать - надо в корне концепцию всего устройства менять.
Конечно надо. Поставить сдвиговый регистр с защёлкой, например.
спасибо за ответы
я и правда новичок, 4 года назад использовал ардуино и регистрировался что то хотел спросить но видимо сам разобрался, там код на 5 строк был...
Возвращаюсь к вопросу.
Про регистры читал, принцип понял, особо не вникал, но видимо для текущей ситуации это мне не очень обязательно.
еще есть вопрос
вот так можно паузы писать? То есть сразу в скобках проводить арифметические действия?
01
void
setup
() {
02
int
T;
03
T=10000;
04
05
void
loop
()
06
{
07
08
//пауза с 12 часов ночи до 8 утра
09
delay( 8*60*60*1000);
10
11
digitalWrite(13, LOW);
12
delay(T);
13
delay(T+1000);
14
}
паузы так писать можно, но остальной код совершенно нерабочий. Переменная Т определена в setup и потому в loop работать не будет. Сам setup не закрыт...
Ну и вообще, если вы будуете задавать время с помощью delay() - больше одного реле у вас в проекте работать не будет, а в первом сообщении вам вроде требовалось много портов
Да и строка №9. Формально-то оно правильно, но выглядит просто страшно.
остальной код совершенно нерабочий. Переменная Т определена в setup и потому в loop работать не будет. Сам setup не закрыт...
вопрос только в незакрытом сетапе? или переменную надо из сетапа вынести выше?
у меня как раз только одно реле работать и будет. порты (пины) хотел задействовать что бы появилось возможность переключая проводком менять время работы реле.
а вобще сейчас в голову пришла еще мысль.
подключить кнопку записи необходимого времени работы.
реле управляет мотором шнека.
нажимаем кнопку, считаем время, глазами с весами ждем пока шнек нагрузит необходимую дозу материала. отпускаем кнопку, записываем значение времени T в EEPROM.
только это я буду месяц писать;)
только это я буду месяц писать;)
Если почитаете статьи в секретном блоге, то все пойдет быстрее.
Да и строка №9. Формально-то оно правильно, но выглядит просто страшно.
У меня - выводит 29696.
1
void
setup
() {
2
Serial
.begin(115200);
3
}
4
5
void
loop
() {
6
Serial
.println(8*60*60*1000);
7
delay(1000);
8
}
Точно правильно. У Вас неудачный тест. Параметр delay описан как uint32_t, поэтому корректный тест выглядит так:
01
void
setup
() {
02
Serial
.begin(115200);
03
}
04
05
void
__delay(uint32_t d) {
06
Serial
.println(d);
07
}
08
09
void
loop
() {
10
__delay(8*60*60*1000);
11
delay(1000);
12
}
Во блин. Я тоже на этом попался.( Век живи - век учись.(
Точно правильно. У Вас неудачный тест. Параметр delay описан как uint32_t, поэтому корректный тест выглядит так:
01
void
setup
() {
02
Serial
.begin(115200);
03
}
04
05
void
__delay(uint32_t d) {
06
Serial
.println(d);
07
}
08
09
void
loop
() {
10
__delay(8*60*60*1000);
11
delay(1000);
12
}
А по моей логике сначала должны проводться вычисления в int, и только потом получившееся 29696 приводится к типу uint32_t. И, кстати, натурные эксперименты это подтверждают, - вывод не поменялся.
Да, наверное, это меня переклинило. Может, о другом думал.
Ага. Сбивают тут, понимаешь, с пути истинного, своим авторитетом.) Достаточтно что бы один из операндов был int32_t, даже без явного указания.
Ага. Сбивают тут, понимаешь, с пути истинного, своим авторитетом.) Достаточтно что бы один из операндов был int32_t, даже без явного указания.
Нет.
Тема второй раз поднимается, в первый я и не понял в чём подвох )))
Нет.
Лаконично.
- что да?
- тоже нет.
1. Преобразование производится только тогда, когда реально нужно.
2. Все операции "*" выполняются слева направо.
Вот и всё. Т.е. не просто "один", а первый. Ну, или не первый, но такой, что "до него" никаких неприятностей не произошло.
) Вот вам "простой как валенок" пример: __delay(8*60*60*33000);
Что там насчёт первого? И "до него никаких неприятностей" - что за выражение?)
Первый - int, второй тоже, перемножается как инт и результат инт. Этот результат умножается на третий (тоже инт) результат - инт), этот результат на четвёртый. Результат опять инт, но это уже неверно - возникло переполнение. Т.е. в данном примере лонгом может быть дюбой член, но в общем случае - любой, но стоящий ДО переполнения. Вот в этот пример добавьте справа ещё один сомножитель (хоть * 2). И получите, что делать его лонгом бесполезно - ошибка уже появилась до него.
ОК. Все верно. А то я уже начал было сомневаться в теории. Подумал, может уже чего улучшили.)
А так ?
delay(8L*60L*60L*33000L);
Можно просто 8L в первой позиции, но потом константы местами не переставлять.
Прошу простить, за возможно идиотский вопрос. Сколько займет процедура "зажигания" пинов в скетче? И в чем надобность "зажигать" пины абсолютно синхронно?
если пины в ОДНОМ порту, то их можно зажигать за 2 или 4 (не помню) такта процессора ОДНОВРЕМЕННО. Зачем - ХЗ.
И в чем надобность "зажигать" пины абсолютно синхронно?
если пины в ОДНОМ порту, то их можно зажигать за 2 или 4 (не помню) такта процессора ОДНОВРЕМЕННО. Зачем - ХЗ.
что-то многовато, по идее должно за такт
CLR R0 - 1 такт
OUT PORTB,R0 - 1 такт
SER R0 - 1 такт
OUT PORTB,R0 - 1 такт
Итого 4 такта чтоб "дрыгануть" весь порт целиком.
CLR R0 - 1 такт
OUT PORTB,R0 - 1 такт
SER R0 - 1 такт
OUT PORTB,R0 - 1 такт
Итого 4 такта чтоб "дрыгануть" весь порт целиком.
я без учета записи в регистр считал, то-есть в регистре уже имеем, то, что надо зажечь, а так да...
и вопрос, без нуления данных и вывода -напрямую, незначащие биты не сбросятся?
блин, с x86 перепутал. да. ты прав, NMi.
И в чем надобность "зажигать" пины абсолютно синхронно?
вобщем то так и есть, абсолютно синхронно и не требуется. Спросил то что хотел, не размышляя о глубине вопроса до тактов и прочих тонкостей... Хотел узнать, можно ли записать одной строкой несколько пинов. я так понимаю нельзя, а жаль.
но все же хочу спросить совета, каким образом легче решить задачу с несколькими пинами.
мне нужно ежедневно в 8 утра и 6 вечера включать "единовременно" (не абсолютно синхронно, и даже не обязательно одновременно) 10 пинов но на разное время работы реле.
Реле в системе только одно, и переключается разьемом "мама" для финишной подстройки работы шнека.
и вопрос, без нуления данных и вывода -напрямую, незначащие биты не сбросятся?
Сбросятся.
Тут два варианта:
SBI или CBI - это побитно с портом.
Либо применить маску с прочитанного с порта, AND или OR в зависимости от "сбросить" или "выставить"
Третий вариант (опционально) --- XOR с маской, так мы "передёргиваем" бит или биты, естественно по маске, в порту (8 бит)
Ваащпе вариантов можно накрапать много... всё зависит от "полёта" мысли :))
1 - Хотел узнать, можно ли записать одной строкой несколько пинов. я так понимаю нельзя, а жаль.
2 - 10 пинов но на разное время работы реле.
1 - можно и одной командой.
2 - можно, но несколькими командами (не более 15-ти команд ASM)
Как? Элементарно... Стакан ---> Деду, закусь ---> мне :))
2 - можно, но несколькими командами (не более 15-ти команд ASM)
Как? Элементарно... Стакан ---> Деду, закусь ---> мне :))
Но здесь только две команды! А где остальные 13? Мож на них там и мне чего перепадёт?
если пины в ОДНОМ порту, то их можно зажигать за 2 или 4 (не помню) такта процессора ОДНОВРЕМЕННО.
А ежли "накатить" стакан-другой, то можно придумать способ и одновременно и не в одном а в нескольких портах (правда не все камни это держут) одновременно. Читаем датащи, фканце, описание портов проца. :))
Но здесь только две команды! А где остальные 13? Мож на них там и мне чего перепадёт?
Умом процессор не понять, пока не выпито 0,5 ... попЫтки глубже понимать уже подразумевают ЛИТР!!!
вобщем то так и есть, абсолютно синхронно и не требуется. Спросил то что хотел, не размышляя о глубине вопроса до тактов и прочих тонкостей... Хотел узнать, можно ли записать одной строкой несколько пинов. я так понимаю нельзя, а жаль.
Ну почему нельзя? Можно написать функцию, которая будет манипулировать несколькими пинами и вызывать эту функцию одной строкой. DigitalWrite это, кстати, тоже функция которая на самом деле занимает довольно много строк.
мне нужно ежедневно в 8 утра и 6 вечера включать "единовременно" (не абсолютно синхронно, и даже не обязательно одновременно) 10 пинов но на разное время работы реле.
Реле в системе только одно, и переключается разьемом "мама" для финишной подстройки работы шнека.
Не могу понять, что означает "10 пинов но на разное время работы реле" и причем здесь мама и шнек?
01
#pragma pack(push,1)
02
typedef
struct
03
{
04
uint8_t pin;
05
uint16_t workTimeInSeconds;
06
uint32_t startedAt;
07
08
} WorkSetting;
09
#pragma pack(pop)
10
11
WorkSetting WorkSettings[] = {
12
13
{2, 10, 0},
14
{3, 20, 0},
15
{4, 30, 0},
16
{5, 15, 0},
17
{6, 20, 0},
18
{7, 30, 0},
19
{8, 60, 0},
20
{9, 44, 0},
21
{10, 99, 0},
22
{11, 120, 0},
23
24
};
25
26
void
setup
()
27
{
28
const
size_t cnt =
sizeof
(WorkSettings)/
sizeof
(WorkSettings[0]);
29
for
(size_t i=0;i<cnt;i++)
30
{
31
pinMode(WorkSettings[i].pin,OUTPUT);
32
}
33
}
34
35
void
loop
()
36
{
37
const
size_t cnt =
sizeof
(WorkSettings)/
sizeof
(WorkSettings[0]);
38
39
if
(время_8_утра или время_6_вечера)
40
{
41
42
for
(size_t i=0;i<cnt;i++)
43
{
44
if
(WorkSettings[i].startedAt == 0)
45
{
46
digitalWrite(WorkSettings[i].pin,HIGH);
47
WorkSettings[i].startedAt = millis();
48
}
49
}
50
}
51
52
uint32_t now = millis();
53
54
for
(size_t i=0;i<cnt;i++)
55
{
56
if
(WorkSettings[i].startedAt > 0)
57
{
58
uint32_t interval = 1000UL * WorkSettings[i].workTimeInSeconds;
59
if
(now - WorkSettings[i].startedAt > interval)
60
{
61
WorkSettings[i].startedAt = 0;
62
digitalWrite(WorkSettings[i].pin,LOW);
63
}
64
}
65
}
66
}
Не могу понять, что означает "10 пинов но на разное время работы реле" и причем здесь мама и шнек?
Ардуино управляет всего лишь одним приводом шнека через реле.
Опытным путем установлено что за 60 секунд шнек нагружает необходимую массу "материала". Но поскольку поставщик материала может измениться изменится насыпная плотность и нужно будет заставить шнек работать 55 или 65 секунд. И что бы каждый раз не лезть в скетч нужно что бы все пины были настроены на разную продолжительность работы, но включались примерно в 8 утра и 18 вечера.
То есть беру просто управляющий провод от реле и переключаю на соседний пин и время подачи материала сокоащается или увеличивается.
То есть беру просто управляющий провод от реле и переключаю на соседний пин и время подачи материала сокоащается или увеличивается.
как всё запущено...а две кнопки управления временем не достаточно?
Гораздо проще подключить переменное сопротивление на аналоговый вход. и в зависимости от его положения модифицировать время работы шнека.
Опытным путем установлено что за 60 секунд шнек нагружает необходимую массу "материала". Но поскольку поставщик материала может измениться изменится насыпная плотность и нужно будет заставить шнек работать 55 или 65 секунд. И что бы каждый раз не лезть в скетч нужно что бы все пины были настроены на разную продолжительность работы, но включались примерно в 8 утра и 18 вечера.
Ну дык паставь RTC и LCD и клавиатуру и сделай меню да и управляй ты хоть часами, хоть секундами... да хоть чем. Неужели для тебя это так трудно???
Обычный галетник для выбора входа, который будет определять время работы: D2 - 45 сек, D3 - 50 секунд и т.д.
Трудно... И кнопки трудно, уж молчу про ЛСД с меню
Но ЛСД с меню конечно самый крутой вариант
Не, ну если ЛСД, то оно, конечно тяжело. Да и недёшево.
с ЛСД еще и глючно.