PC SOFT

FORUMS PROFESSIONNELS
WINDEVWEBDEV et WINDEV Mobile

Accueil → WINDEV 25 → Problème de communication avec MCF Eltrade via port série
Problème de communication avec MCF Eltrade via port série
Débuté par Lionel Gildas KANHON, 14 juin 2020 11:43 - 14 réponses
Membre enregistré
4 messages
Posté le 14 juin 2020 - 11:43
Bonjour,

J'ai un problème de communication via le port série avec un équipement de facturation Eltrade MCF. Le PC envoi une commande à l'équipement en respectant le format suivant :






où SOH=début de la commande; LEN=Nombre total d'octets de la position 2 "LEN" à6 "AMB" (inclus), plus décalage fixe de 20h; SEQ=N° de série de la commande; CMD=code de la commande; Data=Donnée selon la commande (0 s'il n'y a pas de données); AMB=Délimiteur; BCC=somme des octets de données de la position 2 à la position 6; ETX=Fin de commande

J'essaye de lancer la commande C1h pour afficher le status de la machine. Cette commande n'a pas de données.

Voici le code dans le bouton

// Fermetture du port
sFerme(SAI_N_de_Port)

// SOH=0x01; LEN=0x39; SEQ=0x35; CMD=0xC1; DATA=0x30; AMB=0x2C (|); BCC=0x39; ETX=0x03

sChaîneAEcrire est une chaîne =Caract(0x01)+Caract(0x39)+Caract(0x35)+Caract(0xC1)+Caract(0x30)+Caract(0x2C)+Caract(0x39)+Caract(0x03)


// Ouverture du port en mode événement
SI sOuvre(SAI_N_de_Port, 12288, 12288, sTimeoutDéfaut, Vrai)=Vrai ALORS
Trace(" Ouverture du port "+SAI_N_de_Port+" est Ok ")
// Fixer les paramètre du port
SI sFixeParamètre(SAI_N_de_Port, 115200, 0, 8, 0)=Vrai ALORS
Trace(" Paramétrage du port "+SAI_N_de_Port+" est ok")
// Ecriture sur le port
nBcaract est un entier=0
nBcaract=sEcrit(SAI_N_de_Port,sChaîneAEcrire)
SI nBcaract>0 ALORS
Trace(" Des données ont été écris sur le port COM "+SAI_N_de_Port+" "+nBcaract+" caractères écrits")
SINON
Trace(" Une erreur est survenue lors de l'écriture sur le port "+SAI_N_de_Port)
FIN
// Appliquer un délai de temporisation
Multitâche(-100)

// Timer(LectureCOM,1000,1)
LectureCOM()
SINON
Trace(" Paramétrage du port "+SAI_N_de_Port+" a échoué")
FIN
SINON
Trace(" Erreur lors de l'ouverture du port "+SAI_N_de_Port)
FIN

Procédure LectureCOM()

sMessageLu est une chaîne
nNbCar est un entier

nNbCar=sDansFileEntrée(SAI_N_de_Port)

Trace(nNbCar)

sMessageLu+=sLit(SAI_N_de_Port,sDansFileEntrée(SAI_N_de_Port))

Trace(sMessageLu)



Tout semble correct quand j'exécute le code mais j'ai pas le résultat (je reçois le signe ). Je ne sais pas si le problème se situe au niveau du code Hexa.

J'ai vraiment besoin de votre aide.

Merci pour le support,
Membre enregistré
762 messages
Popularité : +3 (5 votes)
Posté le 14 juin 2020 - 14:34
bonjour
Après les instructions :
SI sOuvre(SAI_N_de_Port, 12288, 12288, sTimeoutDéfaut, Vrai)=Vrai ALORS
Trace(" Ouverture du port "+SAI_N_de_Port+" est Ok ")
// Fixer les paramètre du port
SI sFixeParamètre(SAI_N_de_Port, 115200, 0, 8, 0)=Vrai ALORS
Trace(" Paramétrage du port "+SAI_N_de_Port+" est ok")


il manque l'instruction sEvenement() pour gerer la reception et votre timer ne sert plus à rien

--
« L'erreur ne devient pas vérité parce qu'elle se propage et se multiplie ; la vérité ne devient pas erreur parce que nul ne la voit. » Gandhi
Membre enregistré
4 messages
Posté le 14 juin 2020 - 23:14
Bonsoir Philipe,

J'ai ajouté le la gestion des événements avec sEvenement() mais j'ai toujours le même retour (un signe crochet). Je crois que le problème se trouve au niveau de ma conversion du code Hexadécimal. Vous avez eu à débattre d'un problème similaire à cette adresse https://forum.pcsoft.fr/fr-FR/pcsoft.fr.windev/237479-utilisation-port-serie/read.awp.
Avez -vous des acquis du côté conversion Hexadécimal? Merci
Membre enregistré
762 messages
Popularité : +3 (5 votes)
Posté le 15 juin 2020 - 12:30
bonjour
pouriez vous montrer votre code ?

--
« L'erreur ne devient pas vérité parce qu'elle se propage et se multiplie ; la vérité ne devient pas erreur parce que nul ne la voit. » Gandhi
Membre enregistré
4 messages
Posté le 12 juillet 2020 - 22:42
Bonjour Philipe,
Excuse moi pour le retard de ma réponse. J'ai créé une procédure MakeTrame pour générer la trame à envoyer sur le port et une autre LectureCOM pour lire la réponse de l'équipement.

PROCEDURE MakeTrame(cSEQ est un entier sans signe sur 1 octet, cCMD est un entier sans signe sur 1 octet, sData est une chaîne)//:chaîne
//PROCEDURE MakeTrame(cSEQ est une chaîne, cCMD est un entier sans signe sur 1 octet, sData est une chaîne)//:chaîne
cSOH est un entier sans signe sur 1 octet = 0x01
cLEN est un entier sans signe sur 1 octet = 0x24
cAMB est un entier sans signe sur 1 octet = 0x05
iBCC est un entier sans signe sur 2 octets = 0x00
cETX est un entier sans signe sur 1 octet = 0x03
cBCC1, cBCC2, cBCC3, cBCC4 est un entier sans signe sur 1 octet
SousTrame, sTrame est une chaîne

cLEN += Taille(sData)
SousTrame = Caract(cLEN) + Caract(cSEQ) + Caract(cCMD) + sData + Caract(cAMB)

// Calcul du BCC
i est un entier
FOR i=1 _TO_ Taille(SousTrame)
iBCC += Asc(SousTrame[[i]])
END

// BCC en 4 caractères affichables
cBCC1 = bitDécaleDroite(iBCC & 0xf000, 12) + 0x30
cBCC2 = bitDécaleDroite(iBCC & 0x0f00, 08) + 0x30
cBCC3 = bitDécaleDroite(iBCC & 0x00f0, 04) + 0x30
cBCC4 = (iBCC & 0x000f) + 0x30

sTrame = Caract(cSOH) + SousTrame + Caract(cBCC1) + Caract(cBCC2) + Caract(cBCC3) + Caract(cBCC4) + Caract(cETX)
gsTra=sTrame

RENVOYER sTrame


sMessageLu est une chaîne
nNbCar est un entier

nNbCar=sDansFileEntrée(1)

Trace(nNbCar)

sMessageLu+=sLit(1,sDansFileEntrée(1))

SAI_Retour+=" "+RC+sMessageLu


Le code du bouton de la commande C1h qui donne les information sur la machine :

//MakeTrame(seq,0xC1,0x30)
MakeTrame(0x40,0xC1,0x30)

sFerme(SAI_NumPort)
sChaîneAEcrire est une chaîne =gsTra

// Ouverture du port en mode événement
SI sOuvre(SAI_NumPort, SAI_TailleBuffEntree, SAI_TailleBufferSortie, sTimeoutDéfaut, bGesEve)=Vrai ALORS
sEvénement(SAI_NumPort,sEveCaractèreReçu,LectureCOMC1)
SI sFixeParamètre(SAI_NumPort, SAI_Vitesse_de_transmission, nParite, SAI_NombreBitData, SAI_NombreBitArret)=Vrai ALORS
nBcaract est un entier=0
nBcaract=sEcrit(SAI_NumPort,sChaîneAEcrire)
// Appliquer un délai de temporisation
Multitâche(-100)
SINON
Trace(" Paramétrage du port "+SAI_NumPort+" a échoué")
FIN
SINON
Trace(" Erreur lors de l'ouverture du port "+SAI_NumPort)
FIN

sFerme(SAI_NumPort)


Le problème est que en cliquant sur le bouton la machine réagit bien mais pas toutes les fois. Aussi les autres commande sur la machine ne donnent pas les réponses attendues. Je ne sais pas si c'est à cause du numéro de séquence de la commande.

Merci du support,
Membre enregistré
762 messages
Popularité : +3 (5 votes)
Posté le 13 juillet 2020 - 14:46
bonjour
avez-vous testé en incrémentant cSEQ car il ne faut pas envoyer deux fois de suite la même trame

--
« L'erreur ne devient pas vérité parce qu'elle se propage et se multiplie ; la vérité ne devient pas erreur parce que nul ne la voit. » Gandhi
Posté le 13 juillet 2020 - 16:32
La séquence est comprise entre 20h et FFh donc 32-255; je convertis en hexa le nombre trouvé avant de l'appliquer. Le retour n'est pas tout le temps concluant mais je cherche toujours. Une aide de votre part serait la bienvenue.

Merci du support,
Membre enregistré
775 messages
Popularité : +13 (13 votes)
Posté le 13 juillet 2020 - 17:40
hello,
Lionel, il y a un truc louche dans ton code. Tu fermes la liaison série à la fin. Cela n'est pas bon pour les données qui peuvent arriver. Normalement dans une liaison série on programme et on ouvre le port série au début et on le laisse ouvert tout le temps que l'on peut avoir besoin de lui. On ne le ferme que quand on a finit toutes les opérations. Par exemple à la fermeture de l'application.

