Problem z powielaniem funkcje i zmienne globalne w aplikacji PySide6 funkcja drukowania dnia i miesiąca powielane po naciśnięciu przycisku

0

Pytanie

Jestem nowy i wiem, że coś przegapiłem, ale nie wiem, co dokładnie, dlatego mam aplikacja PySide6, i stworzyłem funkcję do tworzenia kalendarza w QTableWidget za pomocą modułu "kalendarz" w Pythonie wszystko działało normalnie, ale problem pojawił się, gdy próbowałem dodać przyciski nawigacji, aby uzyskać następny i poprzedni miesiąc: To jest moja funkcja:

import sys
import os
import platform
import datetime as dt
import time
import calendar

from PySide6 import *
from PySide6 import QtGui
from PySide6 import QtWidgets
from PySide6 import QtCore
from PySide6.QtGui import QColor

from functools import partial

yy = int(dt.datetime.now().strftime("%Y"))
mm = int(dt.datetime.now().strftime("%m"))

class MainWindow(QMainWindow):
    def __init__(self):
        QMainWindow.__init__(self)
        self.ui = Ui_MainWindow()
        self.ui.setupUi(self)
        global widgets
        widgets = self.ui

        # Calender generator
        self.calender_gen(mm,yy)



    def calender_gen(self, mm_g, yy_g):
        # Creat table rows and columns
        widgets.tableWidget_3.setRowCount(5)
        widgets.tableWidget_3.setColumnCount(7)

        # Table header labels
        week_list = ["Sat","Sun","Mon","Tue","Wed","Thu","Fri"]
        widgets.tableWidget_3.setHorizontalHeaderLabels(week_list)

        # Start inserting days of the month into the table
        row = 0
        col = 0
        for week in calendar.monthcalendar(yy_g,mm_g):
            for day in week:
                if day == 0:
                    widgets.tableWidget_3.setItem(row,col,QTableWidgetItem(" "))
                else:
                    widgets.tableWidget_3.setItem(row,col,QTableWidgetItem(str(day)))
                col += 1
            row += 1
            col = 0
        print(mm_g,yy_g)
        # Connect Buttons to function
        widgets.pushButton_3.clicked.connect(partial(self.next_calendar_butt,mm_g,yy_g))
        widgets.pushButton_2.clicked.connect(partial(self.prev_calendar_butt,mm_g,yy_g))

    def next_calendar_butt(self,mm_new, yy_new):
        mm_new += 1
        if mm_new > 12:
            mm_new = 1
            yy_new += 1

        widgets.tableWidget_3.setRowCount(0)
        widgets.tableWidget_3.setColumnCount(0)
        self.calender_gen(mm_new,yy_new)

    def prev_calendar_butt(self,mm_g_new,yy_g_new):
        mm_g_new -= 1
        if mm_g_new == 0:
            mm_g_new = 12
            yy_g_new -= 1

        widgets.tableWidget_3.setRowCount(0)
        widgets.tableWidget_3.setColumnCount(0)
        self.calender_gen(mm_g_new,yy_g_new)

Kiedy uruchamiam aplikację, kalendarz pojawi się w tabeli, jak na zdjęciu, obrazie tabeli interfejsu graficznego

Konsola wyjścia Konsoli drukuje 11 2021

Gdy naciskam na przycisk 3 po raz pierwszy, ona działa i drukuje "12 2021" w konsoli, konsola drukuje 12 2021 Ale po tym, jak ponownie naciśnij ten sam przycisk, zaczyna się powielanie: konsola drukuje "12 2021 2022 1" konsola drukuje 12 2021 2022 1 Jeśli nacisnę jeszcze raz, to wydrukuje '12 2021 1 2022 1 2022 2 2022' jak na zdjęciu, wprowadź opis zdjęcia tutaj z każdym kliknięciem, powiela więcej, gdzie powinno być wydrukowane tylko jedno stwierdzenie, tj. "2 2022".

Próbowałem przenieść poniższe polecenia z funkcji calendar_gen (), ale nie jestem w stanie przekazać parametry, nawet po deklaracji zmiennych globalnych i przypisanie ich parametry :

widgets.pushButton_3.clicked.connect(partial(self.next_calendar_butt,mm_g,yy_g))
widgets.pushButton_2.clicked.connect(partial(self.prev_calendar_butt,mm_g,yy_g))

