Faire un graphique à partir d'un TClientDataSet

Signaler
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009
-
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
-
Bonjour !
Voila, dans ma base j'ai des échantillons avec une date de création, je voudrais afficher un graphique qui représente le nombre d'échantillon créés par mois.
Ma requête pour récupérer le nombre d'échantillon créé par mois est faite. J'ai donc mes variables de type Integer :

nbrEchantJanv -> le nombre d'échantillon créés au mois de janvier
nbrEchantFev -> le nombre d'échantillon créés au mois de Février
nbrEchantMars-> le nombre d'échantillon créés au mois de mars
nbrEchantAvril -> le nombre d'échantillon créés au mois d'avril

J'ai mon TClientDataSet qui se nomme NbrEchantParMCDS, mon data source NbrEchantParM, alors j'ai aussi une grille pour tester si tout marche qui se nomme DBGrid4.

Dans mon TClientDataSet, j'ai créé trois champs : NbEchant de type Integer, Mois de type Integer (qui est mon mois en nombre) et NomMois de type string qui est le nom du mois. J'ai fais créer un ensemble de données.

Alors pour ajouter des données a mon TClientData Set voila ce que j'ai fait :

    NbrEchantParMCDS.EmptyDataSet;
    NbrEchantParMCDS.DisableControls;
    try
      NbrEchantParM.DataSet.Append;
      NbrEchantParM.DataSet.FieldByName('NbEchant').AsInteger :=nbrEchantJanv;
      NbrEchantParM.DataSet.FieldByName('Mois').AsInteger :=1;
      NbrEchantParM.DataSet.FieldByName('NomMois').AsString :='Janvier';
      NbrEchantParM.DataSet.Post;
      NbrEchantParM.DataSet.Append;
      NbrEchantParM.DataSet.FieldByName('NbEchant').AsInteger :=nbrEchantFev;
      NbrEchantParM.DataSet.FieldByName('Mois').AsInteger :=2;
      NbrEchantParM.DataSet.FieldByName('NomMois').AsString :='Février';
      NbrEchantParM.DataSet.Post;
      NbrEchantParM.DataSet.Append;
      NbrEchantParM.DataSet.FieldByName('NbEchant').AsInteger :=nbrEchantMars;
      NbrEchantParM.DataSet.FieldByName('Mois').AsInteger :=3;
      NbrEchantParM.DataSet.FieldByName('NomMois').AsString :='Mars';
      NbrEchantParM.DataSet.Post;
      NbrEchantParM.DataSet.Append;
      NbrEchantParM.DataSet.FieldByName('NbEchant').AsInteger :=nbrEchantAvril;
      NbrEchantParM.DataSet.FieldByName('Mois').AsInteger :=4;
      NbrEchantParM.DataSet.FieldByName('NomMois').AsString :='Avril';
      NbrEchantParM.DataSet.Post;
    finally
      NbrEchantParMCDS.First;
      NbrEchantParMCDS.EnableControls;
    end;




Dans modification TDBChart, j'ai ajouter la série 3 (histogramme), je vais dans l'onglet Séries, puis Sources de données, je choisis DataSet =
NbrEchantParMCDS, puis
Libellé=NomMois
X=Mois
Hist=NbEchant

Quand je compile, ma grille qui est reliée à mon data source

NbrEchantParM affiche bien les résultats entrés mais mon graphique est vide... Quelqu'un aurait il une proposition ?

18 réponses

Messages postés
3793
Date d'inscription
samedi 22 décembre 2007
Statut
Membre
Dernière intervention
3 juin 2016
8
Un "With NbrEchantParM.DataSet do" serait la bienvenue pour alléger tout ça :p
C'est déjà un conseil que je te donne ;)
Exemple :
_____________________________

with NbrEchantParM.DataSet do
try
NbrEchantParMCDS.EmptyDataSet;
NbrEchantParMCDS.DisableControls;
Append;
FieldByName('NbEchant').AsInteger :=nbrEchantJanv;
FieldByName('Mois').AsInteger :=1;
... etc ...
finally
NbrEchantParMCDS.First;
NbrEchantParMCDS.EnableControls;
end;
_________________________

