当前位置: 首页 > 工具软件 > Hope GTK > 使用案例 >

UBUNTU下利用net-snmp进行GTK编程

阎经武
2023-12-01
编辑页面,代码显示很正常,发布后就乱掉了?
/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 4; tab-width: 4 -*- */
/*
 * main.c
 * Copyright (C) UBUNTU10_32 2011 <luciferstar@>
	 * 
 * MyListView 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 3 of the License, or
 * (at your option) any later version.
	 * 
 * MyListView 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, see <http://www.gnu.org/licenses/>.
 */

#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <config.h>

#include <gtk/gtk.h>
#include <glib.h>

#include <netinet/in.h>
#include <net-snmp/net-snmp-config.h>      /*此处原先是ucd-snmp,因为我的是net-snmp所以 自作主张修改了,下面一个include也是*/
#include <net-snmp/net-snmp-includes.h>
//#include "snmpstuff.h"
/*
 * Standard gettext macros.
 */
#ifdef ENABLE_NLS
#  include <libintl.h>
#  undef _
#  define _(String) dgettext (PACKAGE, String)
#  ifdef gettext_noop
#    define N_(String) gettext_noop (String)
#  else
#    define N_(String) (String)
#  endif
#else
#  define textdomain(String) (String)
#  define gettext(String) (String)
#  define dgettext(Domain,Message) (Message)
#  define dcgettext(Domain,Message,Type) (Message)
#  define bindtextdomain(Domain,Directory) (Domain)
#  define _(String) (String)
#  define N_(String) (String)
#endif

/* For testing propose use the local (not installed) ui file */
/* #define UI_FILE PACKAGE_DATA_DIR"/mylistview/ui/mylistview.ui" */

typedef struct {
	int i;
	const char *name;
	const char *community;
}m_host;

struct host {
	const char *name;
	const char *community;
} hosts[] = {
//	{ "192.168.0.21", "public" },
//	{ "192.168.0.21", "public" },
//	{ "192.168.0.21", "public" },
	{ NULL }
};


/* a list of variables to query for*/
//Oid结构
struct oid {
	const char *Name;
	oid Oid[MAX_OID_LEN];
	int OidLen;
}oids[] = {
	{ "system.sysDescr.0" },
	{ "ip.ipForwarding.0" },
	{ "ip.ipOutRequests.0" },
	{ NULL }
};

enum{
	col_ip = 0,
	col_comm,
	col_memo,
	n_cols
};

GtkWidget		*view;//列表视图
GtkTreeModel	*store;//列表模型,可转换成GtkTreeStore
GtkCellRenderer *renderer;//单元格渲染
GtkStatusbar	*statusbar,*statusbar_child;//状态栏
GtkWidget		*ip,*comm,*memo;//三个entry
GtkWidget		*child_window;//主窗口

GtkTextView		*test1,*test2,*test3,*test4,*test5,*test6;


static GArray *garray=NULL;



gint host_size=sizeof(hosts);

///
gint list_collect_to_struct()
{
	GtkTreeIter iter;//定义一个迭代器
	//GtkTreeModel *pmodel;
	//char* pitem;
	//pmodel=gtk_tree_view_get_model((GtkTreeView*)store);//得到TREEVIEW的model
	gtk_tree_model_get_iter_first(store,&iter);//迭代器定位到第一行
	int columns=gtk_tree_model_get_n_columns(store);//获取行数

	//获取列名

	columns=2;
	garray=g_array_new(FALSE,FALSE,sizeof(m_host));
			m_host m_hosts;

	gint count=0;
	
	while(gtk_tree_model_iter_next(store,&iter))//开始遍历内容
	{
	//	int i=0;
	//	for(i=0;i<columns;i++)
	//	{
	//	m_hosts.i=1;
		char *name,*comm;
		gtk_tree_model_get (GTK_TREE_MODEL(store),&iter, 0, &name, -1);
		gtk_tree_model_get (GTK_TREE_MODEL(store),&iter, 1, &comm, -1);
		m_hosts.name=name;
		m_hosts.community=comm;
			//gtk_tree_model_get (GTK_TREE_MODEL(store),&iter,    i,        &pitem,   -1);//将指定单元格的值传给pitem
			//printf("%s",pitem);
		//g_printf("%s\t%s\n",name,comm);
		g_array_append_val(garray,m_hosts);
			
			//try
			//{
			//	cout<<pitem;//输出单元格的值
			//}catch{}
		//}
		count++;
	}


//
//	for(i=0;i<5;i++)
//	{
		//	g_array_append_val(garry,gtk_entry_get_text(gtk_entry_get_buffer ((GtkEntry*)ip)));
	//}
	//int i=0;
	//for(i=0;i<2;i++)
	//{
	//	m_hosts=g_array_index(garray,m_host,i);
	//	g_printf("%s\t%s\n",m_hosts.name,m_hosts.community);
	//}

	return count;

}
///
/*
	 * initialize
	 */
//初始化函数
void initialize (void)
{
	struct oid *op = oids;
	/* Win32: init winsock */
	//SOCK_STARTUP;

	/* initialize library */
	//初始化snmp库
	init_snmp("asynchapp");

	/* parse the oids */
	//根据mibs来parse oids
	while (op->Name) {
		op->OidLen = sizeof(op->Oid)/sizeof(op->Oid[0]);
		if (!snmp_parse_oid (op->Name,op->Oid, (size_t *) &op->OidLen)) {
			snmp_perror("read_objid");
			exit(1);
		}
		op++;//指向oids数组的下一项
	}
}





/* simple printing of returned data*/
//打印返回结果,这部分不是很重要,编写处理函数时候可以参考
int print_result (int status, struct snmp_session *sp, struct snmp_pdu *pdu)
{
	char buf[1024];
	struct variable_list *vp;
	int ix;
	struct timeval now;
	struct timezone tz;
	struct tm *tm;

	gettimeofday(&now, &tz);
	tm = localtime(&now.tv_sec);
	fprintf(stdout, "%.2d:%.2d:%.2d.%.6d ", tm->tm_hour, tm->tm_min, tm->tm_sec, now.tv_usec);
	switch (status) {
		case STAT_SUCCESS:
			vp = pdu->variables;
			if (pdu->errstat == SNMP_ERR_NOERROR) {
				while (vp) {
					snprint_variable(buf, sizeof(buf), vp->name, vp->name_length, vp);
					fprintf(stdout, "%s: %s\n", sp->peername, buf);
					vp = vp->next_variable;
				}
			}
			else {
				for (ix = 1; vp && ix != pdu->errindex; vp = vp->next_variable, ix++)
					;
				if (vp) snprint_objid(buf, sizeof(buf), vp->name, vp->name_length);
				else strcpy(buf, "(none)");
				fprintf(stdout, "%s: %s: %s\n",
				        sp->peername, buf, snmp_errstring(pdu->errstat));
			}
			return 1;
		case STAT_TIMEOUT:
			fprintf(stdout, "%s: Timeout\n", sp->peername);
			return 0;
		case STAT_ERROR:
			snmp_perror(sp->peername);
			return 0;
	}
	return 0;
}

/*
 * poll all hosts in parallel
 */
struct session {
	struct snmp_session *sess; /* SNMP session data */
	struct oid *current_oid; /* How far in our poll are we */
} sessions[sizeof(hosts)/sizeof(hosts[0])];//数量跟host一样多
//active_hosts在asynch_response中减少,在asynchronous中增加
int active_hosts; /* hosts that we have not completed */

/*
 * response handler
 */
int asynch_response(int operation, struct snmp_session *sp, int reqid,
                    struct snmp_pdu *pdu, void *magic)
{
	struct session *host = (struct session *)magic;
	struct snmp_pdu *req;

	if (operation == NETSNMP_CALLBACK_OP_RECEIVED_MESSAGE) {
		if (print_result(STAT_SUCCESS, host->sess, pdu)) {
			//每个host对应了3个oid,对每个都要发送包
			//asynchronous发送第一个包,这里对其他的oid发送包
			host->current_oid++; /* send next GET (if any) */
			//下面的程序跟asynchronous中处理相同
			if (host->current_oid->Name) {
				req = snmp_pdu_create(SNMP_MSG_GET);
				snmp_add_null_var(req, host->current_oid->Oid, host->current_oid->OidLen);
				if (snmp_send(host->sess, req))
					return 1;
				else {
					snmp_perror("snmp_send");
					snmp_free_pdu(req);
				}
			}
		}
	}
	else
		print_result(STAT_TIMEOUT, host->sess, pdu);

	/* something went wrong (or end of variables) 
	* this host not active any more
	 */
	active_hosts--;//处理完后,少了一个active host
	return 1;
}

void asynchronous(void)
{
	struct session *hs;
	struct host *hp;

	int i=0;
	/* startup all hosts */

	//for (hs = sessions, hp = hosts; hp->name; hs++, hp++,i++) {
	for (hs = sessions, hp = hosts; i<garray->len; hs++, hp++,i++) {
		struct snmp_pdu *req;
		struct snmp_session sess;
		snmp_sess_init(&sess); //初始化session /* initialize session */
		//设置session的各变量
		sess.version = SNMP_VERSION_2c;
		
		m_host m_hosts=g_array_index(garray,m_host,i);
				
		sess.peername = strdup(m_hosts.name);//strdup(g_array_index(garray,host_size,i)-> name);//strdup(hp->name);//strdup(garray[hp*2]->name);//
		sess.community = strdup(m_hosts.community);//strdup(g_array_index(garray,host_size,i)->community);//strdup(hp->community);//strdup(garray[hp*2+1]->community);
		sess.community_len = strlen((char *)sess.community);
		sess.callback = asynch_response;//设置回调函数 /* default callback */
		sess.callback_magic = hs;//回调函数的magic,传入打开的session
		//初始化和打开后返回的session不同
		if (!(hs->sess = snmp_open(&sess))) {
			snmp_perror("snmp_open");
			continue;
		}
		//设置oid
		hs->current_oid = oids;
		//创建pdu
		req = snmp_pdu_create(SNMP_MSG_GET); /* send the first GET */
		snmp_add_null_var(req, hs->current_oid->Oid, hs->current_oid->OidLen);
		//用异步方式发送包,不处理,等后面专门处理
		if (snmp_send(hs->sess, req))
			active_hosts++;//增加一个活跃的host
		else {
			snmp_perror("snmp_send");
			snmp_free_pdu(req);
		}
	}

	/* loop while any active hosts */

	while (active_hosts) {//只要有活跃的host就一直处理
		int fds = 0, block = 1;
		fd_set fdset;
		struct timeval timeout;

		FD_ZERO(&fdset);//把fd_set清零
		//Select具体应用请参考《unix网络编程》,或者internet高级编程讲义
		//设置select需要的信息
		snmp_select_info(&fds, &fdset, &timeout, &block);
		//多路复用,直接这么用就行了
		fds = select(fds, &fdset, NULL, NULL, block ? NULL : &timeout);
		if (fds < 0) {
			perror("select failed");
			exit(1);
		}
		//fds返回的是等待处理的io数目
		if (fds)
			snmp_read(&fdset);//到这里就会调用callback
		else
			snmp_timeout();
	}

	/* cleanup */
	//都循环完后清除session
	for (hp = hosts, hs = sessions; hp->name; hs++, hp++) {
		if (hs->sess) snmp_close(hs->sess);
	}
}

///



void
snmp_collector()
{
	/*	struct snmp_session session,*ss;
	 struct snmp_pdu *pdu,*response;
	 struct sockaddr_in *pduIP;

	 oid objid_enterprise[]={1,3,6,1,4,1,3,1,1};
oid objid_sysuptime[]={1,3,6,1,2,1,1,3,0};
oid objid_snmptrap[]={1,3,6,1,6,3,1,1,4,1,0};

struct variable_list *vars;
int status;
char *trap=NULL;
int exitval=0;
long sysuptime;
char csysuptime[20];

init_snmp("snmpd");  // 此处原先代码是init_snmp("");引号中不知和配置文件中的什么一致,请指教  

snmp_sess_init(&session);
session.version=SNMP_VERSION_2c;
session.peername="127.0.0.1";
session.community="public";
session.community_len=strlen(session.community);
SOCK_STARTUP;
session.callback=snmp_input;
session.callback_magic=NULL;
session.remote_port=SNMP_TRAP_PORT;

ss=snmp_open(&session);
if(ss==NULL) {
	snmp_sess_perror("snmptrap",&session);
	SOCK_CLEANUP;
	exit(1);
}

pdu=snmp_pdu_create(SNMP_MSG_TRAP2);

sysuptime=get_uptime();
sprintf(csysuptime,"%ld",sysuptime);
trap=csysuptime;
snmp_add_var(pdu,objid_sysuptime,sizeof(objid_sysuptime)/sizeof(oid),'t',trap);
//sysUptime.0
status=snmp_send(ss,pdu)==0;
if(status){
	snmp_sess_perror("snmptrap",ss);
	snmp_free_pdu(pdu);
	exitval=1;
}

snmp_close(ss);
SOCK_CLEANUP;
*/
}

