📄 mixgtk_mixvm.c
字号:
/* -*-c-*- -------------- mixgtk_mixvm.c : * Implementation of the functions declared in mixgtk_mixvm.h * ------------------------------------------------------------------ * Last change: Time-stamp: "2001-05-19 16:39:16 jao" * ------------------------------------------------------------------ * Copyright (C) 2001 Free Software Foundation, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * */#include <stdlib.h>#include <mixlib/xmix_vm.h>#include "mixgtk_widgets.h"#include "mixgtk_mixvm.h"#include "mixgtk_cmd_dispatcher.h"#include "mixgtk_input.h"/* register widgets */#define REGISTER_NO_ (MIXGTK_WIDGET_rI6 - MIXGTK_WIDGET_rA + 1)static GtkEntry *reg_entries_[REGISTER_NO_];static GtkTooltips *tips_ = NULL;static GtkEntry *loc_entry_;static GtkWidget *goto_ = NULL;static GtkEntry *goto_entry_ = NULL;static GtkToggleButton *over_button_;static GtkToggleButton *cmp_buttons_[3];static GtkCList *memory_;static GtkLabel *laptime_;static GtkLabel *progtime_;static GtkLabel *uptime_;static mix_vm_t *vm_;#define GOTO_ENTRY_NAME_ "goto_entry"static voidinit_goto_ (void){ goto_ = mixgtk_widget_factory_get_dialog (MIXGTK_GOTO_DIALOG); g_assert (goto_ != NULL); goto_entry_ = GTK_ENTRY (mixgtk_widget_factory_get_child_by_name ( MIXGTK_GOTO_DIALOG, GOTO_ENTRY_NAME_)); g_assert (goto_entry_ != NULL);}static voidupdate_register_ (mixgtk_widget_id_t reg){ static gchar BUFFER[20]; mix_word_t tipval = MIX_WORD_ZERO; switch (reg) { case MIXGTK_WIDGET_rA: tipval = mix_vm_get_rA (vm_); mix_word_print_to_buffer (tipval, BUFFER); break; case MIXGTK_WIDGET_rX: tipval = mix_vm_get_rX (vm_); mix_word_print_to_buffer (tipval, BUFFER); break; case MIXGTK_WIDGET_rJ: tipval = mix_short_to_word_fast (mix_vm_get_rJ (vm_)); mix_short_print_to_buffer (mix_vm_get_rJ (vm_), BUFFER); break; case MIXGTK_WIDGET_rI1: case MIXGTK_WIDGET_rI2: case MIXGTK_WIDGET_rI3: case MIXGTK_WIDGET_rI4: case MIXGTK_WIDGET_rI5: case MIXGTK_WIDGET_rI6: { gint k = reg - MIXGTK_WIDGET_rI1 + 1; tipval = mix_short_to_word_fast (mix_vm_get_rI (vm_, k)); mix_short_print_to_buffer (mix_vm_get_rI (vm_, k), BUFFER); } break; default: g_assert_not_reached (); } gtk_entry_set_text (reg_entries_[reg - MIXGTK_WIDGET_rA], BUFFER); snprintf (BUFFER, 20, "%s%ld", mix_word_is_negative (tipval)? "-" : "", mix_word_magnitude (tipval)); gtk_tooltips_set_tip (tips_, GTK_WIDGET (reg_entries_[reg - MIXGTK_WIDGET_rA]), BUFFER, NULL);}static voidon_mem_adj_change_ (GtkAdjustment *adj){ mixgtk_mixvm_update_cells ();}/* initialise the mixvm widgets */gbooleanmixgtk_mixvm_init (mix_vm_t *vm, mixgtk_dialog_id_t top){ int k; gchar *text[] = {"", ""}; GtkWidget *scrol; GtkAdjustment *adj; g_return_val_if_fail (vm != NULL, FALSE); vm_ = vm; if (!tips_) tips_ = gtk_tooltips_new (); for (k = 0; k < REGISTER_NO_; ++k) { reg_entries_[k] = GTK_ENTRY (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_rA + k)); g_return_val_if_fail (reg_entries_[k] != NULL, FALSE); } loc_entry_ = GTK_ENTRY (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_LOC)); g_return_val_if_fail (loc_entry_ != NULL, FALSE); uptime_ = GTK_LABEL (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_UPTIME)); g_return_val_if_fail (uptime_ != NULL, FALSE); progtime_ = GTK_LABEL (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_PROGTIME)); g_return_val_if_fail (progtime_ != NULL, FALSE); laptime_ = GTK_LABEL (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_LAPTIME)); g_return_val_if_fail (laptime_ != NULL, FALSE); over_button_ = GTK_TOGGLE_BUTTON (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_OVER)); g_return_val_if_fail (over_button_ != NULL, FALSE); for (k = 0; k < 3; ++k) { cmp_buttons_[k] = GTK_TOGGLE_BUTTON (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_CMP_L +k)); g_return_val_if_fail (cmp_buttons_[k] != NULL, FALSE); } memory_ = GTK_CLIST (mixgtk_widget_factory_get (top, MIXGTK_WIDGET_CELLS)); g_return_val_if_fail (memory_ != NULL, FALSE); gtk_clist_set_column_justification (memory_, 0, GTK_JUSTIFY_CENTER); gtk_clist_set_column_justification (memory_, 1, GTK_JUSTIFY_CENTER); gtk_clist_freeze (memory_); for (k = 0; k< MIX_VM_CELL_NO; ++k) { gchar buffer[20]; sprintf (buffer, "%04d", k); text[0] = buffer; gtk_clist_append (memory_, text); } gtk_clist_thaw (memory_); scrol = mixgtk_widget_factory_get (top, MIXGTK_WIDGET_CELLS_SCROLL); g_return_val_if_fail (scrol != NULL, FALSE); adj = gtk_scrolled_window_get_vadjustment (GTK_SCROLLED_WINDOW (scrol)); gtk_signal_connect (GTK_OBJECT (adj), "value_changed", GTK_SIGNAL_FUNC (on_mem_adj_change_), NULL); goto_ = NULL; return TRUE;}/* update register widgets */voidmixgtk_mixvm_update_registers (void){ gint k; for (k = MIXGTK_WIDGET_rA; k <= MIXGTK_WIDGET_rI6; ++k) update_register_ (k);}/* update the overflow toggle */voidmixgtk_mixvm_update_over_toggle (void){ g_assert (over_button_); gtk_toggle_button_set_active (over_button_, mix_vm_get_overflow (vm_));}/* update the comparison flag */voidmixgtk_mixvm_update_cmp (void){ gint toggle; g_assert (cmp_buttons_); toggle = mix_vm_get_cmpflag (vm_); gtk_toggle_button_set_active (cmp_buttons_[toggle], TRUE);}/* update the memory cells */voidmixgtk_mixvm_update_cells (void){ static gchar BUFFER[20]; gint k = 0; g_assert (memory_); gtk_clist_freeze (memory_); while (gtk_clist_row_is_visible (memory_, k) == GTK_VISIBILITY_NONE) ++k; while (gtk_clist_row_is_visible (memory_, k) != GTK_VISIBILITY_NONE) { mix_word_print_to_buffer (mix_vm_get_addr_contents (vm_, k), BUFFER); gtk_clist_set_text (memory_, k, 1, BUFFER); ++k; } gtk_clist_thaw (memory_);}voidmixgtk_mixvm_update_cells_to_address (gint address){ g_assert (memory_); if (address >= MIX_VM_CELL_NO) return; gtk_clist_freeze (memory_); gtk_clist_moveto (memory_, address, 0, 0, 0); gtk_clist_thaw (memory_); mixgtk_mixvm_update_cells ();}/* update the loc pointer */voidmixgtk_mixvm_update_loc (void){ enum {SIZE = 10 }; static gchar BUFFER[SIZE]; mix_short_t locval; g_assert (loc_entry_); locval = mix_vm_get_prog_count (vm_); snprintf (BUFFER, SIZE, "%04d", mix_short_magnitude (locval)); gtk_entry_set_text (loc_entry_, BUFFER);}/* update times */voidmixgtk_mixvm_update_times (void){ enum {SIZE = 20 }; static gchar BUFFER[SIZE]; gint uptime, progtime, laptime; g_assert (uptime_ && progtime_ && laptime_); mixgtk_cmd_dispatcher_get_times (&uptime, &progtime, &laptime); snprintf (BUFFER, SIZE, "%d", uptime); gtk_label_set_text (uptime_, BUFFER); snprintf (BUFFER, SIZE, "%d", progtime); gtk_label_set_text (progtime_, BUFFER); snprintf (BUFFER, SIZE, "%d", laptime); gtk_label_set_text (laptime_, BUFFER);}/* update all mixvm widgets */voidmixgtk_mixvm_update_vm_widgets (void){ mixgtk_mixvm_update_registers (); mixgtk_mixvm_update_loc (); mixgtk_mixvm_update_over_toggle (); mixgtk_mixvm_update_cmp (); mixgtk_mixvm_update_cells (); mixgtk_mixvm_update_times ();}/* update cmp flag */voidon_cmp_e_toggled (GtkWidget *widget, gpointer data){ if (GTK_TOGGLE_BUTTON (widget)->active) mix_vm_set_cmpflag (vm_, mix_EQ);}voidon_cmp_l_toggled (GtkWidget *widget, gpointer data){ if (GTK_TOGGLE_BUTTON (widget)->active) mix_vm_set_cmpflag (vm_, mix_LESS);}voidon_cmp_g_toggled (GtkWidget *widget, gpointer data){ if (GTK_TOGGLE_BUTTON (widget)->active) mix_vm_set_cmpflag (vm_, mix_GREAT);}voidon_overflow_toggled (GtkWidget *widget, gpointer data){ mix_vm_set_overflow (vm_, GTK_TOGGLE_BUTTON (widget)->active);}voidon_loc_arrow_clicked (GtkWidget *widget, gpointer data) { gint address = mix_short_magnitude (mix_vm_get_prog_count (vm_)); mixgtk_mixvm_update_cells_to_address (address);}static voidregister_AX_ (mix_word_t w, gpointer reg){ gint k = GPOINTER_TO_INT (reg); if (k == 0) mix_vm_set_rA (vm_, w); else mix_vm_set_rX (vm_, w); update_register_ (MIXGTK_WIDGET_rA + k);}static voidregister_j_ (mix_word_t w, gpointer data){ if (mix_word_is_negative (w)) mix_word_reverse_sign (w); mix_vm_set_rJ (vm_, mix_word_to_short_fast (w)); update_register_ (MIXGTK_WIDGET_rJ);}static voidregister_i_ (mix_word_t w, gpointer reg){ mix_vm_set_rI (vm_, GPOINTER_TO_INT (reg), mix_word_to_short_fast (w)); update_register_ (MIXGTK_WIDGET_rI1 - 1 + GPOINTER_TO_INT (reg));}gbooleanon_register_click (GtkWidget *w, GdkEvent *e, gpointer data){ enum {SIZE = 20}; static gchar BUFFER[SIZE]; gint k; if (w == GTK_WIDGET (reg_entries_[0])) mixgtk_input_word ("Register A", mix_vm_get_rA (vm_), register_AX_, GINT_TO_POINTER (0)); else if (w == GTK_WIDGET (reg_entries_[1])) mixgtk_input_word ("Register X", mix_vm_get_rX (vm_), register_AX_, GINT_TO_POINTER(1)); else if (w == GTK_WIDGET (reg_entries_[2])) mixgtk_input_short ("Register J", mix_vm_get_rJ (vm_), register_j_, NULL); else for (k = 1; k < 7; ++k) { if (w == GTK_WIDGET (reg_entries_[2 + k])) { snprintf (BUFFER, SIZE, "Register I%d", k); mixgtk_input_short (BUFFER, mix_vm_get_rI (vm_, k), register_i_, GINT_TO_POINTER (k)); break; } } return FALSE;}static voidmem_cell_ (mix_word_t w, gpointer a){ mix_short_t addr = mix_short_new (GPOINTER_TO_INT (a)); mix_vm_set_addr_contents (vm_, addr, w); mixgtk_mixvm_update_cells ();}voidon_memory_cells_select_row (GtkCList *w, gint row, gint col, GdkEvent *e, gpointer data){ enum {SIZE = 30}; static gchar BUFFER[SIZE]; snprintf (BUFFER, SIZE, "Memory cell no. %d", row); mixgtk_input_word (BUFFER, mix_vm_get_addr_contents (vm_, mix_short_new (row)), mem_cell_, GINT_TO_POINTER (row));}voidon_memory_cells_click_column (GtkCList *w, gint row, gpointer data){ if (!goto_) init_goto_ (); gtk_widget_show (goto_);}voidon_goto_cancel_clicked (GtkWidget *w, gpointer data){ gtk_widget_hide (goto_);}voidon_goto_ok_clicked (GtkWidget *w, gpointer data){ gchar *txt = gtk_entry_get_text (goto_entry_); mix_short_t addr = mix_short_new (atoi (txt)); if (addr < MIX_VM_CELL_NO) { gtk_widget_hide (goto_); mixgtk_mixvm_update_cells_to_address (addr); }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -