#include "stdafx.h"
#include "dictionary.h"

#include "PSMDoc.h"

/*#include "aplTopLevelItem.h"
#include "aplFolderTreeItem.h"
#include "aplMessageTreeItem.h"*/
#include "aplTreeWfFolderItem.h"
#include "aplMessageFolderTreeItem.h"
#include "aplTreeProcessTmplItem.h"
#include "aplTreeActivityItem.h"
#include "aplTreeProcessItem.h"
#include "TabView.h"
#include "aplDocTreeItem.h"

#include "resource.h"

//CaplProcessTmplTreeItem
CaplProcessTmplTreeItem::CaplProcessTmplTreeItem(CTreeCtrl *tree, CPSMDoc *doc, CaplInstance* inst)
{
	m_type= APL_TREE_ITEM_PROCESSTMPL;
	m_doc= doc;
	m_tree= tree;
	m_proc_tmpl= inst;
	m_folder=0;
	if(doc!=0) 
		doc->m_items.Add(this);	
}

bool CaplProcessTmplTreeItem::GetName(CString &name)
{
	_APL_TREE_ITEM_CHEK_PARAM_BOOL
	CHECK_GET_NAME(m_proc_tmpl);
	
	CString buf;

	m_doc_data.GetAttr(m_proc_tmpl, m_doc->m_wf_mgr.a_action_id, name);
	name+=_T(" : ");
	m_doc_data.GetAttr(m_proc_tmpl, m_doc->m_wf_mgr.a_action_name, buf);
	name+=buf;

	return true;
}

bool CaplProcessTmplTreeItem::RefreshItem()
{
	_APL_TREE_ITEM_CHEK_PARAM_BOOL
	
	UINT ico= ICON_PROCESS_TMPL;
	
	if(m_tree!=0)
	{
		CString name;
		GetName(name);

		SetItemImage(ico, IDX_IL_TREE_ITEM);
		m_tree->SetItemText(m_item, name);
		
		Sort();
		m_tree->RedrawWindow();
	}
	if(m_doc->m_tab_view->m_item_old==this) m_doc->ChangeItem(this);
	return true;
}

bool CaplProcessTmplTreeItem::CreateTreeItem(HTREEITEM parent_item)
{
	_APL_TREE_ITEM_CHEK_PARAM_BOOL
	
	CString buf;
	GetName(buf); 
	UINT ico= ICON_PROCESS_TMPL;

	InsetItem(buf,ico,parent_item);
	SetItemImage(ico, IDX_IL_TREE_ITEM);
	m_fictive_item=m_tree->InsertItem(_T("fictive"), 0, 0, m_item);

	m_expanded=false;

	return true;
}

void CaplProcessTmplTreeItem::ShowActivityList()
{
	_APL_TREE_ITEM_CHEK_PARAM_VOID
	
	aplExtent ext_act, ext_ep;
	m_doc->m_wf_mgr.GetProcessComponents(m_proc_tmpl, ext_act);
	
	for(int i= 0; i<ext_act.GetSize(); i++)
	{
		if(m_doc_data.IsKindOf(ext_act[i], m_doc->m_wf_mgr.e_activity) && 
			-1==m_activity_items.Find(ext_act[i]))
		{
			CaplActivityTreeItem* item= new CaplActivityTreeItem(
				m_tree, m_doc, ext_act[i]);
			item->CreateTreeItem(m_item);
			m_activity_items.Add(ext_act[i]);			
		}
	}
}

bool CaplProcessTmplTreeItem::Expand(UINT action)
{
	_APL_TREE_ITEM_CHEK_PARAM_BOOL
	
	if(action==2)
	{
		if(m_expanded) return true;
		if(m_hasSubItem) Expand(1);
		if(m_fictive_item!=0)
		{
			m_tree->DeleteItem(m_fictive_item);
			m_fictive_item=0;
		}
		ShowActivityList();
		m_hasSubItem= true;
		m_expanded= true;

		bool old = m_bShowNoFoundMessage;
		m_bShowNoFoundMessage = old;
		m_ExecMyExpand = true;
		//if(m_doc->m_auto_expand_items.m_showintree_lot&APL_SHOW_DOC)
			ShowAllDocs(false,false);
		m_bShowNoFoundMessage = old;
		m_ExecMyExpand = true;

		m_tree->SetRedraw(TRUE);
		Sort();
	}
	else if(action==1)
	{
		CollapseItem();
		m_activity_items.Clear();
		m_proc_tmpl_history_items.Clear();
	}	
	return true;
}

