python 我不知道如何制作要展示的分子

l7wslrjt  于 2023-05-27  发布在  Python
关注(0)|答案(1)|浏览(148)

下面是我的程序代码。本程序是为人们制作一个气体分子模拟的程序。按下Ui中的Addmolecule按钮时,分子应随机显示在Ui上。然而,它不起作用。我需要帮助...

import sys
import random
import math
from PyQt5.QtWidgets import QApplication, QMainWindow, QSlider, QLabel, QVBoxLayout, QWidget, QPushButton, QGraphicsEllipseItem, QGraphicsScene, QGraphicsView
from PyQt5.QtGui import QPainter, QColor
from PyQt5.QtCore import Qt
from PyQt5 import uic

form_ui = uic.loadUiType("qqq.ui")[0]

class GasMoleculeWindow(QMainWindow, form_ui):
    def __init__(self):
        super().__init__()
        self.setupUi(self)
         
        self.setWindowTitle("Gas Molecule Simulation")
        self.setGeometry(100, 100, 800, 600)

        self.molecules = []
        self.temperature = 1.0

        self.addMoleculeButton.clicked.connect(self.addMolecule)
        self.stopSimulation.clicked.connect(self.stopProgram)
        self.massSlider.setRange(1,10)
        self.massSlider.valueChanged.connect(self.updateMass)
        self.radiusSlider.valueChanged.connect(self.updateRadius)
        self.temperatureSlider.valueChanged.connect(self.updateTemperature)

        self.massLabel.setAlignment(Qt.AlignCenter)
        self.radiusLabel.setAlignment(Qt.AlignCenter)
        self.temperatureLabel.setAlignment(Qt.AlignCenter)

        self.scene = QGraphicsScene(self)
        self.view = QGraphicsView(self.scene)

        layout = QVBoxLayout(self)
        layout.addWidget(self.view)

        self.timer = self.startTimer(10)

    def addMolecule(self):
        for _ in range(10):
            molecule = {
                'x': random.uniform(0, self.width()),
                'y': random.uniform(0, self.height()),
                'vx': random.uniform(-1, 1) * math.sqrt(3 * self.temperature / self.massSlider.value()),
                'vy': random.uniform(-1, 1) * math.sqrt(3 * self.temperature / self.massSlider.value()),
                'mass': self.massSlider.value(),
                'radius': self.radiusSlider.value()
            }
            self.molecules.append(molecule)

            molecule_item = QGraphicsEllipseItem(
                molecule['x'] - molecule['radius'],
                molecule['y'] - molecule['radius'],
                2 * molecule['radius'],
                2 * molecule['radius']
            )
            molecule_item.setBrush(QColor(255, 0, 0))

            mass_color = self.getColorByMass(molecule['mass'])
            molecule_item.setBrush(QColor(*mass_color))

            self.scene.addItem(molecule_item)

    def getColorByMass(self, mass):
        min_mass = 1
        max_mass = 10

        min_color = QColor(0, 0, 255)  # Blue
        max_color = QColor(255, 0, 0)  # Red

        ratio = (mass - min_mass) / (max_mass - min_mass)

        r = int(min_color.red() + ratio * (max_color.red() - min_color.red()))
        g = int(min_color.green() + ratio * (max_color.green() - min_color.green()))
        b = int(min_color.blue() + ratio * (max_color.blue() - min_color.blue()))

        return r, g, b

    def updateMass(self):
        massValue = self.massSlider.value()
        self.massLabel.setText(f"Mass: {massValue}")

    def updateRadius(self):
        radiusValue = self.radiusSlider.value()
        self.radiusLabel.setText(f"Radius: {radiusValue}")

    def updateTemperature(self):
        temperatureValue = self.temperatureSlider.value() / 10.0
        self.temperature = temperatureValue
        self.temperatureLabel.setText(f"Temperature: {temperatureValue}")

        for molecule in         self.molecules:
            molecule['vx'] = random.uniform(-1, 1) * math.sqrt(3 * temperatureValue / molecule['mass'])
            molecule['vy'] = random.uniform(-1, 1) * math.sqrt(3 * temperatureValue / molecule['mass'])

    def timerEvent(self, event):
        for i in range(len(self.molecules)):
            molecule = self.molecules[i]
            molecule_item = self.scene.items()[i]

            molecule['x'] += molecule['vx']
            molecule['y'] += molecule['vy']

            molecule_item.setRect(
                molecule['x'] - molecule['radius'],
                molecule['y'] - molecule['radius'],
                2 * molecule['radius'],
                2 * molecule['radius']
            )

            if molecule['x'] < molecule['radius'] or molecule['x'] > self.width() - molecule['radius']:
                molecule['vx'] *= -1
            if molecule['y'] < molecule['radius'] or molecule['y'] > self.height() - molecule['radius']:
                molecule['vy'] *= -1

            for j in range(i + 1, len(self.molecules)):
                other_molecule = self.molecules[j]
                dx = other_molecule['x'] - molecule['x']
                dy = other_molecule['y'] - molecule['y']
                distance = math.sqrt(dx ** 2 + dy ** 2)

                if distance < molecule['radius'] + other_molecule['radius']:
                    mass_sum = molecule['mass'] + other_molecule['mass']
                    dx_normalized = dx / distance
                    dy_normalized = dy / distance

                    v1x = molecule['vx']
                    v1y = molecule['vy']

                    v2x = other_molecule['vx']
                    v2y = other_molecule['vy']

                    u1 = v1x * dx_normalized + v1y * dy_normalized
                    u2 = v2x * dx_normalized + v2y * dy_normalized

                    v1 = ((molecule['mass'] - other_molecule['mass']) * u1 + 2 * other_molecule['mass'] * u2) / mass_sum
                    v2 = ((other_molecule['mass'] - molecule['mass']) * u2 + 2 * molecule['mass'] * u1) / mass_sum

                    molecule['vx'] += (v1 - u1) * dx_normalized
                    molecule['vy'] += (v1 - u1) * dy_normalized
                    other_molecule['vx'] += (v2 - u2) * dx_normalized
                    other_molecule['vy'] += (v2 - u2) * dy_normalized

            molecule['x'] += random.uniform(-0.5, 0.5)
            molecule['y'] += random.uniform(-0.5, 0.5)

        self.view.viewport().update()

    def stopProgram(self):
        self.timer.stop() 

if __name__ == '__main__':
    app = QApplication(sys.argv)
    window = GasMoleculeWindow()
    window.show()
    app.exec_()

按下Ui中的Addmolecule按钮时,分子应随机显示在Ui上。然而,它不起作用。我需要帮助...没有错误显示在终端上(使用Visual studio)但我无法在UI上看到分子。

6rqinv9w

6rqinv9w1#

QGraphicsView示例self.view被创建,但从未被设置为主窗口的中心小部件。
让我们将QGraphicsView设置为QMainWindow的中心小部件。

class GasMoleculeWindow(QMainWindow, form_ui):
    def __init__(self):
        super().__init__()
        self.setupUi(self)
         
        self.setWindowTitle("Gas Molecule Simulation")
        self.setGeometry(100, 100, 800, 600)

        self.molecules = []
        self.temperature = 1.0

        self.addMoleculeButton.clicked.connect(self.addMolecule)
        self.stopSimulation.clicked.connect(self.stopProgram)
        self.massSlider.setRange(1,10)
        self.massSlider.valueChanged.connect(self.updateMass)
        self.radiusSlider.valueChanged.connect(self.updateRadius)
        self.temperatureSlider.valueChanged.connect(self.updateTemperature)

        self.massLabel.setAlignment(Qt.AlignCenter)
        self.radiusLabel.setAlignment(Qt.AlignCenter)
        self.temperatureLabel.setAlignment(Qt.AlignCenter)

        self.scene = QGraphicsScene(self)
        self.view = QGraphicsView(self.scene)
        self.setCentralWidget(self.view)  # Set the QGraphicsView to be the central widget

        self.timer = self.startTimer(10)

相关问题