Plus lisible déjà non ? (J'ai pas mis toutes les lignes, mais ça enleve au moins 40% du code)

Cordialement, Bacterius !
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

Effectivement, merci, c'est déjà ca !!
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
bonsoir,

est-ce que tes données sont bien stockées dans ta table ?
est-ce que ta table est ouverte lors de l'activation du TeeChart ?

cantador
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

Bonsoir,
par table tu veux dire quoi ?

Si tu veux dire mon Tclientdataset oui mes données sont bien stockées puisque ma DBGrid est reliée à mon Tclientdataset et lors de la compilation elle affiche bien les données. Donc forcément oui elle est ouverte, juste après mon gros machin de code j'ai :

NbrEchantParMCDS.Open;
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
Remplace ton TClientDataSet par un TDataSource + un TQuery
relie le tout avec ton TDBChart

cantador
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

Ok j'essairai lundi mais un TQuery on s'en sert comment au juste parce que je n'ai pas qu'une requete pour récupérer tous ca !
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
Dans le SQL tu mets la requête qui affiche les données principales

cantador
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

ben c'est ps pssible, comment faire une requete qui afficherai les nom des mois ? Parce que le nombr d'écantillon par mois ok avec des parametres, mais les mois....
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
si c'est paradoxe, il doit y avoir la fonction :

EXTRACT(MONTH FROM MaTable.MaDate) AS MOIS FROM MaTable)

et si tu stockes tes mois en nombre entier :
tu peux créer :

  Mois: array[1..12] of string = ('janvier', 'février', 'mars', 'avril',
    'mai', 'juin', 'juillet', 'août', 'septembre', 'octobre', 'novembre', 'décembre');

mettre dans le OnCalField :

uses  DateUtils;
---
NomMois := Mois[Mois];

cantador
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

Alors le problème c'est que EXTRACT ne fonctionne pas, pourtant j'ai regardé quelques sites pour savoir l'utiliser il ne me semble pas que je montre, dans l'analyseur de requêtes SQL de SQL Server Entreprise Manager j'ai tappé ma requête :
"SELECT EXTRACT(MONTH FROM DateDemande) AS MOIS FROM Sous_Traitance"

j'ai essayé aussi

"SELECT EXTRACT(MONTH FROM Sous_Traitance.DateDemande) AS MOIS FROM Sous_Traitance"

Ca ne marche pas non plus. Cela me met l'erreur : Serveur :
Msg 156, Niveau 15, État 1, Ligne 1
Syntaxe incorrecte vers le mot clé 'FROM'.

Sachant que Sous_Traitance est le nom de ma table et DateDemande le nom de mon champ de type DateTime.

DateUtils permet-il justement de faire des Extract ? Et c'est pour cela que je ne peux pas en faire sur le SQL Server Entreprise Manager ?

De plus, le OnCalcField, je ne savais pas du tout ce que c'était, j'ai lu l'aide de Delphi, je pense avoir compris, il suffit de faire :

procedure TFormSTableauDeBord.Query1CalcFields(DataSet: TDataSet);
begin
    inherited;
    NomMois := Mois[Mois];
end;

Et   Mois: array[1..12] of string = ('janvier', 'février', 'mars', 'avril',
    'mai', 'juin', 'juillet', 'août', 'septembre', 'octobre', 'novembre', 'décembre'); Je le met dans une fonction ?
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
Pour EXTRACT, j'avais précisé "si c'est paradoxe",
pour sql server je ne sais pas mais je pense compte tenu qu'il s'agit d'un bonne base, qu'il doit y avoir une fonction équivalente..

Et   Mois: array[1..12] of string = ('janvier', 'février', 'mars', 'avril',
    'mai', 'juin', 'juillet', 'août', 'septembre', 'octobre', 'novembre', 'décembre'); Je le met dans une fonction ?

Non, ce n'est pas franchement nécessaire tu peux passer ton tableau en constante :

Const
Mois: array[1..12] of string = ('janvier', 'février', 'mars', 'avril',
    'mai', 'juin', 'juillet', 'août', 'septembre', 'octobre', 'novembre', 'décembre');

ainsi tu pourras utiliser patout dans ton programme
NomMois := Mois[Mois];

mais si tu veux passer une fonction pourquoi pas :

Function AfficheMois(NumMois : integer) : string;
begin
Result := Mois[NumMois];
end;



Le inherited n'est pas nécessaire dans le OnCalcFields







cantador
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

Déjà merci merci beaucoup pour ton aide, alors pour information pour SQL server il suffit de faire
SELECT Month(MaDate) AS Mois FROM MaTable;

Sinon, je pousse un peu mais je vois pas comment on se sert de :





NomMois := Mois[Mois];

Qu'est ce que c'est NomMois ? C'est un paramètre de ma requête SQL ?
J'ai fait tenté ca comme ca, vu que jvoulais que ce soit un nouveau champs mais c'est pas glorieux lol :



SELECT     MONTH(S.DateDemande) AS Mois, :NomMois AS NomMois,
                   COUNT(E.NO_ECHANT) AS NbEchant

FROM         SOUS_TRAITANCE S LEFT OUTER JOIN
                     ECHANTILLON E ON E.NoSous_Traitance = S.NO_SOUS_TRAITANCE

WHERE     (E.SousTraite = 1) AND (ISNULL(S.DateDemande, '') <> '')
                   AND ((E.Statut <> '') OR ISNULL(E.Statut,'') <> 'DI')

GROUP BY MONTH(S.DateDemande)
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
NomMois := Mois[Mois];



C'est rien, c'est juste une variable string pour la différencier du Mois (integer)


d'ailleurs, il vaudrait mieux écrire pour le OnCalFields :


var
NomMois : string;
NumMois : integer;
----
begin
NomMois := Mois[NumMois];
end;

Mais c''est bien mieux de l'intégrer dans ta requête.
je ne sais pas exactement ce que tu veux faire au niveau des tests :
WHERE     (E.SousTraite = 1) AND (ISNULL(S.DateDemande, '') <> '')
                   AND ((E.Statut <> '') OR ISNULL(E.Statut,'') <> 'DI')

L'important est que cela donne le résultat attendu

cantador
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
D'ailleurs, il y avait plus simple pour les mois sans DateUtils et sans tableau :
directement sous SysUtils :

NomMois := LongMonthNames[NumMois];

cantador
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

En fait, ce qu'il y a c'est que ne sait pas comment le rendre exploitable le NomMois, voila ce que j'avais fait :


SELECT     MONTH(S.DateDemande) AS Mois,

                   :NomMois,

                   COUNT(E.NO_ECHANT) AS NbEchant


FROM         SOUS_TRAITANCE S LEFT OUTER JOIN

                     ECHANTILLON E ON E.NoSous_Traitance = S.NO_SOUS_TRAITANCE


GROUP BY MONTH(S.DateDemande)


-------------------------------------------------------------------------------------------------------------------

procedure TFormSTableauDeBord.NbrEchantParMQCalcFields(DataSet: TDataSet);

var NomMois : String; Mois : integer;

begin

  NomMois := longmonthnames[Mois];

  NbrEchantParMQ.Parameters.ParamByName('NomMois').Value := NomMois;

  if (not (NbrEchantParM.DataSet.State in [dsInactive])) then

    NbrEchantParMQ.Requery;

end;


Mais quand je compile, ca ne rentre même pas dans la procédure... Qui
plus est, mon histogramme ne veut pas du champs :NonMois, il ne le voit
pas...


J'ai essayé ca aussi :

SELECT     MONTH(S.DateDemande) AS Mois,

                   LongMonthNames[MONTH(S.DateDemande)] AS NomMois,

                   COUNT(E.NO_ECHANT) AS NbEchant


FROM         SOUS_TRAITANCE S LEFT OUTER JOIN

                     ECHANTILLON E ON E.NoSous_Traitance = S.NO_SOUS_TRAITANCE


GROUP BY MONTH(S.DateDemande)


Mais ca me met une erreur, surement à cause du Group By, je pense, ca
me met "Erreur près du mot AS". Je vois pas du tout comment faire...
Et il connait bien LongMonthNames puisque je m'en sert autre part.
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
Et il connait bien LongMonthNames puisque je m'en sert autre part.




oui mais pas dans le SQL je suppose...

cantador
Messages postés
20
Date d'inscription
dimanche 9 novembre 2008
Statut
Membre
Dernière intervention
26 août 2009

Effectivement autant pour moi... Mais du coup je vois quand même pas ce que j'ai pu louper...
Messages postés
4719
Date d'inscription
dimanche 26 février 2006
Statut
Modérateur
Dernière intervention
1 février 2021
14
et cette écriture elle fonctionne ? :

SELECT     MONTH(S.DateDemande) AS Mois,
                COUNT(E.NO_ECHANT) AS NbEchant

FROM         SOUS_TRAITANCE S LEFT OUTER JOIN
                  ECHANTILLON E ON E.NoSous_Traitance = S.NO_SOUS_TRAITANCE

GROUP BY MONTH(S.DateDemande)

Sinon, le mieux est de monter ses requêtes dans un éditeur SQL :
tu poses des tables, en plaçant les relations.
tu complètes l'écriture de la requête et tu testes

cantador