void CaplProcessTmplTreeItem::ShowProperties()
{
	_APL_TREE_ITEM_CHEK_PARAM_VOID
	m_doc->m_wf_mgr.ShowTmplProperties(m_proc_tmpl);
}

bool CaplProcessTmplTreeItem::ShowInListCtrl(CListCtrl *list)
{
	if(list==0) return false;
	else list->DeleteAllItems();
	if(m_doc==0)return false;
	if(m_doc->m_BShowInListCtrl==false) return true;
	CHECK_SHOW_LIST_CTRL(m_proc_tmpl);

	CString buf;
	int i= list->InsertItem(0,  APL_T("Обозначение:"));
	m_doc_data.GetAttr(m_proc_tmpl, m_doc->m_wf_mgr.a_action_id, buf);
	list->SetItemText(i, 1, buf);
	i= list->InsertItem(1,  APL_T("Наименование:"));
	m_doc_data.GetAttr(m_proc_tmpl, m_doc->m_wf_mgr.a_action_name, buf);
	list->SetItemText(i, 1, buf);
	i= list->InsertItem(2,  APL_T("Описание:"));
	m_doc_data.GetAttr(m_proc_tmpl, m_doc->m_wf_mgr.a_action_dscr, buf);
	list->SetItemText(i, 1, buf);

	aplExtent ext;
	CStringArray  comment;

	comment.Add(_T("m_proc_tmpl"));
	ext.Add(m_proc_tmpl);
	
	ShowInstanceInfoInListCtrl(ext,list,&comment);
	
	return true;
}

void CaplProcessTmplTreeItem::ShowCmd(long cmd)
{
	
}

BOOL CaplProcessTmplTreeItem::ShowToolBarButton(CCmdUI* pCmdUI)
{
/*	switch(pCmdUI->m_nID)
	{
	case ID_SHOW_ALL_DOCS:
	case ID_SHOW_ALL_CHARACTERISTIC:
	case ID_SHOW_ALL_APPROVAL:
	case ID_PRODUCT_SHOW_ALL_ZAGOTOV:
	case ID_SHOW_ALL_LOT:
	case ID_SHOW_ALL_PRD_INST:
	case ID_CREATE_APPROVAL:
	case ID_SHOW_ALL_VERSION:
	case ID_CREATE_PRODUCT:
	case ID_CREATE_CHARACTERISTIC:
	case ID_CREATE_DOC:
		pCmdUI->Enable(TRUE); return TRUE; break;
	}*/
	return FALSE;
}

bool CaplProcessTmplTreeItem::TrackPopupMenu(CWnd* wnd, CPoint &point, UINT view_mode)
{
	CMenu menu;  gSetPsmResourceHandle();
	VERIFY(menu.LoadMenu(IDR_TREE_CONTEXT_MENU));
// 	VERIFY(menu.LoadToolBar(IDR_MENU_ICONS));
	CaplMenu::Install(wnd); // 	VERIFY(CaplMenu::Install(wnd, ePopupMenu ));
    CMenu* pPopup = menu.GetSubMenu(INDEX_PROCESS_TMPL_MENU);
    ASSERT(pPopup != NULL);
	if(pPopup==0) return false;

	if(m_proc_tmpl)
	{
		AppendAddIn((CMenu*)pPopup);
		UpdateMenu((CMenu**)&pPopup, view_mode);
	}

	if(m_folder==0)pPopup->EnableMenuItem(ID_REMOVE_FROM_FOLDER, MF_BYCOMMAND | MF_GRAYED);

	BOOL res = pPopup->TrackPopupMenu(TPM_LEFTALIGN | TPM_RIGHTBUTTON | TPM_RETURNCMD,
						point.x, point.y, wnd);
	switch (res)
	{
		case ID_PROC_TMPL_CREATE:
			CreateWfProcess();
			break;
		case ID_PROC_TMPL_HISTORY:
			ShowHistory();
			ShowActivityList();
			if(!IsExpandet())
			{
				m_hasSubItem= true;
				m_expanded= true;
				MyExpand();
			}
			break;
		case ID_PROC_TMPL_CREATE_MANY:
			{
				m_doc->m_wf_mgr.StartManyProcs(m_proc_tmpl, NULL);
				break;
			}
		case ID_SHOW_WF_TEMPL_SCHEMA:
			m_doc->m_wf_mgr.ShowTemplateSchema(m_proc_tmpl,0);
			break;
		case ID_WF_FOLDER_SHOW_WORK_SCREEN:
			{
				m_doc->m_wf_mgr.AnalyzeWorkTimes(m_proc_tmpl);
				break;
			}
		case ID_REMOVE_FROM_FOLDER:
			if(m_folder!=0)
			{
				if(m_doc->m_api.m_folder_mgr.RemoveFromFolder(m_folder,m_proc_tmpl))
					m_doc->m_items.Remove(m_doc->m_items.Find(this));
			}
			break;
/*		case ID_SHOW_PROPERTIES:
			break;*/
		default: PrepareContextMenu(res); 
			break;
	}
	return true;

}

