⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 svclistview.hpp

📁 j2me is based on j2mepolish, client & server for mobile application.
💻 HPP
字号:

//         Copyright E骾n O'Callaghan 2008 - 2008.
// Distributed under the Boost Software License, Version 1.0.
//    (See accompanying file LICENSE_1_0.txt or copy at
//          http://www.boost.org/LICENSE_1_0.txt)

#ifndef SVCLISTVIEW_HPP_INCLUDED
#define SVCLISTVIEW_HPP_INCLUDED

#include "Resource.h"

#include <boost/statechart/event.hpp>
#include <boost/statechart/transition.hpp>
#include <boost/statechart/state_machine.hpp>
#include <boost/statechart/simple_state.hpp>
#include <boost/statechart/state.hpp>
#include <boost/statechart/event.hpp>

#include <boost/iterator/filter_iterator.hpp>
#include <boost/ptr_container/ptr_vector.hpp>
#include <winstl/controls/listview_sequence.hpp>

#include "SettingsIni.hpp"
#include "SortListViewCtrlEx.hpp"
#include "ListViewIterators.hpp"

#include "nt_service.hpp"
#include "event_logger.hpp"

struct ev_switch_to_overview : boost::statechart::event<ev_switch_to_overview> {};
struct ev_switch_to_profile : boost::statechart::event<ev_switch_to_profile> {};

struct overview_mode;
class SvcListViewCtrl;

struct list_state_machine :
	public boost::statechart::state_machine<list_state_machine, overview_mode>
{
	list_state_machine(SvcListViewCtrl* list) :
		list_(list)
	{}

	bool is_overview_mode() const;

	SvcListViewCtrl* list() { return list_; }

private:
	SvcListViewCtrl* list_;
};

class SvcListViewCtrl :
	public WTLx::SortListViewCtrlEx<SvcListViewCtrl>,
	public WTLx::ListViewIterators<SvcListViewCtrl>,
	public WTL::CCustomDraw<SvcListViewCtrl>,
	private SettingsIni<SvcListViewCtrl>
{
	typedef SvcListViewCtrl thisClass;
	typedef WTLx::SortListViewCtrlEx<thisClass> listClass;
	typedef WTL::CCustomDraw<thisClass> ownDrawClass;
	typedef SettingsIni<thisClass> iniClass;
	friend class listClass;

	typedef boost::function<void (size_t)> listview_setting_changed_fn;
	typedef boost::function<void (std::vector<service_ptr>)> listview_items_selected_fn;

	typedef std::vector<std::pair<service_ptr, 
		boost::optional<nt_service::service_settings> > > services_vector;

public:
	BEGIN_MSG_MAP_EX(SvcListViewCtrl)
		MSG_WM_SHOWWINDOW(OnShowWindow)
		MSG_WM_DESTROY(OnDestroy)

		COMMAND_ID_HANDLER(ID_ACTIVE_NO_CHANGE, OnStateChange)
		COMMAND_ID_HANDLER(ID_ACTIVE_STARTED, OnStateChange)
		COMMAND_ID_HANDLER(ID_ACTIVE_PAUSED, OnStateChange)
		COMMAND_ID_HANDLER(ID_ACTIVE_STOPPED, OnStateChange)

		COMMAND_ID_HANDLER(ID_STARTTYPE_NO_CHANGE, OnStartTypeChange)
		COMMAND_ID_HANDLER(ID_STARTTYPE_AUTOMATIC, OnStartTypeChange)
		COMMAND_ID_HANDLER(ID_STARTTYPE_MANUAL, OnStartTypeChange)
		COMMAND_ID_HANDLER(ID_STARTTYPE_DISABLED, OnStartTypeChange)
		
		REFLECTED_NOTIFY_CODE_HANDLER(NM_CLICK, OnLClick)
		
		if (test_notification_lock())
		{
		REFLECTED_NOTIFY_CODE_HANDLER(LVN_ITEMCHANGED, OnItemChanged)
		}

        CHAIN_MSG_MAP_ALT(ownDrawClass, 1)
		CHAIN_MSG_MAP(listClass)
		DEFAULT_REFLECTION_HANDLER()
	END_MSG_MAP()

	SvcListViewCtrl(aux::txml_ini& ini, listview_setting_changed_fn lsc, listview_items_selected_fn lis) :
		iniClass("service_pane", "service_listview", ini),
		listview_setting_changed_(lsc),
		listview_items_selected_(lis),
		state_machine_(this)
	{}

    DWORD OnPrePaint(int idCtrl, LPNMCUSTOMDRAW lpNMCD)
	{
		return CDRF_NOTIFYITEMDRAW;
	}

	DWORD OnItemPrePaint(int idCtrl, LPNMCUSTOMDRAW lpNMCD)
	{
		NMLVCUSTOMDRAW* pnmlv = (NMLVCUSTOMDRAW*) lpNMCD;

		size_t index = pnmlv->nmcd.lItemlParam;

		if (!overview_mode())
		{
			if (!services_[index].second || services_[index].second->is_inert() && 
						!GetCheckState(pnmlv->nmcd.dwItemSpec))
			{
				pnmlv->clrText = RGB(180,180,205);
			}
			else if (services_[index].second && !services_[index].second->is_inert() && 
						!GetCheckState(pnmlv->nmcd.dwItemSpec))
			{
				pnmlv->clrText = RGB(50,50,150);
			}
			else
				pnmlv->clrText = RGB(0,0,40);
		}

		return CDRF_DODEFAULT;
	}

	void OnShowWindow(UINT, INT);

	void DeleteItem(LPDELETEITEMSTRUCT) {};

	void OnDestroy()
	{
		iniClass::SaveSettings();
	}

	LRESULT OnLClick(int i, LPNMHDR pnmh, BOOL& b)
	{
		WTL::CPoint point;
		GetCursorPos(&point);
		ScreenToClient(&point);

		UINT flags;
		HitTest(point, &flags);

		if (flags & LVHT_ONITEMLABEL)
			return OnRClick(i, pnmh, b);
		else
		{
			SetMsgHandled(false);	
			return 0;
		}
	}

	LRESULT OnStateChange(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled)
	{
		winstl::listview_sequence lv_seq(*this);
		DWORD state;

		switch(wID)
		{
		case ID_ACTIVE_STARTED:
			state = SERVICE_RUNNING;
			break;
		case ID_ACTIVE_PAUSED:
			state = SERVICE_PAUSED;
			break;
		case ID_ACTIVE_STOPPED:
			state = SERVICE_STOPPED;
			break;
		case ID_ACTIVE_NO_CHANGE:
		default:
			state = SERVICE_NO_CHANGE;
		};

		foreach(const winstl::listview_sequence::sequence_value_type val, 
			std::make_pair(is_selected_begin(), is_selected_end()))
		{
			WTLx::notification_lock<listClass> lock(*this);

			if (!services_[val.data()].second) 
			{
				services_[val.data()].second = 
					nt_service::service_settings(*services_[val.data()].first, false, false);
			}

			nt_service::service_settings& settings = *services_[val.data()].second;

			settings.set_dwCurrentState(state);	
			SetCheckState(val.index(), true);

			set_item_settings_text(val.index(), settings);
		}
		
		listview_setting_changed_(0);

		return 0;
	}

	LRESULT OnStartTypeChange(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled)
	{
		winstl::listview_sequence lv_seq(*this);
		DWORD type;

		switch(wID)
		{
		case ID_STARTTYPE_AUTOMATIC:
			type = SERVICE_AUTO_START;
			break;
		case ID_STARTTYPE_MANUAL:
			type = SERVICE_DEMAND_START;
			break;
		case ID_STARTTYPE_DISABLED:
			type = SERVICE_DISABLED;
			break;
		case ID_STARTTYPE_NO_CHANGE:
		default:
			type = SERVICE_NO_CHANGE;
		};

		foreach(const winstl::listview_sequence::sequence_value_type val, 
			std::make_pair(is_selected_begin(), is_selected_end()))
		{
			WTLx::notification_lock<listClass> lock(*this);

			if (!services_[val.data()].second) 
			{
				services_[val.data()].second = 
					nt_service::service_settings(*services_[val.data()].first, false, false);
			}

			nt_service::service_settings& settings = *services_[val.data()].second;

			settings.set_dwStartType(type);
			SetCheckState(val.index(), true);

			set_item_settings_text(val.index(), settings);
		}
		
		listview_setting_changed_(0);

		return 0;
	}

	LRESULT OnItemChanged(int, LPNMHDR pnmh, BOOL&)
	{
		if (test_notification_lock())
		{
			LPNMLISTVIEW pnmlv = (LPNMLISTVIEW) pnmh;

			if (pnmlv->uChanged & LVIF_STATE &&
					(pnmlv->uOldState & LVIS_STATEIMAGEMASK) != (pnmlv->uNewState & LVIS_STATEIMAGEMASK))
			{
				item_checked(pnmlv, (GetCheckState(pnmlv->iItem) ? true : false));
			}
			else if (pnmlv->uChanged & LVIF_STATE &&
					(pnmlv->uNewState & LVIS_SELECTED))
			{
				item_selected();
			}
		}
		return 0;
	}

	void display_all_services();

	void item_selected()
	{
		std::vector<service_ptr> vec;

		foreach(const winstl::listview_sequence::sequence_value_type val, 
			std::make_pair(is_selected_begin(), is_selected_end()))
		{
			vec.push_back(services_[val.data()].first);
		}

		listview_items_selected_(vec);
	}

	void item_checked(LPNMLISTVIEW item, bool checked)
	{
		size_t index = item->lParam;

		if (!checked)
		{
			services_[index].second.reset();
			reset_item_settings_text(item->iItem);
		}
		else
		{
			if (!services_[index].second) 
			{
				services_[index].second = 
					nt_service::service_settings(*services_[index].first, false, false);
			}
		}

		listview_setting_changed_(item->iItem);
	}

	void set_item_settings_text(unsigned iItem, const nt_service::service_settings& settings);
	void reset_item_settings_text(unsigned iItem);

	int add_and_list_service(service_ptr svc_p);

	int list_service(nt_service& svc, size_t i=-1);

	void update_with_settings(std::set<nt_service::service_settings> services);

	void reset_display_services();

	void reset_display_item_text(unsigned iItem, service_ptr svc);

	std::vector<nt_service::service_settings> get_checked_settings()
	{
		std::vector<nt_service::service_settings> vec;

		foreach(const winstl::listview_sequence::sequence_value_type val, 
			std::make_pair(is_checked_begin(), is_checked_end()))
		{
			logger.post(new event_type(event_logger::dev, 
				wformat(L"get_checked_settings %1%, %2%.") % val.data() % val.index()));

			assert(services_[val.data()].second);

			if (services_[val.data()].second)
				vec.push_back(*services_[val.data()].second);
		}

		return vec;
	}

    friend class boost::serialization::access;
    template<class Archive>
    void serialize(Archive& ar, const unsigned int version)
    {
		ar & boost::serialization::make_nvp("listview", 
			boost::serialization::base_object<listClass>(*this));
    }

	bool overview_mode();
	void set_overview_mode(bool ob);

	bool is_empty() { return services_.empty(); }

private:
	listview_setting_changed_fn listview_setting_changed_;
	listview_items_selected_fn listview_items_selected_;

	list_state_machine state_machine_;
	services_vector services_;

	WTL::CIcon ico_;
	WTL::CImageList i_list_;
};

#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -