Created
September 7, 2015 13:52
-
-
Save markterrill/dab3fc49cddd14c971e2 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#define FAN1 D0 // A4 on old board, A0 on new board but photon doesn't have PWM etc on A0 | |
// PWM | |
//#define PWM_FREQ 25000 // in Hertz (SET YOUR FREQUENCY) for analogWrite2 | |
// TURN DEBUG ON? | |
#define MYDEBUG TRUE | |
int tinkerAnalogWrite(String command); | |
int percent = 0, dacp = 0; | |
void setup() { | |
// Start serial at 9600 baud | |
Serial.begin(9600); | |
pinMode(FAN1, OUTPUT); | |
analogWrite(FAN1, 0); | |
Spark.function("analogwrite", tinkerAnalogWrite); | |
Serial.println("Started up!"); | |
} | |
void loop() { | |
percent += 10; | |
if (percent > 100){ | |
percent = 0; | |
} | |
//percent = 30; | |
// Use PWM function | |
analogWrite2(FAN1, percent); | |
//analogWrite(DAC1, percent / 100 * 4095); | |
delay(4000); | |
} | |
void analogWrite2(uint16_t pin, double percent) { //Originally using and Bdub's code | |
TIM_OCInitTypeDef TIM_OCInitStructure; | |
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure; | |
STM32_Pin_Info* PIN_MAP = HAL_Pin_Map(); | |
uint16_t Prescaler; // 0.. 65,535 | |
uint16_t Period; // 0.. 65,535 | |
uint16_t Value; // 0.. 65,535 | |
// !! Prescaling doesn't appear to work! if you use a value less than 65534 (uint8_max) I could not get 100% | |
//Prescaler = (((SystemCoreClock / 24000) / 2) - 1); // As SystemCoreClock is 120000000 (120Mhz) on STM32F2/F4, this is setting it to 24hz frequency | |
//Prescaler = ((SystemCoreClock / 1000000) / 2) - 1; // Get clock to 1 MHz on STM32F4 | |
//Prescaler = (SystemCoreClock / 24000000) - 1; // Get clock to 24 MHz | |
//Period = 65535 - 1; | |
// Value = ((percent / 100) * (Period + 1) ); // ie 0...[Period] | |
//Seem to use uint8_max regardless, observed by setting period to 1000 and a value of 1000, it doesn't have a meaningful effect. | |
// Only when setting value to 65k can you see the motor at full | |
//Period = 65535 - 1; | |
// Calcs sourced from http://stm32f4-discovery.com/2014/05/stm32f4-stm32f429-discovery-pwm-tutorial/ | |
Prescaler = 0; //(SystemCoreClock / 120000000) - 1; | |
Period = SystemCoreClock / 25000 - 1; | |
Value = ((Period + 1) * percent) / 100 - 1; | |
Serial.println(" "); | |
Serial.print("System clock: "); | |
Serial.println(SystemCoreClock); | |
Serial.print("analogWrite2 "); | |
Serial.print(percent); | |
Serial.print("% on PIN "); | |
Serial.print(pin); | |
Serial.print(" pre: "); | |
Serial.print(Prescaler); | |
//Serial.print(" pcCalc: "); | |
//Serial.print(percentCalc); | |
Serial.print(" period: "); | |
Serial.print(Period); | |
Serial.print(" value: "); | |
Serial.println(Value); | |
// Don't re-init PWM and cause a glitch if already setup, just update duty cycle and return. | |
if (PIN_MAP[pin].pin_mode == AF_OUTPUT_PUSHPULL) { | |
Serial.print("second time around, just setting speed to "); | |
Serial.println(Value); | |
Serial.print("perip:"); | |
if (PIN_MAP[pin].timer_peripheral == TIM4){ | |
Serial.println(" TIM4"); | |
} else { | |
Serial.println(" TIM not known!!"); | |
} | |
//TIM_OCInitStructure.TIM_Pulse = TIM_CCR; | |
TIM_OCInitStructure.TIM_Pulse = Value; | |
if (PIN_MAP[pin].timer_ch == TIM_Channel_1) { | |
Serial.println("modifying TIM1"); | |
PIN_MAP[pin].timer_peripheral-> CCR1 = TIM_OCInitStructure.TIM_Pulse; | |
} else if (PIN_MAP[pin].timer_ch == TIM_Channel_2) { | |
Serial.println("modifying TIM2"); | |
PIN_MAP[pin].timer_peripheral-> CCR2 = TIM_OCInitStructure.TIM_Pulse; | |
} else if (PIN_MAP[pin].timer_ch == TIM_Channel_3) { | |
Serial.println("modifying TIM3"); | |
PIN_MAP[pin].timer_peripheral-> CCR3 = TIM_OCInitStructure.TIM_Pulse; | |
} else if (PIN_MAP[pin].timer_ch == TIM_Channel_4) { | |
Serial.println("modifying TIM4"); | |
PIN_MAP[pin].timer_peripheral-> CCR4 = TIM_OCInitStructure.TIM_Pulse; | |
} else { | |
Serial.println("did not find a TIM match"); | |
Serial.println(PIN_MAP[pin].timer_ch); | |
} | |
return; | |
} | |
// TIM Channel Duty Cycle(%) = (TIM_CCR / TIM_ARR + 1) * 100 | |
//uint16_t TIM_CCR = (uint16_t)(value * (TIM_ARR + 1) / 255); | |
pinMode(pin, AF_OUTPUT_PUSHPULL); | |
// Random guess | |
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE); | |
/* Time base configuration */ | |
//TIM_TimeBaseStructure.TIM_Prescaler = (SystemCoreClock / 1000000) - 1; // Get clock to 1 MHz on STM32F2/F4 | |
//TIM_TimeBaseStructure.TIM_Prescaler = Prescaler; // Get clock to 1 MHz on STM32F2/F4 | |
TIM_TimeBaseStructure.TIM_Prescaler = Prescaler; // Get clock to 1 MHz on STM32F2/F4 | |
TIM_TimeBaseStructure.TIM_Period = Period; | |
TIM_TimeBaseStructure.TIM_ClockDivision = 0; | |
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; | |
//TIM_TimeBaseInit(PIN_MAP[pin].timer_peripheral, &TIM_TimeBaseStructure); | |
TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure); | |
//TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure); | |
//TIM_TimeBaseInit(PIN_MAP[pin].timer_peripheral, &TIM_BaseStruct); | |
/* Enable TIM1 Preload register on ARR */ | |
//TIM_ARRPreloadConfig(TIM1, ENABLE); | |
/* TIM PWMn Mode configuration */ | |
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1; // default, set on compare match | |
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; | |
TIM_OCInitStructure.TIM_Pulse = Value; | |
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; | |
delay (3000); | |
if (PIN_MAP[pin].timer_ch == TIM_Channel_1) { | |
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1; | |
// PWM1 Mode configuration: Channel1 | |
TIM_OC1Init(PIN_MAP[pin].timer_peripheral, & TIM_OCInitStructure); | |
TIM_OC1PreloadConfig(PIN_MAP[pin].timer_peripheral, TIM_OCPreload_Enable); | |
} else if (PIN_MAP[pin].timer_ch == TIM_Channel_2) { | |
//TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; | |
// PWM1 Mode configuration: Channel2 | |
TIM_OC2Init(PIN_MAP[pin].timer_peripheral, & TIM_OCInitStructure); | |
TIM_OC2PreloadConfig(PIN_MAP[pin].timer_peripheral, TIM_OCPreload_Enable); | |
} else if (PIN_MAP[pin].timer_ch == TIM_Channel_3) { | |
//TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM3; | |
// PWM1 Mode configuration: Channel3 | |
TIM_OC3Init(PIN_MAP[pin].timer_peripheral, & TIM_OCInitStructure); | |
TIM_OC3PreloadConfig(PIN_MAP[pin].timer_peripheral, TIM_OCPreload_Enable); | |
} else if (PIN_MAP[pin].timer_ch == TIM_Channel_4) { | |
//TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM4; | |
// PWM1 Mode configuration: Channel4 | |
Serial.println("modifying TIM4 below"); | |
TIM_OC4Init(PIN_MAP[pin].timer_peripheral, & TIM_OCInitStructure); | |
TIM_OC4PreloadConfig(PIN_MAP[pin].timer_peripheral, TIM_OCPreload_Enable); | |
} | |
TIM_ARRPreloadConfig(PIN_MAP[pin].timer_peripheral, ENABLE); | |
/* TIMn Main Output Enable */ | |
TIM_CtrlPWMOutputs(PIN_MAP[pin].timer_peripheral, ENABLE); | |
// TIM enable counter | |
//TIM_Cmd(PIN_MAP[pin].timer_peripheral, ENABLE); | |
TIM_Cmd(TIM4, ENABLE); | |
} | |
int tinkerAnalogWrite(String command){ | |
int pinNumber = command.charAt(1) - '0'; | |
int rangeMin = 40; | |
int rangeMax = 100; | |
//int range = rangeMax - rangeMin; | |
rangeMin = 0; | |
int range = 255; | |
if (pinNumber< 0 || pinNumber >7) return -1; | |
String value = command.substring(3); | |
if(command.startsWith("D")){ | |
pinMode(pinNumber, OUTPUT); | |
analogWrite(pinNumber, value.toInt()); | |
return 1;} | |
else if(command.startsWith("A")){ | |
pinMode(pinNumber+10, OUTPUT); | |
if (value.toFloat() == 0){ | |
analogWrite2(FAN1, 0); | |
Serial.println("turning off"); | |
} else { | |
analogWrite2(FAN1, value.toInt()); | |
Serial.print("Doing manual speed on PIN "); | |
Serial.print(FAN1); | |
Serial.print(" value: "); | |
Serial.println(value.toInt()); | |
//analogWrite2(pinNumber+10, ((value.toFloat() / 255.0) * range) + rangeMin); | |
} | |
//analogWrite(pinNumber+10, value.toInt()); | |
return 1; | |
} | |
else return -2; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment