ucGUI做的一个TreeView这样的控件!

10 篇文章 0 订阅

用ucGUI做了一个TreeView这样的控件!我用的版本里没有TreeView这个控件,所以自己做了一个.

这个做得比较难看呀!

个人头脑比较简单,所以做的思路也比较简单! 所以后面的代码也很简单

主要如下

一个节点放在一个窗体里,比如从根节点开始,有子节点的话,就创建一个窗体,它的父窗体就是父节点所在的窗体,就是和树一样的嵌套在一起的,这样主要可以方便的运行ucGUI的消息过程,比如节点展开,收起时,对长,宽的处理就会很方便.


我做的效果像这样的,哎,太难看了,程序员做界面还是不行呀, (因为是在嵌入式设备上,没有截图功能,就拍了一张,右边的tab Page也是自定义的,没有UGGUI自带的):



代码如下(我没有单独编译,如果少了什么定义的宏,自己根据定义自己搞一下),有兴趣的可以看一下。

//==========================头文件========================//
typedef struct TreeNode_struct TreeNode;

struct TreeNode_struct{
	int NodeID;       //结点ID
	char *NodeName;   //结点名称
};

static TreeNode MainTreeNode[]={
	{1,"设备1"},
	{2,"设备2"},
	{3,"设备3"},
	{4,"设备4"},
	{5,"设备5"},
};

WM_HWIN CreateTreeView(int x,int y,int xs,int ys,WM_HWIN hParent);

//添加一个子结点
WM_HWIN addTreeNode(WM_HWIN hParent,TreeNode *NodeInfo,int Root);


//=============================代码文件===============================//
#include "CreateTreeView.h"
#include "BUTTON.h"
#include "TEXT.h"
#include "SCROLLBAR.h"

#include "string.h"

#define WindowsBackgroundColor 0x6A4935
#define NodeHeight 20        //节点收起时高度
#define WM_USER_SUBNODESIZE WM_USER + 102

static void _cbMain(WM_MESSAGE *pMsg);

//节点回调
static void _cbTreeNode(WM_MESSAGE *pMsg);
//节点展开按钮回调
static void _cbNodeExpendButton(WM_MESSAGE *pMsg);
//节点按钮回调
static void _cbNodeButton(WM_MESSAGE *pMsg);
//展开节点
static void ExpendNode(WM_HWIN hwin,int flag);

WM_CALLBACK *_cbbtndefault,*_cbSCROLLBARDefault;

WM_HWIN CreateTreeView(int x,int y,int xs,int ys,WM_HWIN hParent){
	WIDGET_SetDefaultEffect_None();
	BUTTON_SetDefaultFont(FontHZText);
	BUTTON_SetDefaultTextColor(GUI_WHITE,0);
	BUTTON_SetDefaultBkColor(WindowsBackgroundColor,0);

	WM_HWIN hwin = WM_CreateWindowAsChild(x,y,xs,ys,hParent,WM_CF_SHOW,_cbMain,0);
	return hwin;
}

static void _cbMain(WM_MESSAGE *pMsg){
	switch(pMsg->MsgId){
		case WM_PAINT:
			GUI_SetBkColor(0x6A4935);
			GUI_Clear();
			break;
		case WM_USER_Change_SCROLLBAR:
		{
			WM_HWIN hwin,SHwin,SVwin;
			int Height=0,Width=0;
			SHwin = WM_GetScrollbarH(WM_GetParent(pMsg->hWin));
			SVwin = WM_GetScrollbarV(WM_GetParent(pMsg->hWin));
			hwin = WM_GetFirstChild(pMsg->hWin);
			while(WM_IsWindow(hwin)){
				if(Width<WM_GetWinSizeX(hwin))
					Width = WM_GetWinSizeX(hwin);
				Height += WM_GetWinSizeY(hwin);
				hwin = WM_GetNextSibling(hwin);
			}
			if(WM_IsWindow(SHwin))
			{
				SCROLLBAR_SetNumItems(SHwin,Width);
			}
			if(WM_IsWindow(SVwin))
			{

				SCROLLBAR_SetNumItems(SVwin,Height);
			}
			break;
		}
		default:
			WM_DefaultProc(pMsg);
	}
}

//添加一个子结点
WM_HWIN addTreeNode(WM_HWIN hParent,TreeNode *NodeInfo,int Root){
	WM_HWIN NodeHwin=0;
	BUTTON_Handle bhwin = 0;
	BUTTON_Handle btexthwin = 0;
	U16 Style;
	int x,y,xs,ys;
	if(WM_IsWindow(hParent))
	{
		if(Root==1)
		{
			WM_HWIN hwin=0,lastHwin=0;
			//加到最后一个根结点后面
			hwin = WM_GetFirstChild(hParent);
			while(WM_IsWindow(hwin)){
				lastHwin = hwin;
				hwin = WM_GetNextSibling(hwin);
			}

			if(lastHwin==0)
			{	x = 5;
				y = 5;
			}else
			{
				x = 5;
				y = WM_GetWinOrgY(lastHwin) - WM_GetWinOrgY(hParent) + WM_GetWinSizeY(lastHwin);
			}
			xs = WM_GetWinSizeX(hParent);
			ys = NodeHeight;
			Style = WM_CF_SHOW;
		}
		else
		{
			x = 20;
			y = WM_GetWindowSizeY(hParent);
			xs = WM_GetWinSizeX(hParent);
			ys = NodeHeight;
			Style = WM_CF_SHOW;
		}
		NodeHwin = WM_CreateWindowAsChild(x,y,xs,ys,hParent,Style,_cbTreeNode,0);
		//展开按钮,隐藏,如果有子节点增加进来,就显示
		bhwin = BUTTON_CreateAsChild(0,5,10,10,NodeHwin,1,GUI_TA_CENTER|GUI_TA_VCENTER|Style);
		WM_HideWin(bhwin);
		//节点名称
		btexthwin = BUTTON_CreateAsChild(20,0,strlen(NodeInfo->NodeName)*10,NodeHeight,NodeHwin,2,WM_CF_SHOW|GUI_TA_LEFT|GUI_TA_VCENTER);
		WM_SetCallback(bhwin,_cbNodeExpendButton);
		_cbbtndefault = WM_SetCallback(btexthwin,_cbNodeButton);
		//BUTTON_setbo
		BUTTON_SetTextAlign(btexthwin,GUI_TA_LEFT|GUI_TA_VCENTER);
		BUTTON_SetText(btexthwin,NodeInfo->NodeName);
		BUTTON_SetFocussable(btexthwin,0);
		BUTTON_SetFocussable(bhwin,0);
		if(Root == 0)
		{
			WM_HWIN Parentbhwin = WM_GetFirstChild(hParent);
			while(WM_IsWindow(Parentbhwin)){
				if(WM_GetId(Parentbhwin) == 1)
				{
					BUTTON_SetText(Parentbhwin,"+");  //显示父节点的展开按钮,创建时是隐藏的
					WM_ShowWin(Parentbhwin);
					break;
				}
				Parentbhwin = WM_GetNextSibling(Parentbhwin);
			}
		}
		return NodeHwin;
	}
}

//节点回调
static void _cbTreeNode(WM_MESSAGE *pMsg){
	WM_MESSAGE Msg;
	WM_HWIN Nexthwin;
	int Xs,Ys;
	switch(pMsg->MsgId)
	{
		case WM_USER_SUBNODESIZE:
			//改变节点的高度(子节点展开或收起时发送来的消息)
			Ys = WM_GetYSize(pMsg->hWin) + pMsg->Data.v;
			WM_SetYSize(pMsg->hWin,Ys);

			//如果子节点的宽度改变,大于父节点了,需要改变父节点宽度
			if(WM_GetXSize(pMsg->hWin)<WM_GetXSize(pMsg->hWinSrc) + 20)
			{
				Xs = WM_GetXSize(pMsg->hWinSrc) + 20;
				WM_SetXSize(pMsg->hWin,Xs);  
			}
			//改变后面兄弟节点Y位置
			Nexthwin = WM_GetNextSibling(pMsg->hWin);
			while(WM_IsWindow(Nexthwin)){
				if(WM_GetId(Nexthwin) == 0)
					WM_MoveTo(Nexthwin,WM_GetWinOrgX(Nexthwin),WM_GetWinOrgY(Nexthwin) + pMsg->Data.v);
				Nexthwin = WM_GetNextSibling(Nexthwin);
			}

			Msg.hWin = WM_GetParent(pMsg->hWin);
			Msg.MsgId = WM_USER_SUBNODESIZE;
			Msg.Data.v = pMsg->Data.v;
			//改变父节点
			WM_SendMessage(Msg.hWin,&Msg);
			//设置设置滚动条
			WM_SendMessageNoPara(WM_GetParent(pMsg->hWin),WM_USER_Change_SCROLLBAR);
			break;	
		case WM_PAINT:
		{
			int dy;
			GUI_SetBkColor(WindowsBackgroundColor);
			GUI_Clear();
			/*if(!WM_IsWindow(WM_GetNextSibling(WM_GetParent(pMsg->hWin))))
			{
				dy = 10;
			}else
			{
				dy = 0;
			}
			GUI_SetColor(GUI_GRAY);
			GUI_DrawLine(4,0,4,WM_GetWinSizeY(pMsg->hWin)-dy);
			GUI_DrawLine(5,9,20,9);
			*/
			break;
		}
		default:
			WM_DefaultProc(pMsg);
	}
}