void CaplProcessTmplTreeItem::ShowHistory()
{
	_APL_TREE_ITEM_CHEK_PARAM_VOID
	
	CaplInstance *user= m_doc->m_api.m_appr_mgr.GetCurrentPerson();
	if(!user) return;
	
	aplExtent ext;

	m_doc->m_wf_mgr.GetProcessTmplHistory(user, m_proc_tmpl, ext);
	
	m_tree->SetRedraw(FALSE);
	for(int i= 0; i<ext.GetSize(); i++)
	{
		if(-1==m_proc_tmpl_history_items.Find(ext[i]))
		{
			CaplProcessTreeItem* item= new CaplProcessTreeItem(m_tree, m_doc, ext[i]);
			item->CreateTreeItem(m_item);
			m_proc_tmpl_history_items.Add(ext[i]);
		}
	}	
	m_tree->SetRedraw(TRUE);
}
 
void CaplProcessTmplTreeItem::CreateWfProcess()
{
	_APL_TREE_ITEM_CHEK_PARAM_VOID

	CaplInstance *user= m_doc->m_api.m_appr_mgr.GetCurrentPerson();
	if(!user) return;
	CaplInstance *inst0= NULL;

	aplExtent tpExt, woExt;

	CaplInstance* proc= m_doc->m_wf_mgr.CreateWfProcess(_T(""), _T(""), _T(""), 
		m_proc_tmpl, user, NULL, 0, 0, 0, tpExt, woExt);

	if(proc) //Новый процесс создан и надо или закрыть папку "Процессs", или добавить туда элемент
	{
		m_doc->m_wf_mgr.RunWfProcess(proc);

		HTREEITEM nextItem= m_tree->GetParentItem(m_item); //Шаблоны
		HTREEITEM item1=0;
		if(nextItem)
			item1= m_tree->GetParentItem(nextItem); //Работы
		if(item1)
			nextItem= m_tree->GetChildItem(item1); //Задания

		while(1)
		{
			item1= m_tree->GetNextItem(nextItem, TVGN_NEXT); //Процессы
			if(item1==0) break;
			CaplWfFolderTreeItem *item= (CaplWfFolderTreeItem*)m_tree->GetItemData(item1);
			
			CString buf;
			item->GetName(buf);
			if(buf== APL_T("Процессы") && item->IsExpandet())
			{
				item->Expand(1);
				item->m_tree->Expand(item->m_item, TVE_COLLAPSE);
				break;
/*				//или
				CaplProcessTreeItem *newProcItem= new CaplProcessTreeItem(m_tree, m_doc, proc);
				newProcItem->CreateTreeItem(item1);
				item->m_items.Add(proc);
				m_tree->SetRedraw();
				break;*/
			}
			nextItem= item1;
		}
	}
}

void CaplProcessTmplTreeItem::GetAccessedInstances(aplExtent &ext)
{
	ext.Clear();
	if(m_proc_tmpl){if(m_proc_tmpl->GetType()!=0)ext.Add(m_proc_tmpl);}
}



bool CaplProcessTmplTreeItem::PasteItem(CaplTreeItem *item, CPoint *point)
{
	if(item==0) return false;
	if (item->m_type != APL_TREE_ITEM_DOCUMENT) return false;
	if(m_tree==0) return false;
	if(m_doc==0) return false;

	CMenu menu;  gSetPsmResourceHandle();
	CMenu *pPopup;
	VERIFY(menu.LoadMenu(IDR_PASTE_ITEM_MENU));
	// 	VERIFY(menu.LoadToolBar(IDR_MENU_ICONS));
	CaplMenu::Install(m_tree); // 	VERIFY(CaplMenu::Install(m_tree, ePopupMenu ));

	//if(item->m_type == APL_TREE_ITEM_PRODUCT)
	//	pPopup = menu.GetSubMenu(INDEX_PRODUCT_MENU);
	//else 
	if(item->m_type == APL_TREE_ITEM_DOCUMENT)
	{
		aplExtent ext;
		item->GetAccessedInstances(ext);
		CString state;
		m_doc_data.GetAttr(ext[0],m_doc->m_api.m_doc_mgr.a_apl_doc_wf_state,state);
		if(state==_T("canceled")) return false;
		pPopup = menu.GetSubMenu(INDEX_DOCUMENT_MENU);
	}

	if(pPopup!=0)
	{
		POINT pnt;
		if(point==0)
		{
			RECT rect;
			m_tree->GetItemRect(m_item,&rect,TRUE);
			m_tree->ClientToScreen(&rect);
			pnt.x=rect.right;
			pnt.y=rect.bottom;
		}
		else
		{
			pnt.x=point->x;
			pnt.y=point->y;
		}

		HTREEITEM parent = m_tree->GetNextItem(item->m_item,TVGN_PARENT);
		CaplTreeItem *parent_item = (CaplTreeItem*)m_tree->GetItemData(parent);
		if(parent_item && parent_item->m_type==APL_TREE_ITEM_QUERY)
		{
			pPopup->EnableMenuItem(ID_DOCUMENT_MOVE, MF_BYCOMMAND|MF_GRAYED);
		}
		pPopup->RemoveMenu(ID_DOCUMENT_INITIAL, MF_BYCOMMAND|MF_GRAYED);

		BOOL res=pPopup->TrackPopupMenu(TPM_LEFTALIGN|
			TPM_RIGHTBUTTON|TPM_RETURNCMD,pnt.x,pnt.y,m_tree);

		// Вставка документа
		if (res == ID_DOCUMENT_COPY)
		{
			CaplInstance *i_doc=((CaplDocTreeItem *)item)->m_inst;

			HTREEITEM ht = m_tree->GetNextItem(item->m_item,TVGN_PARENT);
			CaplTreeItem *Item = (CaplTreeItem*)m_tree->GetItemData(ht);
			aplAccessModeType access =aplOWN;
			if(Item)
			{
				aplExtent instances;
				Item->GetAccessedInstances(instances);
				access = instances.GetAt(0)->GetAccessmode();
			}

			if(m_proc_tmpl->GetAccessmode()>aplRW || access>aplRO)
			{
				AfxMessageBox( APL_T("Нет доступа к объекту"));
				return false;
			}
			if(CaplDocTreeItem::InsertDoc(m_doc,this,&m_all_documents,i_doc,m_proc_tmpl, false))
				ShowCmd(ID_SHOW_ALL_DOCS);
		}
		else if(res == ID_DOCUMENT_BYDOT)
		{
			CaplInstance *inst = m_proc_tmpl;
			CaplInstance *i_doc = ((CaplDocTreeItem *)item)->m_inst;

			aplExtent instances;
			GetAccessedInstances(instances);
			if(m_doc->m_api.m_doc_mgr.CreateDocumentByDot(i_doc,instances[0]))
				ShowCmd(ID_SHOW_ALL_DOCS);
		}
		//премещение документа
		else if(res == ID_DOCUMENT_MOVE)
		{
			CaplDocTreeItem *d_item = (CaplDocTreeItem*)item;
			HTREEITEM parent = m_tree->GetNextItem(d_item->m_item,TVGN_PARENT);
			CaplTreeItem *parent_item = (CaplTreeItem*)m_tree->GetItemData(parent);

			CaplDocTreeItem::MoveDocument(m_doc, d_item, parent_item, this);
		}
	}
	m_tree->RedrawWindow();
	return true;
}