void 
model_data_new(GtkTreeModel* store, const gchar* ip, const gchar* community, const gchar* memo) //列表model初始化
{
	GtkTreeIter iter;
	gtk_list_store_append(GTK_LIST_STORE(store), &iter);
	gtk_list_store_set(GTK_LIST_STORE(store), &iter,
	                   col_ip, ip,
	                   col_comm, community,
	                   col_memo, memo,
	                   -1);
}

GtkTreeModel* create_model()//创建列表model
{
	GtkListStore  *store;
	store = gtk_list_store_new (n_cols,G_TYPE_STRING,G_TYPE_STRING,G_TYPE_STRING);
	return GTK_TREE_MODEL(store);
}

void 
cell_edited_callback (GtkCellRendererText *cell,gchar *path_string,gchar *new_text,gpointer user_data)//列表编辑保存处理
{
	printf("%s_%s\r",path_string,new_text);

	GtkTreeIter iter;
	GtkTreeSelection *selection;
	GtkTreeModel *model;
	// This will only work in single or browse selection mode! 
	selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view));
	if (gtk_tree_selection_get_selected(selection, &model, &iter))
	{
		//	GtkCellRenderer* renderer;    // col 1: name    
		//gtk_list_store_insert_with_values(GTK_LIST_STORE(store),NULL,0,0,"new",1,"new2",2,"new3",-1);
		gtk_tree_model_get_iter_from_string(model,&iter,path_string);

		gint column = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (cell), "column"));

		//gchar *old_text;

		//gtk_tree_model_get (model, &iter, column, &old_text, -1);
		//g_free (old_text);

		gtk_list_store_set (GTK_LIST_STORE(store), &iter, column, new_text, -1);

	}
}

void 
arrange_tree_view(GtkWidget* view) //初始化列数据格式
{
	// col 1: name    
	renderer = gtk_cell_renderer_text_new ();
	g_object_set(renderer, "editable", TRUE, NULL);//可编辑
	g_signal_connect(renderer, "edited", (GCallback) cell_edited_callback, NULL);//编辑响应
	g_object_set_data(G_OBJECT(renderer), "HOST", GUINT_TO_POINTER(0));//列名
	gtk_tree_view_insert_column_with_attributes( GTK_TREE_VIEW(view), -1, "HOST",	   renderer, "text", col_ip, NULL); //列数据格式 
	g_object_set_data (G_OBJECT (renderer), "column", GINT_TO_POINTER (col_ip));//列编辑后列数响应

	renderer = gtk_cell_renderer_text_new ();
	g_signal_connect(renderer, "edited", (GCallback) cell_edited_callback, NULL);
	g_object_set(renderer, "editable", TRUE, NULL);
	g_object_set_data(G_OBJECT(renderer), "COMMUNITY", GUINT_TO_POINTER(1));
	gtk_tree_view_insert_column_with_attributes( GTK_TREE_VIEW(view), -1, "COMMUNITY", renderer, "text", col_comm, NULL);
	g_object_set_data (G_OBJECT (renderer), "column", GINT_TO_POINTER (col_comm));//

	renderer = gtk_cell_renderer_text_new ();
	g_signal_connect(renderer, "edited", (GCallback) cell_edited_callback, NULL);
	g_object_set(renderer, "editable", TRUE, NULL);
	g_object_set_data(G_OBJECT(renderer), "MEMO", GUINT_TO_POINTER(2));
	gtk_tree_view_insert_column_with_attributes( GTK_TREE_VIEW(view), -1, "MEMO",	   renderer, "text", col_memo, NULL);
	g_object_set_data (G_OBJECT (renderer), "column", GINT_TO_POINTER (col_memo));//
}


void 
gtk_button_start_clicked(GtkWidget *view)//开始按钮点击响应
{
	//snmp_collector();
	//snmpwalk("localhost","","public",statusbar);

	/*m_initOid[1]="1.3.6.1.2.1.1.1.0";
	m_initOid[2]="1.3.6.1.2.1.1.2.0";
	m_initOid[3]="1.3.6.1.2.1.1.3.0";
	m_initOid[4]="1.3.6.1.2.1.1.5.0";
	m_initOid[5]="1.3.6.1.2.1.4.3.0";
	m_initOid[6]="1.3.6.1.2.1.4.10.0";

	snmpget("localhost","1.3.6.1.2.1.1.1.0","public",test1 );
	snmpget("localhost","1.3.6.1.2.1.1.2.0","public",test2 );
	snmpget("localhost","1.3.6.1.2.1.1.3.0","public",test3 );
	snmpget("localhost","1.3.6.1.2.1.1.5.0","public",test4 );
	snmpget("localhost","1.3.6.1.2.1.4.3.0","public",test5 );
	snmpget("localhost","1.3.6.1.2.1.4.10.0","public",test6 );
	*/
	if(list_collect_to_struct())
	{
		initialize();
	//printf("---------- asynchronous -----------\n");
		asynchronous();
	}
	else
	{
		//g_statusbar_push(statusbar,"列表不能为空。");
		gtk_statusbar_push(statusbar_child,gtk_statusbar_get_context_id(statusbar_child,"changed"),"列表不能为空。");
	}
}


void 
gtk_button_addwatcher_clicked()//子对话框中add按钮点击响应
{
	//gtk_list_store_insert_with_values(GTK_LIST_STORE(view),NULL,0,0,"new",1,"new2",2,"new3",-1);

	const gchar *ip_text=gtk_entry_get_text((GtkEntry*)ip);
	const gchar *comm_text=gtk_entry_get_text((GtkEntry*)comm);
	const gchar *memo_text=gtk_entry_get_text((GtkEntry*)memo);

	if(strcmp(ip_text,"")==0 || strcmp(comm_text,"")==0 || strcmp(memo_text,"")==0)
	{
		gtk_statusbar_push(statusbar_child,gtk_statusbar_get_context_id(statusbar_child,"changed"),"请输入完整信息");
	}
	else
	{
		gtk_list_store_insert_with_values(GTK_LIST_STORE(store),NULL,0,0,ip_text,1,comm_text,2,memo_text,-1);
		gtk_widget_hide(child_window );
	}
}

void 
gtk_button_cancelwatcher_clicked(GtkWidget *view)//子对话框cancel按钮点击响应
{
	gtk_widget_hide(child_window );
}

void 
gtk_button_add_clicked()//主窗口中add按钮点击响应
{
	gtk_widget_show(child_window);
	gtk_entry_set_text((GtkEntry*)ip,"");
	gtk_entry_set_text((GtkEntry*)comm,"");
	gtk_entry_set_text((GtkEntry*)memo,"");
	gtk_window_set_position((GtkWindow*)child_window,GTK_WIN_POS_CENTER_ALWAYS);
	gtk_statusbar_push(statusbar_child,gtk_statusbar_get_context_id(statusbar_child,"changed"),"请输入相关信息");
}


void 
gtk_button_edit_clicked()//主窗口中edit按钮点击响应
{


}

void 
gtk_button_del_clicked()//主窗口中del按钮点击响应
{
	g_print ("Do deleting!\n");
	GtkTreeSelection *selection;
	GtkTreeModel *model;
	GtkTreeIter iter;
	/* This will only work in single or browse selection mode! */
	selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view));
	if (gtk_tree_selection_get_selected(selection, &model, &iter))
	{
		//gtk_list_store_set (GTK_LIST_STORE(store), &iter, 0, "Foo", -1);
		gtk_list_store_remove(GTK_LIST_STORE(store), &iter);
	}
	else
	{
		//g_print ("no row selected.\n");
		gtk_statusbar_push(statusbar,gtk_statusbar_get_context_id(statusbar,"changed"),"请先选择需要删除的项");
	}
}

void
view_onRowActivated (GtkTreeView *treeview,GtkTreePath *path,GtkTreeViewColumn *col,gpointer userdata)//列表双击响应
{																									  //由于已经设置editable,所以本消息处理已经无效
	GtkTreeModel *model;
	GtkTreeIter iter;
	g_print ("A row has been double-clicked!\n");
	model = gtk_tree_view_get_model(treeview);
	if (gtk_tree_model_get_iter(model, &iter, path))
	{
		gchar *host,*comm,*memo;
		gtk_tree_model_get (model, &iter, 0, &host, -1);
		gtk_tree_model_get (model, &iter, 1, &comm, -1);
		gtk_tree_model_get (model, &iter, 2, &memo, -1);
		g_print ("selected row is: %s\t%s\t%s\n", host,comm,memo);
		g_free(host);
		g_free(comm);
		g_free(memo);
	}
}

void
view_popup_menu_onDoSomething (GtkWidget *menuitem, gpointer userdata)//菜单处理
{
	g_print ("Do something!\n");
	GtkTreeSelection *selection;
	GtkTreeModel *model;
	GtkTreeIter iter;
	/* This will only work in single or browse selection mode! */
	selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(userdata));
	if (gtk_tree_selection_get_selected(selection, &model, &iter))
	{
		//gtk_list_store_set (GTK_LIST_STORE(store), &iter, 0, "Foo", -1);
		gtk_list_store_remove(GTK_LIST_STORE(store), &iter);
	}
	else
	{
		g_print ("no row selected.\n");
	}
}

void
view_popup_menu (GtkWidget *treeview, GdkEventButton *event, gpointer userdata)//菜单弹出处理
{
	GtkWidget *menu, *menuitem;
	menu = gtk_menu_new();
	menuitem = gtk_menu_item_new_with_label("Delete Me!");
	g_signal_connect(menuitem, "activate",(GCallback) view_popup_menu_onDoSomething, treeview);
	gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem);
	gtk_widget_show_all(menu);
	/* Note: event can be NULL here when called from view_onPopupMenu;
	 * gdk_event_get_time() accepts a NULL argument */
	gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL,(event != NULL) ? event->button : 0,gdk_event_get_time((GdkEvent*)event));
}

gboolean
view_onButtonPressed (GtkWidget *treeview, GdkEventButton *event, gpointer userdata)//菜单项点击响应
{
	/* single click with the right mouse button? */
	if (event->type == GDK_BUTTON_PRESS && event->button == 3)
	{
		g_print ("Single right click on the tree view.\n");
		/* optional: select row if no row is selected or only
		 * one other row is selected (will only do something
		                              * if you set a tree selection mode as described later
		 * in the tutorial) */
		if (1)
		{
			GtkTreeSelection *selection;
			selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(treeview));
			/* Note: gtk_tree_selection_count_selected_rows() does not
				* exist in gtk+-2.0, only in gtk+ >= v2.2 ! */
			if (gtk_tree_selection_count_selected_rows(selection) <= 1)
			{
				GtkTreePath *path;
				/* Get tree path for row that was clicked */
				if (gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(treeview),(gint) event->x,(gint) event->y,&path, NULL, NULL, NULL))
				{
					gtk_tree_selection_unselect_all(selection);
					gtk_tree_selection_select_path(selection, path);
					gtk_tree_path_free(path);
				}
			}
		} /* end of optional bit */
		view_popup_menu(treeview, event, userdata);
		return TRUE; /* we handled this */
	}
	return FALSE; /* we did not handle this */
}

gboolean
view_onPopupMenu (GtkWidget *treeview, gpointer userdata)//响应需要菜单弹出的消息
{
	view_popup_menu(treeview, NULL, userdata);
	return TRUE; /* we handled this */
}

gboolean 
My_Timeout_Dealer()//定时器
{
	char data[32];
	time_t ttime;
	struct tm* t;
	time (&ttime);
	t=localtime(&ttime);
	sprintf(data,"%04d-%02d-%02d %02d:%02d:%02d",t->tm_year+1900,t->tm_mon+1,t->tm_mday,t->tm_hour,t->tm_min,t->tm_sec);

	gtk_statusbar_push(statusbar,gtk_statusbar_get_context_id(statusbar,"changed"),data);

	return 1;
}

void hide_child_window()//隐藏子窗口
{
	gtk_widget_hide(child_window);
}

