Pwm pic16f690

C, C++, Pascal, Assembly, Raspberry, Java, Matlab, Python, BASIC, SQL, PHP, etc.
wiktorahlander
Inlägg: 22
Blev medlem: 1 mars 2012, 20:19:36

Pwm pic16f690

Inlägg av wiktorahlander »

Har försökt söka mig till ett svar men misslyckats.
Kan jag på en 16f690 ha två olika pwm utgångar som inte påverkar varandra?

Ex:
LED1 dimmad
knapptryck > LED1full
Knapptryck > LED1 dimmad

Och sedan göra samma sak med en till LED oberoende av den andra?

Själva pwm styrningen har jag löst, men den gör samma sak på alla portar?
Användarvisningsbild
Magnus_K
EF Sponsor
Inlägg: 5854
Blev medlem: 4 januari 2010, 17:53:25
Ort: Skogen mellan Uppsala-Gävle

Re: Pwm pic16f690

Inlägg av Magnus_K »

Har du chans att posta koden?

EDIT: Låter som om du styr just alla portar istället för en specifik. Typ PORTA istället för PORTA.RA0...
wiktorahlander
Inlägg: 22
Blev medlem: 1 mars 2012, 20:19:36

Re: Pwm pic16f690

Inlägg av wiktorahlander »

Ja kan fixa det imorgon!
sodjan
EF Sponsor
Inlägg: 43241
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Re: Pwm pic16f690

Inlägg av sodjan »

> Kan jag på en 16f690 ha två olika pwm utgångar som inte påverkar varandra?

Du kan ha så många som du har lediga I/O pinnar.
D.v.s utan några andra förutsättning kända.

> Själva pwm styrningen har jag löst...

Hur då?
SW eller HW PWM?
wiktorahlander
Inlägg: 22
Blev medlem: 1 mars 2012, 20:19:36

Re: Pwm pic16f690

Inlägg av wiktorahlander »

Här kommer koden på det jag gjort!

Kod: Markera allt

#include <pic.h>

__CONFIG (FOSC_INTRCCLK&WDTE_OFF&MCLRE_OFF&CP_OFF);

// Using Internal Clock of 8 MHz
#define FOSC 8000000L

// Delay Function
#define	_delay_us(x) { unsigned char us; \
		       us = (x)/(12000000/FOSC)|1; \
		       while(--us != 0) continue; }
void _delay_ms(unsigned int ms)
{
  unsigned char i;
  if (ms == 0) return;
  do {
    i = 4;
    do {
      _delay_us(164);
    } while(--i);
  } while(--ms);
}
void main(void)
{
  unsigned int ipwm;
  unsigned char state;
  OSCCON=0x70;         // Select 8 MHz internal clock
  TRISC = 0x00;        // Set All on PORTC as Output
  ANSEL = 0x00;        // Set PORT AN0 to AN7 digital I/O
  ANSELH = 0x00;       // Set PORT AN8 to AN11 as Digital I/O
  PORTC = 0x00;        // Turn Off all PORTC
  /* Init PWM for Single Output */
  CCP1CON=0b00001100;  // Single PWM mode; P1A, P1C active-high; P1B, P1D active-high
  CCPR1L=0;            // Start with zero Duty Cycle
  T2CON=0b00000101;    // Postscale: 1:1, Timer2=On, Prescale = 1:4
  PR2=0x65;            // Frequency: 4.90 kHz
  TMR2=0;              // Start with zero Counter

    // Enable Pulse Steering on P1C (RC3)
  state=0;
  ipwm=13;
  PSTRCON=0b00001111;
  CCPR1L=ipwm;
  for(;;) {
      PSTRCON=0b00001111;
      if(RA1==1 && ipwm < 14)
      {
        PSTRCON=0b00001100;
        while (ipwm < 255) {
          CCPR1L=++ipwm;
          _delay_ms(1);
        }
      }
    if(RA1==1 && ipwm==255)
    {
    PSTRCON=0b00001100;
    while (ipwm > 12) {
      CCPR1L=--ipwm;
      _delay_ms(1);     
    }
    }




      if(RA3==1 && ipwm < 14)
      {
        PSTRCON=0b00000011;
        while (ipwm < 255) {
          CCPR1L=++ipwm;
          _delay_ms(1);
        }
      }
    if(RA3==1 && ipwm==255)
    {
    PSTRCON=0b00000011;
    while (ipwm > 12) {
      CCPR1L=--ipwm;
      _delay_ms(1);
    }
    }



  }
}
sodjan
EF Sponsor
Inlägg: 43241
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Re: Pwm pic16f690