Próbowałem to zrobić: Wewnątrz funkcji calendar_gen() ogłosiłem zmienne globalne i wyznaczył ich w parametrach funkcji, aby stworzyć coś w rodzaju globalnego parametru

global var_mm
global var_yy

var_mm = mm_g
var_yy = yy_g

następnie w funkcji inicjalizacji(self) podłączam te 2 linie:

def __init__(self):
    widgets.pushButton_3.clicked.connect(partial(self.next_calendar_butt,var_mm,var_yy))
    widgets.pushButton_2.clicked.connect(partial(self.prev_calendar_butt,var_mm,var_yy))

Ale to nie działa w konsoli, ona drukuje "11 2021", gdy uruchamiam aplikację, a następnie, gdy wciskam przycisk 3, drukuje "12 2021", a kiedy znowu klikam na nią, ona znowu drukuje "12 2021" i tak dalej To samo z innym przyciskiem, na której ponownie i ponownie pojawi się "10 2021"

global-variables pyqt pyqt6 pyside6
2021-11-21 22:34:07
1

Najlepsza odpowiedź

0

Połączenia sygnałów Qt nie są wyłączone (domyślne), a sygnał może być podłączony do tej samej funkcji więcej niż jeden raz.

Ponieważ podłączeniu clicked sygnały z przycisków w calender_genza każdym razem, gdy wywoływana jest ta funkcja, można dodać dodatkowe połączenie do tych transakcji. W wyniku podłączone funkcje będą wywoływane tyle razy, ile były one podłączone za każdym razem, gdy podawany jest sygnał.

Dobrym rozwiązaniem jest połączenie do funkcji, które przełączyłeś miesiąc i ratowali link na bieżący miesiąc do obliczenia "nowego" miesiąca.

Ponieważ funkcje są niemal identyczne, lepiej pogrupować je w unikalną funkcję, a następnie połączyć sygnały z poszczególnymi funkcjami, które w efekcie spowodują tę poprzednią funkcję z odpowiednim parametrem:

class MainWindow(QMainWindow):
    def __init__(self):
        # ...
        self.calender_gen(mm,yy)

        self.pushButton_2.clicked.connect(self.prev_month)
        self.pushButton_3.clicked.connect(self.next_month)

    def calender_gen(self, mm_g, yy_g):
        # Creat table rows and columns
        self.tableWidget_3.setRowCount(5)
        self.tableWidget_3.setColumnCount(7)

        # Table header labels
        week_list = ["Sat","Sun","Mon","Tue","Wed","Thu","Fri"]
        self.tableWidget_3.setHorizontalHeaderLabels(week_list)

        # Start inserting days of the month into the table
        row = 0
        col = 0
        for week in calendar.monthcalendar(yy_g,mm_g):
            for day in week:
                if day == 0:
                    self.tableWidget_3.setItem(row,col,QTableWidgetItem(" "))
                else:
                    self.tableWidget_3.setItem(row,col,QTableWidgetItem(str(day)))
                col += 1
            row += 1
            col = 0

        self.current_month = mm_g
        self.current_year = yy_g

    def prev_month(self):
        self.step_month(-1)

    def next_month(self):
        self.step_month(1)

    def step_month(self, delta):
        mm_new = self.current_month + delta
        mm_year = self.current_year
        if mm_new > 12:
            mm_new = 1
            mm_year += 1
        elif mm_new < 1:
            mm_new = 12
            mm_year -= 1

        self.calender_gen(mm_new, mm_year)

Oczywiście, że prawidłowa realizacja QCalendarWidget może być o wiele łatwiejsze, ponieważ ona już udostępnia większość funkcji.

2021-11-21 23:56:46

W innych językach

Ta strona jest w innych językach

Русский
..................................................................................................................
Italiano
..................................................................................................................
Română
..................................................................................................................
한국어
..................................................................................................................
हिन्दी
..................................................................................................................
Français
..................................................................................................................
Türk
..................................................................................................................
Česk
..................................................................................................................
Português
..................................................................................................................
ไทย
..................................................................................................................
中文
..................................................................................................................
Español
..................................................................................................................
Slovenský
..................................................................................................................