void
create_child_window()//创建子窗口
{
	GtkWidget *vboxx,*vbox,*hbox;//整体框架
	GtkWidget *button_add,*button_cancel;//按钮

	GtkWidget *labelip,*labelcomm,*labelmemo;

	/* This is called in all GTK applications. Arguments are parsed
	 * from the command line and are returned to the application. */

	child_window = gtk_window_new( GTK_WINDOW_TOPLEVEL );
	gtk_window_set_title( GTK_WINDOW( child_window  ), "NEW WATCHER");
	//	gtk_widget_set_sensitive(child_window,FALSE);
	g_signal_connect( G_OBJECT( child_window  ), "delete_event", hide_child_window, NULL);

	vboxx = gtk_vbox_new(FALSE,0);//主容器,垂直排列
	gtk_container_add(GTK_CONTAINER(child_window),vboxx);
	gtk_widget_show(vboxx);

	hbox = gtk_hbox_new (FALSE, 0);//子容器1,水平排列,容纳三个输入entry和三个label
	gtk_container_add (GTK_CONTAINER (vboxx), hbox);
	gtk_widget_show (hbox);

	vbox = gtk_vbox_new (FALSE, 0);//子容器hbox中的容器,垂直排列,放置三个label
	gtk_container_add (GTK_CONTAINER (hbox), vbox);
	gtk_widget_show (vbox);

	labelip=gtk_label_new("IP:        ");
	gtk_container_add(GTK_CONTAINER(vbox),labelip);
	labelcomm=gtk_label_new("COMM:");
	gtk_container_add(GTK_CONTAINER(vbox),labelcomm);
	labelmemo=gtk_label_new("MEMO:");
	gtk_container_add(GTK_CONTAINER(vbox),labelmemo);

	vbox = gtk_vbox_new(FALSE,0);//子容器hbox中的容器,垂直排列,放置三个entry
	gtk_container_add( GTK_CONTAINER(hbox),vbox);
	gtk_widget_show(vbox);

	ip= gtk_entry_new();//tree列表视图
	gtk_container_add( GTK_CONTAINER(vbox), ip);
	comm= gtk_entry_new();//tree列表视图
	gtk_container_add( GTK_CONTAINER(vbox), comm);
	memo= gtk_entry_new();//tree列表视图
	gtk_container_add( GTK_CONTAINER(vbox), memo);

	hbox = gtk_hbox_new (FALSE, 0);//子容器2,水平放置两个按钮
	gtk_container_add (GTK_CONTAINER (vboxx), hbox);//在window里插入vbox,垂直方向布局
	gtk_widget_show (hbox);

	button_add=gtk_button_new_with_label("add   ");//按钮
	gtk_container_add( GTK_CONTAINER(hbox), button_add);
	//gtk_button_set_label((GtkButton*)button_add,"add   ");
	g_signal_connect( G_OBJECT( button_add ), "clicked", G_CALLBACK (gtk_button_addwatcher_clicked), NULL);
	gtk_widget_show (button_add);

	button_cancel=gtk_button_new_with_label("cancel");//按钮
	gtk_container_add( GTK_CONTAINER(hbox), button_cancel);
	//gtk_button_set_label((GtkButton*)button_cancel,"cancel");
	g_signal_connect( G_OBJECT( button_cancel ), "clicked", G_CALLBACK (gtk_button_cancelwatcher_clicked), NULL);
	gtk_widget_show (button_cancel);

	statusbar_child= (GtkStatusbar*)gtk_statusbar_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vboxx), (GtkWidget*)statusbar_child);//在主容器里添加状态栏
	gtk_widget_show ((GtkWidget*)statusbar_child);
	gtk_statusbar_push(statusbar_child,gtk_statusbar_get_context_id(statusbar_child,"changed"),"请输入相关信息");

	gtk_widget_show_all (child_window );
	gtk_widget_hide(child_window);
	/* All GTK applications must have a gtk_main(). Control ends here
		* and waits for an event to occur (like a key press or
		                                   * mouse event). */
	//	g_timeout_add_full(G_PRIORITY_DEFAULT ,1000,My_Timeout_Dealer,NULL,NULL);
	gtk_main ();

}

void my_main_quit()
{
	g_array_free(garray,TRUE); 
	//g_timeout_removeall();
	gtk_main_quit();
}

int 
main( int argc, char *argv[] ) //main
{
	/* GtkWidget is the storage type for widgets */
	GtkWidget *window;//主窗口
	GtkWidget *vbox,*hbox;//整体框架
	GtkWidget *button_add,*button_edit,*button_del,*button_start;//按钮

	//GtkStatusbar *statusbar;
	/* This is called in all GTK applications. Arguments are parsed
	 * from the command line and are returned to the application. */
	gtk_init ( &argc, &argv );
	window = gtk_window_new( GTK_WINDOW_TOPLEVEL );
	gtk_window_set_position((GtkWindow*)window,GTK_WIN_POS_CENTER_ALWAYS);
	gtk_window_set_title( GTK_WINDOW( window ), "SNMP WATCHER");
	g_signal_connect( G_OBJECT( window ), "destroy", my_main_quit, NULL);

	vbox = gtk_vbox_new (FALSE, 0);//列表视图
	gtk_container_add (GTK_CONTAINER (window), vbox);//在window里插入vbox,垂直方向布局
	gtk_widget_show (vbox);

	view = gtk_tree_view_new();//tree列表视图
	gtk_container_add( GTK_CONTAINER(vbox), view);
	//g_signal_connect(view, "row-activated", (GCallback) view_onRowActivated, NULL);//双击
	g_signal_connect(view, "button-press-event", (GCallback) view_onButtonPressed, NULL);//单击
	g_signal_connect(view, "popup-menu", (GCallback) view_onPopupMenu, NULL);//菜单

	// arrange view columns    			  
	arrange_tree_view(view); // set mode
	store = create_model();			  
	gtk_tree_view_set_model ( GTK_TREE_VIEW(view),  store);
	model_data_new( store, "127.0.0.1",			"public",   "watching");//初始化
	model_data_new( store, "192.168.61.129",   "public",   "watching");    
	model_data_new( store, "127.0.0.1",			"private",  "watching");//初始化
	model_data_new( store, "192.168.202.131",   "private",  "watching");    
	//g_signal_connect( G_OBJECT( store ), "clicked", G_CALLBACK (gtk_store_clicked), view);
	g_object_unref( store ); 

	hbox = gtk_hbox_new (FALSE, 0);//列表视图
	gtk_container_add (GTK_CONTAINER (vbox), hbox);//在window里插入vbox,垂直方向布局
	gtk_widget_show (hbox);

	button_add=gtk_button_new_with_label("add");//按钮
	gtk_container_add( GTK_CONTAINER(hbox), button_add);
	//gtk_button_set_label((GtkButton*)button_add,"add");
	g_signal_connect( G_OBJECT( button_add ), "clicked", G_CALLBACK (gtk_button_add_clicked), NULL);
	gtk_widget_show (button_add);

	button_edit=gtk_button_new_with_label("edit");//按钮
	gtk_container_add( GTK_CONTAINER(hbox), button_edit);
	//gtk_button_set_label((GtkButton*)button_edit,"edit");
	g_signal_connect( G_OBJECT( button_edit ), "clicked", G_CALLBACK (gtk_button_edit_clicked), NULL);
	gtk_widget_show (button_edit);

	button_del=gtk_button_new_with_label("del");//按钮
	gtk_container_add( GTK_CONTAINER(hbox), button_del);
	//gtk_button_set_label((GtkButton*)button_del,"del");
	g_signal_connect( G_OBJECT( button_del ), "clicked", G_CALLBACK (gtk_button_del_clicked), NULL);
	gtk_widget_show (button_del);

	button_start=gtk_button_new_with_label("Click to Start");//按钮
	gtk_container_add( GTK_CONTAINER(vbox), button_start);
	//gtk_button_set_label((GtkButton*)button_start,"Click to Start");
	g_signal_connect( G_OBJECT( button_start ), "clicked", G_CALLBACK (gtk_button_start_clicked), NULL);
	gtk_widget_show (button_start);

	test1= (GtkTextView*)gtk_text_view_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vbox), (GtkWidget*)test1);
	gtk_widget_show ((GtkWidget*)test1);
	test2= (GtkTextView*)gtk_text_view_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vbox), (GtkWidget*)test2);
	gtk_widget_show ((GtkWidget*)test2);
	test3= (GtkTextView*)gtk_text_view_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vbox), (GtkWidget*)test3);
	gtk_widget_show ((GtkWidget*)test3);
	test4= (GtkTextView*)gtk_text_view_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vbox), (GtkWidget*)test4);
	gtk_widget_show ((GtkWidget*)test4);
	test5= (GtkTextView*)gtk_text_view_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vbox), (GtkWidget*)test5);
	gtk_widget_show ((GtkWidget*)test5);
	test6= (GtkTextView*)gtk_text_view_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vbox), (GtkWidget*)test6);
	gtk_widget_show ((GtkWidget*)test6);

	statusbar= (GtkStatusbar*)gtk_statusbar_new();//状态栏
	gtk_container_add( GTK_CONTAINER(vbox), (GtkWidget*)statusbar);
	gtk_widget_show ((GtkWidget*)statusbar);

	gtk_widget_show_all ( window );
	/* All GTK applications must have a gtk_main(). Control ends here
		* and waits for an event to occur (like a key press or
		                                   * mouse event). */
	g_timeout_add_full(G_PRIORITY_DEFAULT ,1000,My_Timeout_Dealer,NULL,NULL);

	create_child_window();
	gtk_main ();
	//	
	return 0;
}


 

 类似资料: