I’m using Timer1 as the main control for measurement and velocity control of a motor. I want to create pulses of variable duration. One option seemed to be to simply use Timer1 to control these pulses – add the wanted “off” time to the current Timer1 registers and create an event using CCP Compare.
The simple option is to stop Timer1 and calculate the “off” time, restart Timer1 and set up a CCP Compare event.
CCP1CON = 0b00001010 ; CCP Compare mode, generate software interrupt on Timer1 match.
…
…
T1CON.TMR1ON = 0 ; Stop Timer1 or we might capture rollover error.
PulseWidth = c500uS + Timer1 ; Flash LED for 500uS - so add it to Timer1 to get off count.
T1CON.TMR1ON = 1 ; Start Timer1.
CCPR1L = PulseWidth ; Set wanted CCP register Timer1 match count.
CCPR1H = PulseWidth_H
GPIO.4 = 1 ; Turn LED on.
PIR1.CCP1IF = 0 ; Clear match flag
do until (PIR1.CCP1IF = 1) ; Wait until Timer1 matches pulse end count.
loop
GPIO.4 = 0 ; Turn LED off
The above code works and I can use CCP Compare to create a timed event relative to Timer1. I know that there are other solutions – like Wait 500uS but it is more about the concept. Also the pulse durations need to be accurate and variable.
Now, I’d like to avoid stopping Timer1 – I should be able to use CCP Capture to get a copy of Timer1 registers but need to trigger an edge event on GPIO.2. (The data sheet says the writing to the CCP1 pin can trigger this event - more cryptic references state that alterations to CCP1CON may also do the same - I read this as "might not" also but no statement that it definitely does !)
I tried, this :
CCP1CON = 0b00000100 ; Capture mode, every falling edge
TRISIO.2 = 0 ; GPIO.2 now an output.
GPIO.2 = 0 ; Fake a falling edge.
TRISIO.2 = 1 ; Need it as an input.
CCP1CON = 0b00001010 ; Compare mode.
So I’d expect this to have worked and CPPR1L, CPPR1H should have a copy of Timer1’s registers.
I’ve got lost here but I’d expected to be able to do something like :
CCPR1 = CCPR1 + PulseWidth but the assembler seems to treat CCPR1 as a byte value.
I’ve tried doing :
ww = CCPR1L
ww_H = CCPR1H
ww = ww + PulseWidth
CCPR1L = ww
CCPR1H = ww_H
So there’s one issue and that relates to word mathematics, processing of registers and updates – Timer1 is defined and works as I’d expect but references to CCPR1 don’t.
Can I actually reliably grab a code triggered capture copy of Timer1’s registers ?
At the moment, it does actually work but not reliably. When it is working the pulses are correct in duration and timing … and then there are other pulses that don’t !
I hope the concept is clear – create a CCP Compare event by adding a duration to Timer1 … what am I missing or is there another way ?
Andrew
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Having slept on it and rethought the problem it became obvious that the capture event should be the trigger and not the INT interrupt that I'd used - everything then dropped neatly and more simply into place and even the CCP Compare has been implemented in a more logical way to define the wanted pulse duration. Grabbing the Timer1 registers "on the fly" was no longer needed either.
Life's message - starting from the wrong place all too often leads nowhere ...
Andrew
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Fairly new to the PIC world and part of me keeps looking sideways at using CMOS digital control - and I've got a bag load of 12F683s but I'll look into your suggestion.
I've set myself and others (schools) a challenge to produce the lowest powered yet controlled motor for summer term project - essentially pulse, a coil and control a "spinney magnet thing". Ideally it should be solar powered running on uW, self starting and run 24 / 7.
So need to determine, ideal parameters for the pulse - so from the magnet rotor detection, need to be able to control delay interval prior to pulse, pulse duration and keep an eye on overall RPM. Ideally, need to get the PIC to sleep a lot and the PIC needs to run at low clock speed too. It's a good challenge as the actual clock / timer intervals become comparable to the pulse width, as does the instruction code. A good intro to efficient and effective code.
I've played with this idea for many years, actually ever since my own school physics lessons ! The nearest project that I've found is here :
Somewhat bizarrely, the creator of this work attended the same college as me and my school physics teacher set us a challenge to create a "novel electric motor" - so 50 years ago, I came up with an identical motor.
So that's the challenge - any takers or thoughts ?
Back quite few years ago I was looking at the claims of "overunity" for was was called the Bedini Motor" invented by John Bedini. Of course overunity is not possible in scope of known physics, so I decide to replicate the motor and analyze the claims. The motor ran well but of course there was no "overunity" as claimed. It was a somewhat novel approach for a simple motor but the torque was so low that it could too very little work.
That lead me to make a motor using hand wound bifilar coils hot glued to a board and with magnets hot glued into a skate board wheel. It worked well using a PIC to control the pulses to the coil. If I recall. correctly it spun the wheel at about 5,000 RPM using about 1/4 of a watt of power but with only the mass of the wheel and the friction of the bearings as a load. But again very little torque. Lots of fun though.
Last edit: William Roth 2021-03-19
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Sounds like it would work well for a radio controlled or battery operated slot car set.
You are on to something there Bill not all motors need torque to provide the desired effect.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Hi,
PIC 12F683
I’m using Timer1 as the main control for measurement and velocity control of a motor. I want to create pulses of variable duration. One option seemed to be to simply use Timer1 to control these pulses – add the wanted “off” time to the current Timer1 registers and create an event using CCP Compare.
The simple option is to stop Timer1 and calculate the “off” time, restart Timer1 and set up a CCP Compare event.
CCP1CON = 0b00001010 ; CCP Compare mode, generate software interrupt on Timer1 match.
…
…
T1CON.TMR1ON = 0 ; Stop Timer1 or we might capture rollover error.
PulseWidth = c500uS + Timer1 ; Flash LED for 500uS - so add it to Timer1 to get off count.
T1CON.TMR1ON = 1 ; Start Timer1.
CCPR1L = PulseWidth ; Set wanted CCP register Timer1 match count.
CCPR1H = PulseWidth_H
GPIO.4 = 1 ; Turn LED on.
PIR1.CCP1IF = 0 ; Clear match flag
do until (PIR1.CCP1IF = 1) ; Wait until Timer1 matches pulse end count.
loop
GPIO.4 = 0 ; Turn LED off
The above code works and I can use CCP Compare to create a timed event relative to Timer1. I know that there are other solutions – like Wait 500uS but it is more about the concept. Also the pulse durations need to be accurate and variable.
Now, I’d like to avoid stopping Timer1 – I should be able to use CCP Capture to get a copy of Timer1 registers but need to trigger an edge event on GPIO.2. (The data sheet says the writing to the CCP1 pin can trigger this event - more cryptic references state that alterations to CCP1CON may also do the same - I read this as "might not" also but no statement that it definitely does !)
I tried, this :
CCP1CON = 0b00000100 ; Capture mode, every falling edge
TRISIO.2 = 0 ; GPIO.2 now an output.
GPIO.2 = 0 ; Fake a falling edge.
TRISIO.2 = 1 ; Need it as an input.
CCP1CON = 0b00001010 ; Compare mode.
So I’d expect this to have worked and CPPR1L, CPPR1H should have a copy of Timer1’s registers.
I’ve got lost here but I’d expected to be able to do something like :
CCPR1 = CCPR1 + PulseWidth but the assembler seems to treat CCPR1 as a byte value.
I’ve tried doing :
ww = CCPR1L
ww_H = CCPR1H
ww = ww + PulseWidth
CCPR1L = ww
CCPR1H = ww_H
So there’s one issue and that relates to word mathematics, processing of registers and updates – Timer1 is defined and works as I’d expect but references to CCPR1 don’t.
Can I actually reliably grab a code triggered capture copy of Timer1’s registers ?
At the moment, it does actually work but not reliably. When it is working the pulses are correct in duration and timing … and then there are other pulses that don’t !
I hope the concept is clear – create a CCP Compare event by adding a duration to Timer1 … what am I missing or is there another way ?
Andrew
Having slept on it and rethought the problem it became obvious that the capture event should be the trigger and not the INT interrupt that I'd used - everything then dropped neatly and more simply into place and even the CCP Compare has been implemented in a more logical way to define the wanted pulse duration. Grabbing the Timer1 registers "on the fly" was no longer needed either.
Life's message - starting from the wrong place all too often leads nowhere ...
Andrew
Good work.
Did you know that many more modern PIC's have a signal measurement timer (SMT) peripheral that simplifies measuring nearly all aspects of a signal?
This includes the PIC12F1612, 16F18424/25/26. All cost less than $1
SMT Techical Brief
Last edit: William Roth 2021-03-19
Thanks William,
Fairly new to the PIC world and part of me keeps looking sideways at using CMOS digital control - and I've got a bag load of 12F683s but I'll look into your suggestion.
I've set myself and others (schools) a challenge to produce the lowest powered yet controlled motor for summer term project - essentially pulse, a coil and control a "spinney magnet thing". Ideally it should be solar powered running on uW, self starting and run 24 / 7.
So need to determine, ideal parameters for the pulse - so from the magnet rotor detection, need to be able to control delay interval prior to pulse, pulse duration and keep an eye on overall RPM. Ideally, need to get the PIC to sleep a lot and the PIC needs to run at low clock speed too. It's a good challenge as the actual clock / timer intervals become comparable to the pulse width, as does the instruction code. A good intro to efficient and effective code.
I've played with this idea for many years, actually ever since my own school physics lessons ! The nearest project that I've found is here :
https://www.instructables.com/Electronic-Motor-Control-Using-Optical-Pick-Up/
Somewhat bizarrely, the creator of this work attended the same college as me and my school physics teacher set us a challenge to create a "novel electric motor" - so 50 years ago, I came up with an identical motor.
So that's the challenge - any takers or thoughts ?
Here's a bit of my work from a few years ago :
https://youtu.be/7t6apY227yw
Cheers,
Andrew
Back quite few years ago I was looking at the claims of "overunity" for was was called the Bedini Motor" invented by John Bedini. Of course overunity is not possible in scope of known physics, so I decide to replicate the motor and analyze the claims. The motor ran well but of course there was no "overunity" as claimed. It was a somewhat novel approach for a simple motor but the torque was so low that it could too very little work.
That lead me to make a motor using hand wound bifilar coils hot glued to a board and with magnets hot glued into a skate board wheel. It worked well using a PIC to control the pulses to the coil. If I recall. correctly it spun the wheel at about 5,000 RPM using about 1/4 of a watt of power but with only the mass of the wheel and the friction of the bearings as a load. But again very little torque. Lots of fun though.
Last edit: William Roth 2021-03-19
Sounds like it would work well for a radio controlled or battery operated slot car set.
You are on to something there Bill not all motors need torque to provide the desired effect.