//节点展开按钮回调
static void _cbNodeExpendButton(WM_MESSAGE *pMsg)
{
	switch(pMsg->MsgId)
	{
		case WM_PAINT:
			GUI_Clear();
			break;
		case WM_PID_STATE_CHANGED:
		{
			WM_PID_STATE_CHANGED_INFO *PID_STATE_CHANGED_INFO;
			PID_STATE_CHANGED_INFO = (WM_PID_STATE_CHANGED_INFO *)pMsg->Data.p;
			if(PID_STATE_CHANGED_INFO->State > 0)
			{	
				if(WM_GetWinSizeY(WM_GetParent(pMsg->hWin)) == NodeHeight )
				{
					BUTTON_SetText(pMsg->hWin,"-");
					ExpendNode(WM_GetParent(pMsg->hWin),1);
				}else
				{
					BUTTON_SetText(pMsg->hWin,"+");
					ExpendNode(WM_GetParent(pMsg->hWin),0);
				}
			}
			break;
		}
	}
	_cbbtndefault(pMsg);
}

//节点按钮回调
static void _cbNodeButton(WM_MESSAGE *pMsg)
{
	switch(pMsg->MsgId)
	{
		case WM_PAINT:
			GUI_SetBkColor(WindowsBackgroundColor);
			GUI_Clear();
			break;
		case WM_NOTIFY_PARENT:
		{
			int Id = pMsg->hWinSrc;
			if(pMsg->Data.v == WM_NOTIFICATION_RELEASED)
			{
				;
			}
			break;
		}
		case WM_PID_STATE_CHANGED:
		{
			WM_PID_STATE_CHANGED_INFO *PID_STATE_CHANGED_INFO;
			PID_STATE_CHANGED_INFO = (WM_PID_STATE_CHANGED_INFO *)pMsg->Data.p;
			if(PID_STATE_CHANGED_INFO->State > 0)
			{
				//ExpendNode(WM_GetParent(pMsg->hWin),);	
			}
			break;
		}
	}
	_cbbtndefault(pMsg);
}

static void _cbSCHandle(WM_MESSAGE *pMsg){
	switch(pMsg->MsgId)
	{
		case WM_PAINT:
			GUI_SetBkColor(WindowsBackgroundColor);
			GUI_Clear();
			break;
	}
	_cbSCROLLBARDefault(pMsg);
}

static void ExpendNode(WM_HWIN hParent,int flag){
	WM_HWIN hwin;
	WM_MESSAGE Msg;
	int i=0,chHeight=0;
	hwin = WM_GetFirstChild(hParent);
	while(WM_IsWindow(hwin))
	{
		if(WM_GetId(hwin)==0)
		{
			i++;
			if(flag==1){
				Msg.hWin = hParent;
				Msg.Data.v = WM_GetWinSizeY(hwin);
				chHeight += WM_GetWinSizeY(hwin);
				Msg.hWinSrc = hwin;
				Msg.MsgId = WM_USER_SUBNODESIZE;
				WM_SendMessage(hParent,&Msg);
				WM_MoveTo(hwin,WM_GetWinOrgX(hwin),WM_GetWinOrgY(hParent) + WM_GetWinSizeY(hParent) - WM_GetWinSizeY(hwin));
				WM_ShowWin(hwin);
			}else
			{
				Msg.hWin = hParent;
				Msg.hWinSrc = hwin;
				Msg.Data.v = -WM_GetWinSizeY(hwin);
				chHeight += -WM_GetWinSizeY(hwin);
				Msg.MsgId = WM_USER_SUBNODESIZE;		
				WM_SendMessage(hParent,&Msg);
				WM_HideWin(hwin);
			}
		}
		hwin = WM_GetNextSibling(hwin);
	}
	if(flag == 0)
	{
		//WM_SetXSize(hParent,
		WM_SetYSize(hParent,NodeHeight);
	}

}




  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值