--
Ami calmant, J.P
Membre enregistré
762 messages
Popularité : +3 (5 votes)
Posté le 13 juillet 2020 - 21:45
1 bouton juste pour ouvrir et parametrer le port (je vous laisse rajouter les contrôles) mais "normalement" 3 lignes sufisent
sOuvre(SAI_NumPort, 2400, 2400, sTimeoutDéfaut, True)
sFixeParamètre(SAI_NumPort, SAI_Vitesse_de_transmission, nParite, SAI_NombreBitData, SAI_NombreBitArret)
sEvénement(SAI_NumPort, sEveCaractèreReçu, LectureCOMC1)

Une fois que vous aurez cliqué sur ce bouton et si le port de com est bien paramètré alors si le port com reçois des octets et ça quelque soit l'endroit où se trouve le programme, ce dernier sera interompu pour exécuter la procédure LectureCOMC1 (c'est le principe des Interrutions)
C'est donc dans la procédure LectureCOMC1 que le travail de lecture des données doit se faire...

1 bouton juste pour ennvoyer la trame
Ecrit(SAI_NumPort, MakeTrame(0x40, 0xC1, 0x30)) // modifier nSEQ


1 bouton juste pour fermer le port

--
« L'erreur ne devient pas vérité parce qu'elle se propage et se multiplie ; la vérité ne devient pas erreur parce que nul ne la voit. » Gandhi
Membre enregistré
4 messages
Posté le 14 juillet 2020 - 15:02
Bonjour Philippe,

Oui j'ai essayé de corriger comme expliqué en dessus. Mon problème actuellement se trouve au niveau des autres commandes. Normalement la machine est connecté pour envoyer les facture saisi par mon logiciel vers la direction des impôts; donc il y a une suite de commandes à exécuter pour récupérer le code de normalisation à afficher sur la facture.

La commande C1h pour voir le status marche correctement mais le problème se trouve au niveau des autres commande qui prennent des paramètres (donc plus de 0x30). Comment préfixer la donnée en paramètre à la procédure MakeTrame de "0x". Pour être plus explicite j'ai la commande C0 qui doit prendre comme données : "1,Bienvenu,9999900000154,0.00,18.00,0.00,18.00,FV"; apès conversion de cette donnée en hexa et envoyer à la procédure, on a pas le résultat attendu.

Si possible envoie moi ton email, j'enverrai mon programme avec la documentation pour que tu puisses mieux me corriger

Toujours merci pour le support
Membre enregistré
762 messages
Popularité : +3 (5 votes)
Posté le 14 juillet 2020 - 15:23
bonjour
je viens de vous envoyer un mail

--
« L'erreur ne devient pas vérité parce qu'elle se propage et se multiplie ; la vérité ne devient pas erreur parce que nul ne la voit. » Gandhi
Membre enregistré
762 messages
Popularité : +3 (5 votes)
Posté le 14 juillet 2020 - 16:02
bonjour
je comprend pas " apès conversion de cette donnée en hexa"

Il suffit juste de faire :
NumSeq++
if NumSeq < 0x20 then NumSeq = 0x20
sEcrit(ComPort, MakeTrame (NumSeq, 0xC0, "1,Bienvenu,9999900000154,0.00,18.00,0.00,18.00,FV"))
Posté le 21 juillet 2020 - 11:09
Bonjour,

Je reviens avec un autre soucis toujours dans le même cadre. Tout marche bien à présent et je récupère toute les réponses émises par la machine sans faute. Mon soucis actuellement est au niveau des factures avec plusieurs lignes. Quand j'émets une facture avec plusieurs lignes de produits, la machine ne prend en compte que la première ligne malgré que j'ai mis ce traitement dans une boucle. En dessous le code :
gsReponse="" // variable qui contient le retour de la machine
Sequence() // La procédure de mise à jour de la séquence

// La commande 31h qui permet d'ajouter des articles à la facture créée

i est un entier
Pour i=1 a TABLE_SansNom2..occurence sDataAscii=TABLE_SansNom2.COL_Réf_Article[i]+TAB+TABLE_SansNom2.COL_TG[i]+TABLE_SansNom2.COL_Total_TTC[i]
Trace(sDataAscii)
MakeTrame(gnNumSeq,0x31,sDataAscii) // La procédure qui créée la trame à envoyer à la machine
sChaîneAEcrire=gsTra

nBcaract=sEcrit(gnNumPort,sChaîneAEcrire)
// Trace(sChaîneAEcrire)
SI nBcaract=0 ALORS
Trace(" Une erreur est survenue lors de l'écriture sur le port "+gnNumPort+" alloué à la machine MCF ")
gnSaveFacture=0
SINON
Temporisation(100)
gnSaveFacture=1
FIN
Fin


Ai-je fais une erreur dans ce code? Votre aide me sera utile.

Merci,
Posté le 01 août 2020 - 23:37
Il y a toujours une erreur dans ton code.
Le numero de séquence doit varier d'une ligne de facture à une autre.
Dans ton code c'est la même séquence que tu envoies l'Eltrade considère que c'est la même ligne de facture.
Membre enregistré
1 message
Posté le 28 septembre 2020 - 18:13
bonjour mr lionel gildas
Pourras tu partager avec moi la solution pour l'utilisation de la machine électronique de facturation.??
Merci