Files
shipheart-qt/Shipheart_bouton_circuit.qml

340 lines
19 KiB
QML

//-----------------------------------------------------------------------------------------------------
// Fichier définissant un bouton de type Circuit sur la page d'accueil
// A priori, appelé depuis "home.qml"
//-----------------------------------------------------------------------------------------------------
import QtQuick 2.12
//=======================================================
// Ensemble du bouton
//=======================================================
Item {
id: bouton_circuit
// Paramètres d'affichage :
readonly property int largeur_bouton: circuits_grid.cellWidth - espace_colonnes_secondaires;
readonly property int hauteur_bouton: circuits_grid.cellHeight - espace_lignes_secondaires;
readonly property double pourcentage_largeur_zone_affichage_nom: 0.60
readonly property double pourcentage_largeur_zone_affichage_consigne: 0.25
readonly property int espace_interne: 5
// | zone affichage nom | cdes auto | consigne |
// | zone affichage intensité | | |
width: largeur_bouton
height: hauteur_bouton
Rectangle {
width: parent.width
height: parent.height
color: (model.Etat_systeme === 0) ? "transparent" : shipheart_couleur_fond_bouton // On ne peut pas mettre l'opacité sur celui-ci, sinon tous ses enfants sont aussi semi-transparents...
radius: shipheart_rayon_bouton
border.color: couleur_rouge
border.width: (model.Etat_systeme === 0) ? 0 : 3
//------------------------------------------------------------------------------------------
// Zone de parametres (toute la partie gauche, hors consigne et hors cde AUTO s'il y en a :
//------------------------------------------------------------------------------------------
Rectangle {
id: zone_parametres
x: 0
y: 0
width: ((model.Type_circuit === shipheart_type_module_shipbase) && (model.No_circuit === 0)) ?
parent.width : // Cas du circuit #0 de ShipBase
(model.Validation_cdes_events >= 0) ? // Cas général :
(parent.width * pourcentage_largeur_zone_affichage_nom) - espace_interne : // Avec commandes AUTO
parent.width * (1 - pourcentage_largeur_zone_affichage_consigne) // Sans commandes AUTO
height: parent.height;
color: (model.Etat_systeme === 0) ? shipheart_couleur_fond_bouton : "transparent"
radius: shipheart_rayon_bouton
Image { // Affichage du coin inférieur-droit en rouge ou orange si alarme ou alerte
source: ( (Etat_circuit === shipheart_etat_circuit_limitation) ||
(Etat_circuit === shipheart_etat_circuit_protection) ||
(Etat_circuit === shipheart_etat_circuit_disjonte) ||
(Etat_circuit === shipheart_etat_circuit_absence_terre) ||
(Etat_circuit === shipheart_etat_circuit_absence_masse) )
? "/images/coin_bas_droite_rouge.png"
: "/images/coin_bas_droite_orange.png"
// (Etat_commande_carte === shipheart_etat_commande_module_test) ||
// (Etat_commande_carte === shipheart_etat_commande_module_undervoltage) ||
// (Etat_circuit === shipheart_etat_circuit_cc_batterie) ||
// (Etat_circuit === shipheart_etat_circuit_deleste) ||
// (Etat_circuit === shipheart_etat_circuit_inversion_phase_neutre) ||
// (Etat_circuit === shipheart_etat_circuit_undervoltage) ||
// (Etat_events > 0)
sourceSize.height: 20
anchors {
bottom: parent.bottom
right: parent.right
}
visible: ( (Etat_commande_carte !== shipheart_etat_commande_module_ok)
|| (Etat_circuit !== shipheart_etat_circuit_ok)
|| (Etat_events > 0) )
&& (model.Etat_systeme === 0) // SDIR #285
}
MouseArea { // Zone d'interaction Paramètres du circuit
id: mouse_area_zone_parametres
x: 0
y: 0
anchors.fill: parent
onClicked: {
shipheart_clic();
stackView.push("circuit.qml", {"id_circuit": model.Cle_primaire, "consigne": model.Consigne })
}
}
}
//-------------------------------------------------------
// Zone du nom (en haut à gauche et au milieu) :
//-------------------------------------------------------
Rectangle {
id: nom
color: "transparent"
x: 0
y: 0
width: (parent.width * pourcentage_largeur_zone_affichage_nom) - espace_interne
height: parent.height / 2;
Text {
text: model.Nom
anchors.fill: parent // Permet que le texte occupe tout l'espace du parent (et que le centrage vertical qui suit fonctionne...)
verticalAlignment: Text.AlignVCenter
horizontalAlignment: Text.AlignLeft
leftPadding: 10
font.pixelSize: 15
font.weight: Font.Bold
color: couleur_blanc_casse
}
}
//-------------------------------------------------------
// Zone de cdes auto (en haut au centre) :
//-------------------------------------------------------
Rectangle {
id: cdes_auto
x: parent.width * pourcentage_largeur_zone_affichage_nom
y: 0;
width: (parent.width * (1 - pourcentage_largeur_zone_affichage_nom - pourcentage_largeur_zone_affichage_consigne));
height: parent.height;
radius: shipheart_rayon_bouton
color: shipheart_couleur_fond_bouton
visible: (model.Etat_systeme === 0) && (model.Validation_cdes_events >= 0)
Text {
text: "Auto" // Attention : Non traduit...
anchors.fill: parent // Permet que le texte occupe tout l'espace du parent (et que le centrage vertical qui suit fonctionne...)
verticalAlignment: Text.AlignVCenter
horizontalAlignment: Text.AlignHCenter
font.pixelSize: 15
font.weight: Font.Bold
color : (model.Validation_cdes_events === 0) ? couleur_gris_moyen : couleur_green_yellow
}
MouseArea { // Zone d'interaction. On est obligé de la mettre dans la grille pour que Rectangle et MouseArea soient frères ou parent/enfant ET qu'on n'occupe qu'un espace dans la grille.
id: mouse_area_cdes_auto
x: 0
y: 0
width: parent.width
height: parent.height
pressAndHoldInterval: shipheart_mouse_press_and_hold_interval_long
onPressAndHold: {
shipheart_clic();
toggle_cdes_auto();
timer_home.restart(); // Permet de réarmer le timer (qui ne doit PAS être 'triggeredOnStart' !) afin de reporter la prochaine mise à jour à une période entière de timer. Cela évite qu'un raffraichissement arrive trop tôt, avant que la nouvelle consigne ne soit prise en compte => On>Off>On ou Off>On>Off...
}
}
// Halo autour du bouton pendant l'appui :
Rectangle {
anchors {
verticalCenter: parent.verticalCenter
horizontalCenter: parent.horizontalCenter
}
width: Math.max(parent.width, parent.height) + 100
height: width
radius: width / 2
color : (model.Validation_cdes_events === 0) ? couleur_gris_moyen : couleur_green_yellow
opacity: 0.2
visible: mouse_area_cdes_auto.pressed
}
}
//-------------------------------------------------------
// Zone du courant instantané (en bas à gauche) :
//-------------------------------------------------------
Rectangle {
id: courant_instantane
color: "transparent" // Sinon, le fond du rectangle est blanc...
x: 0
y: hauteur_bouton / 2;
width: parent.width * pourcentage_largeur_zone_affichage_nom;
height: parent.height / 2;
visible: (model.Etat_systeme === 0) ? (consigne_principale.text !== qsTr("Off")) : 0
Image {
source: "/images/icone_consommation_electrique.png"
sourceSize.height: 20
anchors.left: courant_instantane.left
anchors.leftMargin: 5
anchors.verticalCenter: courant_instantane.verticalCenter
}
Text {
text: (model.Type_circuit !== shipheart_type_module_shippower4AC ?
"DC " + model.Tension.toFixed(2) + " V " + (model.Intensite > shipheart_plancher_intensite_circuit_sp8xx ? " | " + model.Intensite.toFixed(2) + " A | " + (model.Tension * model.Intensite).toFixed(0) + " W" : "") :
"AC " + model.Tension.toFixed(0) + " V | " + model.Frequence.toFixed(1) + " Hz " + (model.Intensite > shipheart_plancher_intensite_circuit_sp4ac ? " | " + model.Intensite.toFixed(1) + " A | " + (model.Tension * model.Intensite).toFixed(0) + " VA" : ""))
anchors.fill: parent // Permet que le texte occupe tout l'espace du parent (et que le centrage vertical qui suit fonctionne...)
verticalAlignment: Text.AlignVCenter
horizontalAlignment: Text.AlignLeft
leftPadding: 20
font.pixelSize: 12
color: couleur_gris_tres_tres_pale
}
}
//-------------------------------------------------------
// Zone de consigne (au milieu, à droite) :
//-------------------------------------------------------
Rectangle {
id: consigne
x: (parent.width * (1 - pourcentage_largeur_zone_affichage_consigne)) + espace_interne
width: (parent.width * pourcentage_largeur_zone_affichage_consigne) - espace_interne
height: parent.height;
//color: (model.Etat_commande_carte === shipheart_etat_commande_module_ok) ? ((model.Consigne === 0) ? couleur_rouge_transparent : couleur_vert_transparent) : "transparent"
color: (model.Etat_commande_carte === shipheart_etat_commande_module_ok) ? ((model.Consigne === 0) ? shipheart_couleur_fond_bouton : couleur_vert_transparent) : "transparent" // SDIR #207
radius: shipheart_rayon_bouton
border.width: (model.Etat_commande_carte === shipheart_etat_commande_module_ok) ? 0 : 3
border.color: (model.Etat_commande_carte === shipheart_etat_commande_module_ok) ? // SDIR #182
((model.Consigne === 0) ? couleur_rouge : couleur_green_yellow) : // SDIR #159. En pratique, inutile car dans ce cas, border.width=0
// ((model.Mode_test === 0) ? couleur_rouge : couleur_green_yellow) // SDIR #182
((model.Mode_test === 0) ? shipheart_couleur_fond_bouton : couleur_green_yellow) // SDIR #182 & SDIR #207
visible: (model.Etat_systeme === 0) && ((model.Type_circuit !== shipheart_type_module_shipbase) || (model.No_circuit !== 0))
Text {
id: consigne_principale
text: (model.Etat_commande_carte === shipheart_etat_commande_module_undervoltage) ?
"Off" :
((model.Etat_commande_carte === shipheart_etat_commande_module_ok) ?
((model.Consigne === 0) ? qsTr("Off") : qsTr("On")) :
((model.Mode_test === 0) ? qsTr("Off") : qsTr("On")))
anchors.verticalCenter: consigne.verticalCenter
anchors.verticalCenterOffset: ((model.Etat_commande_carte === shipheart_etat_commande_module_ok) && (model.Consigne > 0) && (model.Consigne < 100)) ? -10 : 0
anchors.horizontalCenter: consigne.horizontalCenter
font.pixelSize: 20
font.weight: Font.Bold
color: (model.Etat_commande_carte === shipheart_etat_commande_module_ok) ? // SDIR #182
((model.Consigne === 0) ? couleur_gris_pale : couleur_green_yellow) : // SDIR #159 & SDIR #207
((model.Mode_test === 0) ? couleur_gris_pale : couleur_green_yellow) // SDIR #182 & SDIR #207
}
Text {
id: consigne_secondaire
text: (model.Etat_commande_carte === shipheart_etat_commande_module_undervoltage) ?
"" :
((model.Etat_commande_carte === shipheart_etat_commande_module_ok) ?
((model.Consigne === 0) ? "" : ((model.Consigne === 100) ? "" : (model.Consigne + "%"))) :
"" )
anchors.top: consigne_principale.bottom
anchors.horizontalCenter: consigne.horizontalCenter
font.pixelSize: 16
color: (model.Consigne === 0) ? couleur_gris_pale : couleur_green_yellow // SDIR #159 & SDIR #207
}
MouseArea { // Zone d'interaction. On est obligé de la mettre dans la grille pour que Rectangle et MouseArea soient frères ou parent/enfant ET qu'on n'occupe qu'un espace dans la grille.
id: mouse_area_consigne
anchors.fill: parent
enabled: (model.Etat_commande_carte === shipheart_etat_commande_module_ok) // Si on est en Undelvoltage ou en Test, on rend le bouton inoppérant...
pressAndHoldInterval: shipheart_mouse_press_and_hold_interval_long
onClicked: {
shipheart_clic();
var new_consigne;
if (model.Consigne === 0)
{
if (model.Old_consigne === 0) new_consigne = 100; // Si OLD = 0, on passe la consigne à 100%
else new_consigne = model.Old_consigne; // Sinon, on applique OLD à NEW
}
else new_consigne = 0;
// Mise à jour de la nouvelle consigne :
changement_consigne(new_consigne, -1);
timer_home.restart(); // Permet de réarmer le timer (qui ne doit PAS être 'triggeredOnStart' !) afin de reporter la prochaine mise à jour à une période entière de timer. Cela évite qu'un raffraichissement arrive trop tôt, avant que la nouvelle consigne ne soit prise en compte => On>Off>On ou Off>On>Off...
}
onPressAndHold: {
shipheart_clic();
if ((model.Consigne > 0) && (model.Consigne <100)) // On ne traite l'appui long que si on est ON [ET] en gradateur
{
// Mise à jour des nouvelles Consigne et Old_consigne :
changement_consigne(100, 100);
timer_home.restart(); // Permet de réarmer le timer (qui ne doit PAS être 'triggeredOnStart' !) afin de reporter la prochaine mise à jour à une période entière de timer. Cela évite qu'un raffraichissement arrive trop tôt, avant que la nouvelle consigne ne soit prise en compte => On>Off>On ou Off>On>Off...
}
}
}
}
// Fin de 'Zone de consigne'
//-------------------------------------------------------
//-------------------------------------------------------
// Zone d'interaction du circuit lorsque le circuit est ABSENT :
//-------------------------------------------------------
MouseArea {
id: mouse_area_absence
anchors.fill: parent
width: largeur_bouton * pourcentage_largeur_zone_affichage_nom;
height: hauteur_bouton;
enabled: (model.Etat_systeme !== 0)
onClicked: {
shipheart_clic();
stackView.push("circuit.qml", {"id_circuit": model.Cle_primaire })
}
}
// Fin de 'mouse_area_absence'
//-------------------------------------------------------
}
//=============================================================================================================
// Mise à jour de la valeuer de consigne
//=============================================================================================================
function changement_consigne(new_consigne, old_consigne)
{
var req;
// Mise à jour immédiate du modèle pour que l'affichage réagisse immédiatement :
modele_circuits.setProperty(index , "Consigne", new_consigne);
// Mise à jour dans la BDD :
req = "UPDATE TB_Circuits SET New_consigne=" + new_consigne + " ";
if (old_consigne !== -1) req += ", Old_consigne=" + old_consigne + " ";
req += " WHERE Cle_primaire='" + model.Cle_primaire + "'";
//console.log("Requête = [" + req + "]");
bdd.requete_unique(req);
synchro_bdd(shipheart_type_synchro_data);
}
//=============================================================================================================
// Mise à jour de Cdes Auto
//=============================================================================================================
function toggle_cdes_auto()
{
var req;
var mode;
if (model.Validation_cdes_events === 0) mode = 1;
else mode = 0;
// Mise à jour immédiate du modèle pour que l'affichage réagisse immédiatement :
modele_circuits.setProperty(index , "Validation_cdes_events", mode);
// Mise à jour dans la BDD :
bdd.requete_unique("UPDATE TB_Circuits SET Validation_cdes_events=" + mode + " WHERE Cle_primaire='" + model.Cle_primaire + "'")
// Note : le modèle sera ensuite remis à jour par la routine périodique dans HOME. en l'occurence, le modèle sera déjà à jour sur ce champ...
}
}