Inlägg av sodjan »

OK. Så där ska du nog inte göra. :-)

Vad har du för krav på själva PWM'en?
Grundfrekvens (d.v.s blinkfrekvens på lysdioderna)?
Antal steg för ljusstyrkan?
Antal lysdioder?

Om vi antar 100 Hz och 16 steg.

Det betyder att man behöver göra något varje 625'e us.
Med en intern oscillator på 8Mhz ger det ca 1.200 instruktioner/"varv".
Det borde räcka till. Vill du ha 32 steg så blir det 600 instruktioner
vilket fortfarande bör vara OK för 8 LEDs. Sedan så skulle jag
ta en modernare PIC som kan köras snabbare.

Ett timerinterrupt med ungefär detta intervall.
Vid varje interrupt räknas en räknare ner för varje lysdiod.
Om den räknaren blir 0 så släcks lysdioden.
Om det har gått 16 (eller 32) varv så tänds alla lysdioder
igen alla och räknare återställs till respektive "ljusstyrka".

Ovanstående görs alltså i timerinterruptet.

Sedan kan du ha valfri övrig kod som har hand om att
ställa de olika ljusstyrkorna. Det kan vara beräknat, styrt
av någon tabell, kommandon via USART eller något liknande.
wiktorahlander
Inlägg: 22
Blev medlem: 1 mars 2012, 20:19:36

Re: Pwm pic16f690

Inlägg av wiktorahlander »

Okej ett exempel på hur jag kan göra istället?
Har bara denna pic som en test just nu.
sodjan
EF Sponsor
Inlägg: 43241
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Re: Pwm pic16f690

Inlägg av sodjan »

Ett exempel har du fått, koden får du fixa själv.
Jag ser inte heller några svar på frågorna...
wiktorahlander
Inlägg: 22
Blev medlem: 1 mars 2012, 20:19:36

Re: Pwm pic16f690

Inlägg av wiktorahlander »

Vad har du för krav på själva PWM'en?
inga större krav, mer än att jag ska kunna ha olika styrkor (signal) på olika pinnar.
Grundfrekvens (d.v.s blinkfrekvens på lysdioderna)?
Den ska bara minska i ljusstyrka blinkningarna ska inte synas.
Antal steg för ljusstyrkan?
10 steg kanske är lagomt.
Antal lysdioder?
blir nog 5-6 st skulle jag tro.


Skulle underlätta med ett kod exempel. förstår det bättre än din förklaring. Självklart handlar det inte om att du ska skriva allt åt mig!!
Niklas-k
Inlägg: 354
Blev medlem: 10 mars 2004, 15:59:21
Ort: Katrineholm

Re: Pwm pic16f690

Inlägg av Niklas-k »

Ungefär så här kan du göra. Du får sätta upp en "free running timer".

Kod: Markera allt

Var

PWM_Tot_step=10
LED1_PWM=5 !50% Duty
LED2_PWM=1 !10% Duty
PWM_step=0






Timer begin


IF LED1_PWM>=PWM_step LED1_ON ELSE LED1_OFF
IF LED2_PWM>=PWM_step LED2_ON ELSE LED2_OFF
......
......

PWM_step=PWM_step+1

IF PWM_step>PWM_Tot_step Then PWM_step=0

Timer End
Skriv svar