Question simple pour un quasi noob en C

Bonsoir tous. Je me permet de solliciter votre aide pour résoudre un mien problème.
Voilà, je voudrais réaliser la chose suivante:
-j’ai une carte bricolée qui simule un capteur de poids: en appuyant sur un interrupteur, deux condesateurs se mettent en parallèle et change la fréquence de l’horloge global du système. Ceci représente ce qui sera plus tard une maquette plus mastoque d’un capteur de poids. Quand on appuie, la fréquence est de 6 kHz, sinon elle est de 10kHz.
-j’ai aussi un PIC (un 18F258 pour les curieux) à programmer (d’où la pertinence de mettre le sujet ici), configuré de la sorte
*PortA.0 en sortie (alimentation de mon horloge (un trigger de Schmitt du plus bel effet))
*PortA.1 en entrée, c’est lui qui va prendre la sortie de ma carte horloge.
*Il devait y avoir une LED en PortB pour aider visuellement à comprendre quand ça marcahit, mais en fait, non, défaut de la carte, vais devoir bosser en aveugle.
Et j’ai commencé ce bout de programme:

void main()
{
int i;
int X; // nombre d’incémentations nécessaires à la détection
TRISA.F0 = 0; // initialise le PORTA.0 en sortie
TRISA.F1 = 1; // initialise le PORTA.1 en entrée

 while(1)
 {
        i=0               // toujours exécuté ce qui suit
        while  (PORTA.F1==1)
        {
               i=i+1;
               if (i>=X) //savant calcul de détection basse fréquence
               {
                         PORTB=1;  //allume la diode si la fréquence est basse
                         PORTA.F1=0;
               }
        }
        PORTB=0;
        PORTA.F1=1;
 }

}

//Les fréquences oscillent entre 6kHz (capté), et 10 kHz (non capté).
//si on n’appuie pas, les incrémentations dépassent X, la LED s’allume et c’est mort.
//si on appuie, les incrémentations ne dépassent pas X, et c’est bon
//penser à faire un if pour faire clignoter la LED si appuyage (histoire de voir)

