AT89C51ED2 PWM-Duty per Taste verändern

OP #1977375
Lesenswert?

Hallo Gemeinde,

kleines Problem: ich möchte den Tastgrad einer Hard-PWM an Pin 1.3 
verändern.
Der erste Programmentwurf funktioniert erstmal auch grundsätzlich. Taste 
"tief" macht dunkel und Taste "hoch" macht hell. Wenn ich am Ende des 
Arrays angekommen bin z.b. ganz dunkel (bei mir wert 255) springt wird 
die LED bei einem weiteren Tastendruck auf "tief" wieder auf einen sehr 
hellen Wert obwohl die LED bei weiteren Tastendrücken auf "tief" dunkel 
bleiben soll. Beim hellsten Wert das gleiche Verhalten. Springt bei 
weiteren Tastendrücken zw. hell und dunkel.
Tastenentprellen habe ich erstmal nicht implementiert und spielt in dem 
Fall auch keine Rolle.

Eine Weitere Frage betrifft die PWM selbst. Kann ich die Frequenz 
veringern ohne einen Timer oder ext. Signal zu verwenden? Habe jetzt 
PCA-Clock/6. Sollten ca. 2 MHz sein. Ich möchte ca. 200 bis 600 Hz 
haben.


MfG Matze
1
#include <at89c51xd2.h>
2

3

4
sbit pulsweite_tief=P2^2; // Drucktasten für Pulsweiten
5
sbit pulsweite_hoch=P2^5;
6

7
sbit Pin10=P1^0;    // kann raus beim richtigen programm
8
sbit Pin11=P1^1;
9
sbit Pin12=P1^2;
10
sbit Pin14=P1^4;
11
sbit Pin15=P1^5;
12
sbit Pin16=P1^6;
13
sbit Pin17=P1^7;
14
/*--------------------------------------------------------------------
15
Globale Variablen
16
----------------------------------------------------------------------*/
17
unsigned char pwm_array[32] = {255, 215, 181, 152, 128, 108, 91, 76, 64,
18
                               54, 45, 38, 32, 27, 23, 19, 16, 13, 11,
19
                               10, 8, 7, 6, 5, 4, 3, 3, 2, 2, 2, 1, 0};
20
/* invertierte PWM-Tabelle da LED bei 255 = dunkel und bei 0 = hell */
21

22
/*-----------------------------------------------------------------------
23
Zusatzfunktionen
24
------------------------------------------------------------------------*/
25

26
/*void wait(void)
27
{
28
unsigned int x;
29
for(x=1;x<=20000;x++); //Delay
30
}*/
31

32
void PWM_INI(void)
33
{ CMOD=0x00; // Interner Clock fpca/6 -- kein Interruptbetrieb
34
  CCON=0x00; // PCA steht still
35
  CCAPM0=0x42; // ECOM0-Bit und PWM0-Bit werden gesetzt
36
}
37

38
/*--------------------------------------------------------------------
39
Hauptprogramm
40
----------------------------------------------------------------------*/
41
void main(void)
42

43
{  
44
  static char old_level_t1=0;
45
  char new_level_t1;
46
  static char old_level_t2=0;
47
  char new_level_t2;
48
  
49
  char i=0;  // Arrayzaehler
50

51
  Pin10=0;   // andere Ports aus; kann raus beim richtigen programm
52
  Pin11=0;
53
  Pin12=0;
54
  Pin14=0;
55
  Pin15=0;
56
  Pin16=0;
57
  Pin17=0;
58
  
59
  PWM_INI();  // PWM-Initialisierung
60
  CR=1;    // PWM starten
61
  CCAP0H=255;  // Startwert der PWM
62
  
63
  while(1)        // Endlosschleife
64
  {   
65
    new_level_t1 = (pulsweite_hoch != 0);    //Taste 1 Flankenerkennung
66
    if(!old_level_t1 && new_level_t1)
67
      {
68
        if(i <= 31)    // steigende flanke erkannt 
69
        {i++;}        // gehe ein Feld weiter
70
        else
71
        {i=31;}
72
        CCAP0H=pwm_array[i];  // schreibe aktuelle stelle in Register Tastgrad      
73
      }
74
      old_level_t1 = new_level_t1;
75

76
    new_level_t2 = (pulsweite_tief != 0);  //Taste 2 Flankenerkennung
77
    if(!old_level_t2 && new_level_t2)
78
      {
79
        if(i >= 0)  // steigende flanke erkannt 
80
        {i--;}  // gehe ein Feld zurueck
81
        else
82
        {i=0;}
83
        CCAP0H=pwm_array[i];  // schreibe aktuelle stelle in Register Tastgrad
84
      }
85
      old_level_t2 = new_level_t2;
86
  }
87
}
Gast #1977422
Lesenswert?

>        if(i <= 31)    // steigende flanke erkannt
>        {i++;}        // gehe ein Feld weiter

Dein Array hat nur die Indizes 0..31.
Das letzte i++ kann aber auf 32 kommen.
Peng Arrayindex falsch.

Hier das selbe in umgekehrter Richtung:

>        if(i >= 0)  // steigende flanke erkannt
>        {i--;}  // gehe ein Feld zurueck

i kann kleiner Null werden. Peng;)

Mach die beiden = weg.
Also

  if(i < 31)    // steigende flanke erkannt
  if(i > 0)  // steigende flanke erkannt

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren