def submit(self): """ This function gets called after clicking on the submit button """ myLogger.message("New system submitted...") try: xtxt = str(self.xDotLineEdit.text()) ytxt = str(self.yDotLineEdit.text()) except UnicodeEncodeError as exc: myLogger.warn_message("UnicodeEncodeError! Please check input.") myLogger.debug_message(str(exc)) else: cond1 = str(self.xDotLineEdit.text()) != "" cond2 = str(self.yDotLineEdit.text()) != "" if cond1 and cond2: x_string = str(self.xDotLineEdit.text()) y_string = str(self.yDotLineEdit.text()) try: # Non-modal (!) Box intended for calming down the user... info_box = QtWidgets.QMessageBox(self) info_box.setAttribute(Qt.WA_DeleteOnClose) info_box.setStandardButtons(QtWidgets.QMessageBox.Ok) info_box.setIcon(QtWidgets.QMessageBox.Information) info_box.setWindowTitle("New system submitted") info_box.setText( "The new system is being processed now, please wait! \n" "Especially when LaTeX is used for the labels this may take some time and the " "program might seem unresponsive!") info_box.setModal(False) info_box.show() QtCore.QCoreApplication.processEvents() # Processing equations equation = (x_string, y_string) system = System(self, equation) self.systems.insert(0, system) self.save_tmp_system() myLogger.message("------ new system created ------") myLogger.message( " x' = " + str(system.equation.what_is_my_system()[0])) myLogger.message( " y' = " + str(system.equation.what_is_my_system()[1]) + "\n", ) try: info_box.close() except RuntimeError: # if dialog has already been closed by the user pass except BaseException as exc: QtWidgets.QMessageBox.critical( self, "Error!", "An error occured while processing the system. " "Detailed error message: \n %s" % exc) myLogger.error_message(str(exc)) else: myLogger.error_message("Please check system!")
def submit(self): """ This function gets called after clicking on the submit button """ try: xtxt = str(self.xDotLineEdit.text()) ytxt = str(self.yDotLineEdit.text()) except UnicodeEncodeError as exc: myLogger.warn_message("UnicodeEncodeError! Please check input.") myLogger.debug_message(str(exc)) else: cond1 = str(self.xDotLineEdit.text()) != "" cond2 = str(self.yDotLineEdit.text()) != "" if cond1 and cond2: x_string = str(self.xDotLineEdit.text()) y_string = str(self.yDotLineEdit.text()) equation = (x_string, y_string) system = System(self, equation) self.systems.insert(0, system) self.save_tmp_system() myLogger.message("------ new system created ------") myLogger.message(" x' = " + str(system.equation.what_is_my_system()[0])) myLogger.message( " y' = " + str(system.equation.what_is_my_system()[1]) + "\n", ) else: myLogger.error_message("Please check system!")
def submit(self): """ This function gets called after clicking on the submit button """ try: xtxt = str(self.xDotLineEdit.text()) ytxt = str(self.yDotLineEdit.text()) except UnicodeEncodeError as exc: myLogger.warn_message("UnicodeEncodeError! Please check input.") myLogger.debug_message(str(exc)) else: cond1 = str(self.xDotLineEdit.text()) != "" cond2 = str(self.yDotLineEdit.text()) != "" if cond1 and cond2: x_string = str(self.xDotLineEdit.text()) y_string = str(self.yDotLineEdit.text()) equation = (x_string, y_string) system = System(self, equation) self.systems.insert(0, system) self.save_tmp_system() myLogger.message("------ new system created ------") myLogger.message(" x' = " + str(system.equation.what_is_my_system()[0])) myLogger.message(" y' = " + str(system.equation.what_is_my_system()[1]) + "\n", ) else: myLogger.error_message("Please check system!")
def save_tmp_system(self): if len(self.systems) > 0: index = self.tabWidget.currentIndex() system = self.systems[index] file_name = 'library/tmp.ppf' self.save_system(file_name, system.equation.what_is_my_system()) else: myLogger.error_message("There is no system to save!")
def handle_exception(error): myLogger.error_message("Error: An Python Exception occured.") myLogger.debug_message(str(type(error))) myLogger.debug_message(str(error)) myLogger.message("See the log file config/logmessages.txt for full traceback ") exc_type, exc_value, exc_tb = sys.exc_info() lines = traceback.format_exception(exc_type, exc_value, exc_tb) tb_msg = "".join(lines) myLogger.append_to_file(tb_msg)
def save_file(self): if len(self.systems) > 0: index = self.tabWidget.currentIndex() system = self.systems[index] file_name, file_type = QtWidgets.QFileDialog.getSaveFileName( self, "Save pyplane file", "", "pyplane file (*.ppf)") # sys_pickleds = system.pickle(file_name) # system.equation.what_is_my_system() self.save_system(file_name, system.equation.what_is_my_system()) else: myLogger.error_message("There is no system to save!")
def set_window_range(self, Graph): """ This function changes the window range of Graph. """ # TODO: check if there is a better way to do this? --> put lineedit stuff in PyplaneMainWindow or MainApp! try: # phase plane flag pp_flag = False if Graph == self.plot_pp: xmin = float(self.parent.PP_xminLineEdit.text()) xmax = float(self.parent.PP_xmaxLineEdit.text()) ymin = float(self.parent.PP_yminLineEdit.text()) ymax = float(self.parent.PP_ymaxLineEdit.text()) # set flag pp_flag = True elif Graph == self.plot_x: xmin = float(self.parent.X_tminLineEdit.text()) xmax = float(self.parent.X_tmaxLineEdit.text()) ymin = float(self.parent.X_xminLineEdit.text()) ymax = float(self.parent.X_xmaxLineEdit.text()) # elif Graph == self.plot_y: else: xmin = float(self.parent.Y_tminLineEdit.text()) xmax = float(self.parent.Y_tmaxLineEdit.text()) ymin = float(self.parent.Y_yminLineEdit.text()) ymax = float(self.parent.Y_ymaxLineEdit.text()) if xmin < xmax and ymin < ymax: Graph.axes.set_xlim(xmin, xmax) Graph.axes.set_ylim(ymin, ymax) if pp_flag: # self.update_graph(Graph) myVectorfield.update() myStreamlines.update() #self.update_vectorfield() #self.update_streamlines() myNullclines.update() else: myLogger.error_message("Please check window size input!") except Exception as error: myLogger.error_message("Error!") myLogger.debug_message(str(type(error))) myLogger.debug_message(str(error)) # update_all graph self.update_graph(Graph)
def handle_exception(error): myLogger.error_message("Error: An Python Exception occured.") myLogger.debug_message(str(type(error))) myLogger.debug_message(str(error)) myLogger.message( "See the log file config/logmessages.txt for full traceback ") exc_type, exc_value, exc_tb = sys.exc_info() lines = traceback.format_exception(exc_type, exc_value, exc_tb) tb_msg = "".join(lines) myLogger.append_to_file(tb_msg)
def submit(self): """ This function gets called after clicking on the submit button """ try: xtxt = str(self.xDotLineEdit.text()) ytxt = str(self.yDotLineEdit.text()) except UnicodeEncodeError as exc: myLogger.warn_message("UnicodeEncodeError! Please check input.") myLogger.debug_message(str(exc)) else: cond1 = str(self.xDotLineEdit.text()) != "" cond2 = str(self.yDotLineEdit.text()) != "" if cond1 and cond2: # set right hand side, print rhs to logfield, solve, # then plot vector field # initialize system mySystem.__init__() # set rhs x_string = str(self.xDotLineEdit.text()) y_string = str(self.yDotLineEdit.text()) mySystem.set_rhs(x_string, y_string) try: # write to tmp file: self.save_system('library/tmp.ppf') # clear figure, if there is any self.myGraph.clear() # delete linearization tabs (index 3 to n) if len(self.linearization_stack) > 0: for i in xrange(0, len(self.linearization_stack)): index = 3 + len(self.linearization_stack) - i self.tabWidget.removeTab(index) #reset stack self.linearization_stack = [] myLogger.debug_message("All linearization tabs removed.") self.initializing() myLogger.message("------ new system created ------") myLogger.message(" x' = " + str(mySystem.what_is_my_system()[0])) myLogger.message(" y' = " + str(mySystem.what_is_my_system()[1]) + "\n", ) except Exception as error: handle_exception(error) else: myLogger.error_message("No system entered")
def save_file(self): if len(self.systems) > 0: index = self.tabWidget.currentIndex() system = self.systems[index] file_name, filter = QtGui.QFileDialog.getSaveFileNameAndFilter( self, 'Save pyplane file', '', 'pyplane file (*.ppf)') #~ sys_pickleds = system.pickle(file_name) #~ system.equation.what_is_my_system() self.save_system(file_name, system.equation.what_is_my_system()) else: myLogger.error_message("There is no system to save!")
def save_file(self): if len(self.systems) > 0: index = self.tabWidget.currentIndex() system = self.systems[index] file_name, file_type = QtWidgets.QFileDialog.getSaveFileName(self, "Save pyplane file", "", "pyplane file (*.ppf)") # sys_pickleds = system.pickle(file_name) # system.equation.what_is_my_system() self.save_system(file_name, system.equation.what_is_my_system()) else: myLogger.error_message("There is no system to save!")
def submit(self): """ This function gets called after clicking on the submit button """ myLogger.message("New system submitted...") try: xtxt = str(self.xDotLineEdit.text()) ytxt = str(self.yDotLineEdit.text()) except UnicodeEncodeError as exc: myLogger.warn_message("UnicodeEncodeError! Please check input.") myLogger.debug_message(str(exc)) else: cond1 = str(self.xDotLineEdit.text()) != "" cond2 = str(self.yDotLineEdit.text()) != "" if cond1 and cond2: x_string = str(self.xDotLineEdit.text()) y_string = str(self.yDotLineEdit.text()) try: # Non-modal (!) Box intended for calming down the user... info_box = QtWidgets.QMessageBox(self) info_box.setAttribute(Qt.WA_DeleteOnClose) info_box.setStandardButtons(QtWidgets.QMessageBox.Ok) info_box.setIcon(QtWidgets.QMessageBox.Information) info_box.setWindowTitle("New system submitted") info_box.setText("The new system is being processed now, please wait! \n" "Especially when LaTeX is used for the labels this may take some time and the " "program might seem unresponsive!") info_box.setModal(False) info_box.show() QtCore.QCoreApplication.processEvents() # Processing equations equation = (x_string, y_string) system = System(self, equation) self.systems.insert(0, system) self.save_tmp_system() myLogger.message("------ new system created ------") myLogger.message(" x' = " + str(system.equation.what_is_my_system()[0])) myLogger.message(" y' = " + str(system.equation.what_is_my_system()[1]) + "\n", ) try: info_box.close() except RuntimeError: # if dialog has already been closed by the user pass except BaseException as exc: QtWidgets.QMessageBox.critical(self, "Error!", "An error occured while processing the system. " "Detailed error message: \n %s" % exc) myLogger.error_message(str(exc)) else: myLogger.error_message("Please check system!")
def save_file(self): if len(self.systems) > 0: index = self.tabWidget.currentIndex() system = self.systems[index] file_name, filter = QtGui.QFileDialog.getSaveFileNameAndFilter(self, 'Save pyplane file', '', 'pyplane file (*.ppf)') #~ sys_pickleds = system.pickle(file_name) #~ system.equation.what_is_my_system() self.save_system(file_name, system.equation.what_is_my_system()) else: myLogger.error_message("There is no system to save!")
def onclick(self, event): """ This function is in charge of the mouse-click behaviour. A left mouse button click is recognized, the mouse location serves as an initial condition for trajectories. """ #TODO: check if try/except is the best thing to do here! if not self.plot_pp.zoomMode: try: mySystem except: # only capture mouse click if system exists myLogger.error_message("Please enter system.") else: cond1 = mySystem.x_dot is not None cond2 = mySystem.x_dot is not None cond3 = str(self.parent.xDotLineEdit.text()) != "" cond4 = str(self.parent.yDotLineEdit.text()) != "" if cond1 and cond2 and cond3 and cond4: event1 = event.xdata is not None event2 = event.ydata is not None button = event.button == 1 if not myEquilibria.eqp_toggle: # event.xdata and event.ydata are initial conditions for integration # mouse click will also be recognized if clicked outside of the graph area, so filter that: if event1 and event2 and button: forward, backward = self.trajectory_direction() if myTrajectories.plot_trajectory( [event.xdata, event.ydata], forward, backward): myLogger.message("New initial condition: " + str(event.xdata) + ", " + str(event.ydata)) else: pass else: # equilibrium point if event1 and event2 and button: equilibrium_point = myEquilibria.find_equilibrium( [event.xdata, event.ydata]) if equilibrium_point is not None: self.parent.add_linearization_tab( equilibrium_point) else: # only capture mouse click if system exists myLogger.error_message("Please enter system.") else: myLogger.debug_message("in zoom mode")
def set_window_range(self): _min = float(self.myWidget.xminLineEdit.text()) _max = float(self.myWidget.xmaxLineEdit.text()) _tmin = float(self.myWidget.yminLineEdit.text()) _tmax = float(self.myWidget.ymaxLineEdit.text()) if _min < _max and _tmin < _tmax: self.canvas.axes.set_xlim(_min, _max) self.canvas.axes.set_ylim(_tmin, _tmax) else: myLogger.error_message("Please check window size input!") self.update()
def read(self, section, variable): if self.config.has_option(str(section), str(variable)): value = self.config.get(str(section), str(variable)) # TODO: check if the config value is of same type as fallback value myLogger.debug_message(str(variable) + "\": " + str(value) + " (config)") return value elif str(variable) in self.descr: # fallback value value = self.descr[str(variable)][1] myLogger.debug_message(str(variable) + "\": " + str(value) + " (fallback)") return value else: #pass myLogger.error_message("Error! A variable was called that does not exist.")
def remove_all(self): """ this function removes every trajectory in y(x), x(t) and y(t) """ for i in self.traj_dict: # i is the next key for j in range(0, len(self.traj_dict[i])): # j is a list element from the traj_stack try: self.traj_dict[i].pop()[0].remove() except Exception as error: myLogger.error_message("Could not delete trajectory") myLogger.debug_message(str(type(error))) myLogger.debug_message(str(error)) self.mySystem.update()
def export_as(self): """ export dialog for pyplane plot """ q_files_types = QtCore.QString(".png;;.svg;;.pdf;;.eps") q_file_name, q_file_type = QtGui.QFileDialog.getSaveFileNameAndFilter( self, "Export PyPlane Plot as .png, .svg, .pdf, or .eps-file", "", q_files_types) # Ensure we are out of the QString world in the following file_name = str(q_file_name) file_type = str(q_file_type) if file_name: # Fix: Under some KDE's the file_type is returned empty because # of a "DBUS-error". Hence, in such cases, we try to take the # file_type from the extension specified by the user . If no valid extension # is set by the user file_type is set to png. This bugfix is addressed # in the first part of the "if not" structure. # # In the else part of the "if not" structure the case is handled # where the user wants to have dots in the basename of the file # (affects all operating systems) # file_name2, file_type2 = os.path.splitext(file_name) if not file_type: if file_type2 not in [".png", ".svg", ".pdf", ".eps"]: file_type = ".png" else: # Allow things like figure.case21.pdf file_name = file_name2 file_type = file_type2 else: # This part runs on non KDE-systems or KDE-systems without # the DBUS error: # drop accidently added duplicate file extensions # (avoid figure.png.png but allow figure.case1.png) if file_type2 == file_type: file_name = file_name2 # ------ if file_type == ".png": self.export_as_png(file_name) elif file_type == ".svg": self.export_as_svg(file_name) elif file_type == ".pdf": self.export_as_pdf(file_name) elif file_type == ".eps": self.export_as_eps(file_name) else: myLogger.error_message("Filetype-Error")
def export_as(self): """ export dialog for pyplane plot """ q_files_types = QtCore.QString(".png;;.svg;;.pdf;;.eps") q_file_name, q_file_type = QtGui.QFileDialog.getSaveFileNameAndFilter(self, "Export PyPlane Plot as .png, .svg, .pdf, or .eps-file", "", q_files_types) # Ensure we are out of the QString world in the following file_name = str(q_file_name) file_type = str(q_file_type) if file_name: # Fix: Under some KDE's the file_type is returned empty because # of a "DBUS-error". Hence, in such cases, we try to take the # file_type from the extension specified by the user . If no valid extension # is set by the user file_type is set to png. This bugfix is addressed # in the first part of the "if not" structure. # # In the else part of the "if not" structure the case is handled # where the user wants to have dots in the basename of the file # (affects all operating systems) # file_name2, file_type2 = os.path.splitext(file_name) if not file_type: if file_type2 not in [".png", ".svg", ".pdf", ".eps"]: file_type = ".png" else: # Allow things like figure.case21.pdf file_name = file_name2 file_type = file_type2 else: # This part runs on non KDE-systems or KDE-systems without # the DBUS error: # drop accidently added duplicate file extensions # (avoid figure.png.png but allow figure.case1.png) if file_type2 == file_type: file_name = file_name2 # ------ if file_type == ".png": self.export_as_png(file_name) elif file_type == ".svg": self.export_as_svg(file_name) elif file_type == ".pdf": self.export_as_pdf(file_name) elif file_type == ".eps": self.export_as_eps(file_name) else: myLogger.error_message("Filetype-Error")
def get_boolean(self, section, variable): if self.config.has_option(str(section), str(variable)): value = self.config.getboolean(str(section), str(variable)) myLogger.debug_message(str(variable) + "\": " + str(value) + " (config)") return value elif str(variable) in self.decr: #self.descr.has_key(str(variable)): # fallback value value = self.descr[str(variable)][1] myLogger.debug_message(str(variable) + "\": " + str(value) + " (fallback)") return value else: #pass myLogger.error_message("Error! A variable was called that does not exist.")
def remove_all(self): """ this function removes every trajectory in y(x), x(t) and y(t) """ for i in self.traj_dict: # i is the next key for j in xrange(0, len(self.traj_dict[i])): # j is a list element from the traj_stack try: self.traj_dict[i].pop()[0].remove() except Exception as error: myLogger.error_message("Could not delete trajectory") myLogger.debug_message(str(type(error))) myLogger.debug_message(str(error)) self.mySystem.update()
def onclick(self, event): """ This function is in charge of the mouse-click behaviour. A left mouse button click is recognized, the mouse location serves as an initial condition for trajectories. """ #TODO: check if try/except is the best thing to do here! if not self.plot_pp.zoomMode: try: mySystem except: # only capture mouse click if system exists myLogger.error_message("Please enter system.") else: cond1 = mySystem.x_dot is not None cond2 = mySystem.x_dot is not None cond3 = str(self.parent.xDotLineEdit.text()) != "" cond4 = str(self.parent.yDotLineEdit.text()) != "" if cond1 and cond2 and cond3 and cond4: event1 = event.xdata is not None event2 = event.ydata is not None button = event.button == 1 if not myEquilibria.eqp_toggle: # event.xdata and event.ydata are initial conditions for integration # mouse click will also be recognized if clicked outside of the graph area, so filter that: if event1 and event2 and button: forward, backward = self.trajectory_direction() if myTrajectories.plot_trajectory([event.xdata, event.ydata], forward, backward): myLogger.message("New initial condition: " + str(event.xdata) + ", " + str(event.ydata)) else: pass else: # equilibrium point if event1 and event2 and button: myEquilibria.find_equilibrium([event.xdata, event.ydata]) else: # only capture mouse click if system exists myLogger.error_message("Please enter system.") else: myLogger.debug_message("in zoom mode")
def create_trajectory(self): try: initial_condition = self.mySystem.Phaseplane.read_init() forward, backward = self.mySystem.Phaseplane.trajectory_direction() cond1 = initial_condition[0] is not None cond2 = initial_condition[1] is not None # check if trajectory with initial_condition exists already cond3 = not str(initial_condition) in self.traj_dict if cond1 and cond2 and cond3: self.plot_trajectory(initial_condition, forward, backward) myLogger.message("New initial condition: " + str(initial_condition[0]) + ", " + str(initial_condition[1])) except Exception as error: myLogger.error_message("Could not create trajectory") myLogger.debug_message(str(type(error))) myLogger.debug_message(str(error))
def export_as(self): """ export dialog for pyplane plot """ files_types = "png;;svg;;pdf;;eps" file_name, filter = QtGui.QFileDialog.getSaveFileNameAndFilter(self, 'Export PyPlane Plot', '', files_types) if len(file_name) > 0: if filter == "png": self.export_as_png(file_name) elif filter == "svg": self.export_as_svg(file_name) elif filter == "pdf": self.export_as_pdf(file_name) elif filter == "eps": self.export_as_eps(file_name) else: myLogger.error_message("Filetype-Error")
def add(self): try: fct_string = str(self.mySystem.myPyplane.yLineEdit.text()) except UnicodeEncodeError as exc: myLogger.error_message("input error!") myLogger.debug_message(str(exc)) fct_string = str(self.mySystem.myPyplane.yLineEdit.text()) if fct_string != "": try: self.fct_expr = sp.sympify(fct_string) self.fct = sp.lambdify((self.x, self.y), self.fct_expr, 'numpy') xmin, xmax, ymin, ymax = self.mySystem.Phaseplane.Plot.canvas.axes.axis( ) # plot the function for an x-interval twice as big as the current window deltax = (xmax - xmin) / 2 deltay = (ymax - ymin) / 2 plot_xmin = xmin - deltax plot_xmax = xmax + deltax plot_ymin = ymin - deltay plot_ymax = ymax + deltay pts_in_x = int(myConfig.read("Functions", "fct_gridPointsInX")) pts_in_y = int(myConfig.read("Functions", "fct_gridPointsInY")) fct_color = myConfig.read("Functions", "fct_color") fct_linewidth = float( myConfig.read("Functions", "fct_linewidth")) x = np.arange(plot_xmin, plot_xmax, (xmax - xmin) / pts_in_x) y = np.arange(plot_ymin, plot_ymax, (ymax - ymin) / pts_in_y) X, Y = np.meshgrid(x, y) myfunc = self.fct(X, Y) # TODO: plots like y=1/x have a connection between -inf and +inf that is not actually there! # plot function and put on function-stack new_fct = self.mySystem.Phaseplane.Plot.canvas.axes.contour( X, Y, myfunc, [0], zorder=100, linewidths=fct_linewidth, colors=fct_color) # new_fct = self.myGraph.plot_pp.axes.plot(xvalue, yvalue, label="fct", color="green") self.fct_stack.append(new_fct) self.mySystem.Phaseplane.Plot.update() myLogger.message("function plot: 0 = " + fct_string) except Exception as error: # TODO: use handle_exception for this myLogger.error_message(str(error)) else: myLogger.error_message("Please enter function.")
def add(self): try: fct_string = str(self.mySystem.myPyplane.yLineEdit.text()) except UnicodeEncodeError as exc: myLogger.error_message("input error!") myLogger.debug_message(str(exc)) fct_string = str(self.mySystem.myPyplane.yLineEdit.text()) if fct_string != "": try: self.fct_expr = sp.sympify(fct_string) self.fct = sp.lambdify((self.x, self.y), self.fct_expr, 'numpy') xmin, xmax, ymin, ymax = self.mySystem.Phaseplane.Plot.canvas.axes.axis() # plot the function for an x-interval twice as big as the current window deltax = (xmax - xmin) / 2 deltay = (ymax - ymin) / 2 plot_xmin = xmin - deltax plot_xmax = xmax + deltax plot_ymin = ymin - deltay plot_ymax = ymax + deltay pts_in_x = int(myConfig.read("Functions", "fct_gridPointsInX")) pts_in_y = int(myConfig.read("Functions", "fct_gridPointsInY")) fct_color = myConfig.read("Functions", "fct_color") fct_linewidth = float(myConfig.read("Functions", "fct_linewidth")) x = np.arange(plot_xmin, plot_xmax, (xmax - xmin) / pts_in_x) y = np.arange(plot_ymin, plot_ymax, (ymax - ymin) / pts_in_y) X, Y = np.meshgrid(x, y) myfunc = self.fct(X, Y) # TODO: plots like y=1/x have a connection between -inf and +inf that is not actually there! # plot function and put on function-stack new_fct = self.mySystem.Phaseplane.Plot.canvas.axes.contour(X, Y, myfunc, [0], zorder=100, linewidths=fct_linewidth, colors=fct_color) # new_fct = self.myGraph.plot_pp.axes.plot(xvalue, yvalue, label="fct", color="green") self.fct_stack.append(new_fct) self.mySystem.Phaseplane.Plot.update() myLogger.message("function plot: 0 = " + fct_string) except Exception as error: # TODO: use handle_exception for this myLogger.error_message(str(error)) else: myLogger.error_message("Please enter function.")
def find_equilibrium(self, z_init): """ hopf2.ppf has problems with this algorithm -> TODO: debug!!! """ # TODO: this try-loop is too long! try: if self.tgl: # newton's method to find equilibrium points iterlimit = 50 iter = 0 h = .000001 z_next = z_init functionf = self.myWidget.mySystem.equation.rhs(z_init) # allow for large/small solutions errorlim = np.linalg.norm(functionf, np.inf) * 0.000001 while ((np.linalg.norm(functionf, np.inf) > errorlim) & (iter < iterlimit)): iter = iter + 1 # now we calculate the jacobian jacobian = np.eye(2) for i in range(0, 2): sav = z_next[i] z_next[i] = z_next[i] + h functionfhj = self.myWidget.mySystem.equation.rhs(z_next) jac = (functionfhj - functionf) / h jacobian[0, i] = jac[0] jacobian[1, i] = jac[1] z_next[i] = sav z_next = z_next - np.linalg.solve(jacobian, functionf) functionf = self.myWidget.mySystem.equation.rhs(z_next) if iter > (iterlimit - 1): fLag = [0, 0] else: fLag = [1, 1] # TODO: this for loop is used twice: why not put it in a function? for i in range(0, 2): sav = z_next[i] z_next[i] = z_next[i] + h functionfhj = self.myWidget.mySystem.equation.rhs(z_next) jac = (functionfhj - functionf) / h jacobian[0, i] = jac[0] jacobian[1, i] = jac[1] z_next[i] = sav #TODO: use list instead of array and safe casting z_next = list(z_next) # due to numerical errors, this is not sufficient and # there could be multiple equilibria plotted where # only one should be: # calculate the distance to all existing equilibrium points # if the distance is smaller than a certain value epsilon, it is # assumed that this equilibrium point is already calculated epsilon = 1e-4 if len(self.stack) == 0: self.plot_equilibrium(z_next, jacobian) self.jacobians[str(z_next)] = jacobian return z_next else: # there are equilibria already # if the distance to an existing equilibrium point is less # than epsilon, do not plot if not self.calculated_before(z_next): myLogger.debug_message("Equilibrium Point already there!") else: self.plot_equilibrium(z_next, jacobian) # add to jacobians self.jacobians[str(z_next)] = jacobian return z_next # d_norm = [] # list with distance to equ. pts # # for ep in self.eqp_stack.keys(): # ep = ast.literal_eval(ep) # x_val = z_next[0] - ep[0] # y_val = z_next[1] - ep[1] # # d_norm.append(np.sqrt(x_val ** 2 + y_val ** 2)) # # if any(d < epsilon for d in d_norm): # myLogger.debug_message("Equilibrium Point already there!") # # else: # self.plot_equilibrium(z_next, jacobian) # # add to jacobians # self.jacobians[str(z_next)] = jacobian except Exception as error: myLogger.error_message("Something strange happened while calculating the equilibrium") if myConfig.read("Logging", "log_showDbg"): myLogger.debug_message(error)
def add_function_to_plot(self): """ will plot additional functions and put it on a stack """ self.x = sp.symbols('x') self.y = sp.symbols('y') self.fct = None fct_txt = "" try: fct_txt = str(self.yLineEdit.text()) except UnicodeEncodeError as exc: myLogger.error_message("input error!") myLogger.debug_message(str(exc)) if fct_txt != "": try: self.fct_string = str(self.yLineEdit.text()) self.fct_expr = sp.sympify(self.fct_string) # self.fct = sp.lambdify(self.x,self.fct_expr,'numpy') self.fct = sp.lambdify((self.x, self.y), self.fct_expr, 'numpy') xmin, xmax, ymin, ymax = self.myGraph.get_limits(self.myGraph.plot_pp) # plot the function for an x-interval twice as big as the current window deltax = (xmax - xmin) / 2 deltay = (ymax - ymin) / 2 plot_xmin = xmin - deltax plot_xmax = xmax + deltax plot_ymin = ymin - deltay plot_ymax = ymax + deltay pts_in_x = int(myConfig.read("Functions", "fct_gridPointsInX")) pts_in_y = int(myConfig.read("Functions", "fct_gridPointsInY")) fct_color = myConfig.read("Functions", "fct_color") fct_linewidth = float(myConfig.read("Functions", "fct_linewidth")) x = np.arange(plot_xmin, plot_xmax, (xmax - xmin) / pts_in_x) y = np.arange(plot_ymin, plot_ymax, (ymax - ymin) / pts_in_y) X, Y = np.meshgrid(x, y) # yvalue = self.fct(xvalue) myfunc = self.fct(X, Y) # TODO: plots like y=1/x have a connection between -inf and +inf that is not actually there! # plot function and put on function-stack new_fct = self.myGraph.plot_pp.axes.contour(X, Y, myfunc, [0], zorder=100, linewidths=fct_linewidth, colors=fct_color) # new_fct = self.myGraph.plot_pp.axes.plot(xvalue, yvalue, label="fct", color="green") self.fct_stack.append(new_fct) self.myGraph.update_graph(self.myGraph.plot_pp) myLogger.message("function plot: 0 = " + self.fct_string) except Exception as error: handle_exception(error) else: myLogger.error_message("Please enter function.")
def add_function_to_plot(self): """ will plot additional functions and put it on a stack """ self.x = sp.symbols('x') self.y = sp.symbols('y') self.fct = None try: fct_txt = str(self.yLineEdit.text()) except UnicodeEncodeError as exc: myLogger.error_message("input error!") myLogger.debug_message(str(exc)) if fct_txt != "": try: self.fct_string = str(self.yLineEdit.text()) self.fct_expr = sp.sympify(self.fct_string) # self.fct = sp.lambdify(self.x,self.fct_expr,'numpy') self.fct = sp.lambdify((self.x, self.y), self.fct_expr, 'numpy') xmin, xmax, ymin, ymax = self.myGraph.get_limits( self.myGraph.plot_pp) # plot the function for an x-interval twice as big as the current window deltax = (xmax - xmin) / 2 deltay = (ymax - ymin) / 2 plot_xmin = xmin - deltax plot_xmax = xmax + deltax plot_ymin = ymin - deltay plot_ymax = ymax + deltay pts_in_x = int(myConfig.read("Functions", "fct_gridPointsInX")) pts_in_y = int(myConfig.read("Functions", "fct_gridPointsInY")) fct_color = myConfig.read("Functions", "fct_color") fct_linewidth = float( myConfig.read("Functions", "fct_linewidth")) x = np.arange(plot_xmin, plot_xmax, (xmax - xmin) / pts_in_x) y = np.arange(plot_ymin, plot_ymax, (ymax - ymin) / pts_in_y) X, Y = np.meshgrid(x, y) #yvalue = self.fct(xvalue) myfunc = self.fct(X, Y) # TODO: plots like y=1/x have a connection between -inf and +inf that is not actually there! # plot function and put on function-stack new_fct = self.myGraph.plot_pp.axes.contour( X, Y, myfunc, [0], zorder=100, linewidths=fct_linewidth, colors=fct_color) # new_fct = self.myGraph.plot_pp.axes.plot(xvalue, yvalue, label="fct", color="green") self.fct_stack.append(new_fct) self.myGraph.update_graph(self.myGraph.plot_pp) myLogger.message("function plot: 0 = " + self.fct_string) except Exception as error: handle_exception(error) else: myLogger.error_message("Please enter function.")