Et je me demandais, si au lieu de calculer X et de passer par un second while(PORTA.F1==1), s’il n’était pas plus pratique et simple d’utiliser une commande du type “delay” et de compter les incrémentations (ou faire un "while(delay())"
Bref un truc facile à comprendre et clair d’utilisation.
Le hic, c’est que je trouve plus comment faire un delay (et si c’est pertinent)

PS: je bosse sous MikroC, si ça peut aider.

Merci de votre aide, Le-Captain loind de l’émulation des cours

Bon j’avoue que je comprends pas tout mais:

_Pourquoi faire un systeme avec 6khz/10khz alors qu’un simple bouton suffirait? Est ce que tu veux dire que la frequence est dependante du poids et que dans ce cas, c’est un range plus que 2 valeurs distinctes?
_Le delay, c’est le MAL. Pendant un delay, ton systeme ne fait rien d’autres qu’attendre et il peut rater des evenements.
_INDENTE TON FUCKING CODE. (la balise code est ton amie)

D’autres donnees?

LoneWolf
Comment faire pour bien expliquer un probleme :stuck_out_tongue:

Alors voila ce que j’ai compris:
t’as un signal périodique sur ton port A, d’une fréquence de 6kHz quand on appuie et de 10kHz quand on appuie pas et de rapport cyclique 1/2.
donc ce que tu fais, c’est que tu mesure la demi période de ton horloge pour savoir quelle est sa fréquence en mesurant le nombre d’occurences qui se suivent pendant lesquelles le signal vaut 1. Si ca dépasse une certaine valeur précalculée, t’es à 6kHz (période plus élevée donc fréquence plus faible). et dans ce cas, tu allume la LED.

si ce que j’ai dit plus haut est correct alors tu ne risque pas de voir la LED s’allumer parce qu’elle va clignoter a une fréquence de 6kHz et avec un rapport cyclique inférieur a 1/2 (elle sera plus “longtemps” éteinte qu’allumée, donc éteinte pour ton oeil).

Je pense que tu devrais rajouter un if pour le moment ou le signal de ton horloge pas de 1 à 0 afin de savoir si tu as dépassé X ou pas

[code]void main() {
int i;
int X; // nombre d’incémentations nécessaires à la détection
TRISA.F0 = 0; // initialise le PORTA.0 en sortie
TRISA.F1 = 1; // initialise le PORTA.1 en entrée

while(1) {
i=0 // toujours exécuté ce qui suit
while (PORTA.F1==1)
i=i+1;
if (i > X)
PORTB=1;
else
PORTB=0;
while(!PORTA.F1);
}
}[/code]

P.S. : ca fait quoi, les PORTA.F1=0 ou 1 ???parce que là, je comprends pas trop. Il est pas en entrée, le port a ???

Je me rends compte que j’étais un peu abstrait.
En gros, pour les besoins d’un projets, j’ai besoin de réaliser une « plateforme » circulaire qui détecterai la présence d’une personne dessus. Je ne peux pas utiliser de système à diodes/photodiodes ou autres pour certaines raisons. Donc je me tourne vers un systême de condo, explication:
-ma plateforme est composée de deux plaque de tôle circulaire de 60cm de diamètre, et séparée par quelques feuilles de papier, le tout faisant un beau sandwich. Le système est relié à un trigger pour avoir une horloge variable (seul moyen que j’ai trouvé pour avoir une différence avec/sans personne et pour peu cher)
-quand personne ne marche sur la plateforme, j’ai 10 kHz en sorite d’horlgoe. S’il y quelqu’un j’ai 6kHz

A savoir que ce n’est que le début du problème, car quand quelqu’un s emet sur la plateforme, ça doit activer l’avancée d’automates, enfin bref, un beau bordel en perspetive.

Lonewolf:
Bien j’y penserai :stuck_out_tongue:

Molyss:
PORTA.F1=0 ou 1, respectivement l’entrée 1 du port A mise en sortie ou en entrée
Le rapport cyclique, c’est un peu comme il veut, ça varie entre 1/3 et 2/3. Normalement, y’a pas de problèmes, car ça détecte les fronts montants.

while(!PORTA.F1);

Qu’est-ce que veut dire le ! avant la variable? L’inverse, comme /A est à A?

Merci pour ces commentaires.

Ouaip, exactement.

Sinon, est-ce que c’est normal que X n’ait pas de valeur? Et d’après ce que je comprend, X devrait être une constante.

Autre question, tu fais où exactement la mesure? J’ai pas bien compris.

while (!porta.f1); c’est pareil que while (porta.fi == 0); . ca ne fait qu’attendre le prochain 1 sur ton entrée.
Par contre, je ne comprends tj pas pourquoi tu fais passer portA un coup en entrée et un coup en sortie… Les bus bidirectionnels, faut y faire gaffe, c’est un coup a faire de zoli signaux de fumée.
Par contre, si tu détecte que les fronts montants, mon code ne marche plus (et le tien non plus, a priori), et en plus, ca fait tout sauf faciliter les choses… a ce moment, il faudrait que t’ai une horloge beaucoup plus lente a coté qui te serve d’étalon pour comparer les fréquence.

Très exactement, c’ets une constante, que je n’ai pas encore calculée, mais ça devrait pas tarder (faut dire aussi que je connais pas le temps d’exécution de ce qu’il y a dns ma boucle while).

La mesure?
Du poids? C’est en fait quand la fréquence change de 10kHZ à 6kHz, en sortie de mon montage d’horloge, qui arrive en PORTA.1.
J’espère avoir pu répondre à ta question

Ouais alors, le X qui compte le nombre de boucle, c’est aussi mal que delay, parce que ca sera JAMAIS constant.
En fait, je vois pas de solution sans une horloge etalon qui genererait une interruption a chaque front montant (le pc fonctionne comme ca).

Autre chose, je pige pas pourquoi ton detecteur de personne n’est pas un bete bouton ON/OFF, ca parait plus simple non?

LoneWolf
Pourquoi faire simple quand on peut faire complique :stuck_out_tongue:

Bon, le X, c’ets une valeur que j’attriburai, quand je l’aurais calculé, donc il sera constant.
Ensuite pour le capteur, c’ets ainsi et pas autrement, j’explique: c’est pour un projet d’arts moderne, nous avons une pièce carrée de facilement 10 mètres de côté. En son centre se tient une plateforme circulaire d’environ 60 cm de diamètre. Lorsque quelqu’un se place dessus, quatre automates (que je programmerai après) fonce vers le centre, via un astucieux système de balises DEL IR. Il y a des contraintes graphiques faisant que la plate forme doit être la moins haute possible. Pour des raisons d’uniformisation esthétique, on couvrira le tout avec un tapis (ou un truc équivalent). Ah, et il faut que le système global (capteur, balise, automate) soit un minimum autonome une fois installé.
Donc pour moi, et l’interessée, le choix du “pèse personne” s’impose.

Et j’oubliais, on a aussi de contraintes budgétaires, donc on fait avec ce qu’on a ^^!

C’est pas que j’ai quelque chose contre le c ou que je sois un faux geek ( :stuck_out_tongue: ), mais pour ton capteur il doit y avoir plus simple. Ca n’existe pas un détecteur de poids qui te délivre un « 0 » si y’a personne et un « 1 » si y’a quelqu’un? Le genre petit interrupteur qui se referme quand on vient marcher dessus.
Et je pense qu’au niveau coût, il doit en exister des pas trop chers, vu que technologiquement ça ne va pas chercher très loin… En plus tu n’auras pas besoin d’un microcontrôlleur pour ta détection. Maintenant, je dis ça sans être marchant de capteurs, mais un coup de fil ou deux à des boîtes spécialisées et tu seras fixé.

Non, ce que LoneWolf t’expliquait c’est que d’utiliser une boucle pour faire un délais c’est vraiment pas propre.
Parce que le temps que va réellement durer le délai ne sera jamais constant. Ca dépendra de plein de choses.

Maintenant faut voir tes contraintes au niveau timing. Si tu dois être super précis, il faudra utiliser un clock, une horloge étalon, comme l’explique LoneWolf. Mais si tes contraintes de timing ne sont pas super importantes, tu devrais pouvoir utiliser la fonction Delay, qui ira très bien, même si elle est loin d’être précise.

Mais, je suis assez d’avis avec les autres, je vois pas bien l’utilité d’un tel système compliqué alors qu’un simple switch suffisemment plat pourrait très bien convenir.

Yop, merci pour les réponses, et oui il y a plus simple. Après un petit brainstorming ave cmon géntieur, j’ai opté pour un système de filtre passe haut suivi d’une diode zener, qui me donnera un “zéro” ou un “un” selon la fréquence, voir le super shcèma de folie ^^:
Attention le mirettes:
juste là
Donc ceci devrait me dispenser d’écrire la moindre ligne de programme pour la conversion fréquence/bits.

VOilà, j’ai trouvé comment faire, même si j’utilise un Delay ^^

void main (void) { TRISB=0x80; //initialisation du PORT B7 à 1 int B; ADCON1=0x07; //dispose le PORT A en numérique (pour plus tard) while (1) { while (PORTB.F7 == 0) //expliquer plus bas {} while (PORTB.F7 == 1) {} while (PORTB.F7 == 0) {B++;} if (B>=24) PORTB.F=1; else PORTB.F=0; B=0; Delay_ms (100); } }

Les trois while me permettent d’être sûr de compter les coups d’horloges pendant le temps bas, préalablement vérifié à l’oscilloscope. Je connais donc le nombre de coups qu’il y a quand on appuie, et quand on n’appuie pas, et je prends une valeur intermédiaire (ici 24) .

Ensuite pour la réalisation du condo géant, j’ai pris deux plaques de tôle circulaire (diamètre de 60 cm), superposées et séparées par deux épaisseurs d’essui-tout bon marché (genre ceux pour s’essuyer les mains dans les aires d’autoroute ou les écoles. Et ça marche nickel!

bah dis-donc, t’as de la chance d’avoir un delay… moi, quand je code sur mon CP, les attentes c’est avec un for(i=0, i<100000, i++);
remarque, c’est peut-être la même chose qui est codée dans ton delay :stuck_out_tongue:

un délais en programmation embarquée ( fin sur pic quoi ) c’est pas tres grave si ? toute façon il gere pas le multi threading, donc il peut pas attendre et revenir apres pour voir si c’est bon … si ?
edit : pincettes