package cn.net.connor.std.processedit.newmeprocess;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.teamcenter.rac.aif.AbstractAIFApplication;
import com.teamcenter.rac.aif.kernel.AIFComponentContext;
import com.teamcenter.rac.aif.kernel.InterfaceAIFComponent;
import com.teamcenter.rac.kernel.SoaUtil;
import com.teamcenter.rac.kernel.TCComponent;
import com.teamcenter.rac.kernel.TCComponentFolder;
import com.teamcenter.rac.kernel.TCComponentItem;
import com.teamcenter.rac.kernel.TCComponentItemRevision;
import com.teamcenter.rac.kernel.TCComponentItemRevisionType;
import com.teamcenter.rac.kernel.TCComponentItemType;
import com.teamcenter.rac.kernel.TCException;
import com.teamcenter.rac.util.MessageBox;
import com.teamcenter.rac.util.Registry;
import com.teamcenter.services.rac.core.DataManagementService;
import com.teamcenter.services.rac.core._2008_06.DataManagement.CreateIn;
import com.teamcenter.services.rac.core._2008_06.DataManagement.CreateInput;
import com.teamcenter.services.rac.core._2008_06.DataManagement.CreateOut;
import com.teamcenter.services.rac.core._2008_06.DataManagement.CreateResponse;

import cn.net.connor.std.aifrcp.KDialogController;
import cn.net.connor.std.aifrcp.util.KUtil;
import cn.net.connor.std.processedit.util.OptionItem;
import cn.net.connor.std.processedit.util.ProcessUtil;

public class NewProcessDialogController extends KDialogController {

	private NewProcessDialog dialog;
	private TCComponentItemRevision targetRev;
	public static final String PREF_PREFIX = "Connor_AVIC_";
	public static final String PREF_GROUP_SPLITTER = "---";
	public static final String PROP_OBJECT_TYPE = "object_type";
	protected List<PrefComponent> procComps = new ArrayList<PrefComponent>();
	protected List<PrefComponent> itemComps = new ArrayList<PrefComponent>();
	private PrefComponent objectTypeComp;
	protected int procCols = 2;
	protected int itemCols = 2;
	public static final String PREF_PROCTYPE_SYMBOL = "Connor_AVIC_ProcType_Symbol";
	private Map<String, String> procTypeSymbolMap = new HashMap<String, String>();
	private Map<PrefComponent, String> symbolCompMap = new HashMap<PrefComponent, String>();
	public static final String FLAG_TYPE_SYMBOL = "[PROC_TYPE]";
	private static final Registry REG = Registry.getRegistry(NewProcessDialogController.class);

	public NewProcessDialogController(AbstractAIFApplication app) {
		super();
	}

	@Override
	public boolean init() throws Exception {
		this.dialog = (NewProcessDialog) aifDialog;
		InterfaceAIFComponent comp = app.getTargetComponent();
		if (comp == null || !(comp instanceof TCComponentItemRevision)) {
			throw new Exception(REG.getString("selectnewprocesstarget.ERROR"));
		}
		this.targetRev = (TCComponentItemRevision) comp;
		String revType = this.targetRev.getType();
		System.out.println("Select Rev: " + this.targetRev + "| " + revType);
		String prefName = PREF_PREFIX + revType;
		System.out.println("Load Preference: " + prefName);
		String[] prefVals = KUtil.getPrefVals(session, prefName);
		int len = KUtil.getLen(prefVals);
		if (len == 0) {
			System.out.println(String.format(REG.getString("prefnotconfiged.ERROR1"), prefName));
			throw new TCException(REG.getString("selectnewprocesstarget.ERROR"));
		}
		/*if (!"NHL8_VirtualPart".equals(this.targetRev.getItem().getType())) {
			TCComponent[] statusList = this.targetRev.getReferenceListProperty("release_status_list");
			System.out.println("Check Release Status: " + Arrays.toString(statusList));
			if (KUtil.getLen(statusList) < 1) {
				MessageBox.post(REG.getString("revreleased.ERROR"), "", MessageBox.WARNING);
				return false;
			}
		}*/
		List<PrefComponent> compList = procComps;
		for (int i = 0; i < len; i++) {
			String pref = prefVals[i];
			if (pref.length() == 1 && Character.isDigit(pref.charAt(0))) {
				if (compList == itemComps) {
					int col = pref.charAt(0) - '0';
					if (col > 0) {
						System.out.println("Reset Item Col: " + col);
						itemCols = col;
					}
				} else if (compList == procComps) {
					int col = pref.charAt(0) - '0';
					if (col > 0) {
						System.out.println("Reset Proc Col: " + col);
						procCols = col;
					}
				}
				continue;
			}
			if (pref.startsWith(PREF_GROUP_SPLITTER)) {
				compList = itemComps;
				continue;
			}
			PrefComponent prefComp = new PrefComponent(pref, this.targetRev);
			if (prefComp.init(session)) {
				if (PROP_OBJECT_TYPE.equals(prefComp.propConfig)) {
					this.objectTypeComp = prefComp;
					System.out.println("objectTypeComp.lov.length=="+objectTypeComp.lov.length);
					if(objectTypeComp.comboBox != null && objectTypeComp.lov.length == 1)
					{
						objectTypeComp.comboBox.setSelectedIndex(1);
					}
				}
				compList.add(prefComp);
			} else {
				System.out.println("Error Config: " + pref);
			}
		}
		if (procComps.size() + itemComps.size() == 0) {
			throw new Exception(String.format(REG.getString("prefnotconfiged.ERROR1"), prefName));
		}
		
		
		
		
		
		
		
		for (PrefComponent c : procComps) {
			if (c.textField != null && c.getValue() != null && c.getValue().contains(FLAG_TYPE_SYMBOL)) {
				this.symbolCompMap.put(c, c.getValue());
				c.textField.setText(c.getValue().replace(FLAG_TYPE_SYMBOL, ""));
			}
		}
		for (PrefComponent c : itemComps) {
			if (c.textField != null && c.getValue() != null && c.getValue().contains(FLAG_TYPE_SYMBOL)) {
				this.symbolCompMap.put(c, c.getValue());
				c.textField.setText(c.getValue().replace(FLAG_TYPE_SYMBOL, ""));
			}
		}
		
		
		
		
		
		for (int i = 0; i < itemComps.size(); i++) {
		    PrefComponent prefParent = itemComps.get(i);
		    if (prefParent.isLovParent) {
		        for (int j = 0; j < itemComps.size(); j++) {
		            PrefComponent prefChild = itemComps.get(j);
		            if (prefParent.lovName.equals(prefChild.lovName) && prefChild.isLovChild) {
		                prefParent.comboBox.addActionListener(new ActionListener() {
		                    @Override
		                    public void actionPerformed(ActionEvent e) {
		                        String selectedProvince = (String) prefParent.bigJtf.getText();
		                        if (selectedProvince != null) {
		                            List<String> cities = prefParent.listLov.get(selectedProvince);
		                            
		                            // 清空子级控件和数据
		                            prefChild.comboBox.removeAllItems();
		                            prefChild.opHashMap.clear();
		                            prefChild.lovDisRealMap.clear();
		                            prefChild.list.clear();

		                            if (cities != null && !cities.isEmpty()) {
		                                for (String city : cities) {
		                                    OptionItem optionItem = new OptionItem(city, "");
		                                    prefChild.comboBox.addItem(optionItem);
		                                    prefChild.opHashMap.put(city, optionItem);
		                                    prefChild.lovDisRealMap.put(city, city);
		                                    prefChild.list.add(city);
		                                }
		                                //  关键：不自动选中任何项
		                                prefChild.comboBox.setSelectedIndex(-1);
		                            } else {
		                                // 没有子项时也确保无选中
		                                prefChild.comboBox.setSelectedIndex(-1);
		                            }
		                        } else {
		                            prefChild.comboBox.removeAllItems();
		                            prefChild.comboBox.setSelectedIndex(-1); // 确保无选中
		                        }
		                    }
		                });
		            }
		        }
		    }
		}
		
		for (int i = 0; i < procComps.size(); i++) {
		    PrefComponent prefParent = procComps.get(i);
		    if (prefParent.isLovParent) {
		        for (int j = 0; j < procComps.size(); j++) {
		            PrefComponent prefChild = procComps.get(j);
		            if (prefParent.lovName.equals(prefChild.lovName) && prefChild.isLovChild) {
		                prefParent.comboBox.addActionListener(new ActionListener() {
		                    @Override
		                    public void actionPerformed(ActionEvent e) {
		                        String selectedProvince = (String) prefParent.bigJtf.getText();
		                        if (selectedProvince != null) {
		                            List<String> cities = prefParent.listLov.get(selectedProvince);
		                            
		                            // 清空子级控件和数据
		                            prefChild.comboBox.removeAllItems();
		                            prefChild.opHashMap.clear();
		                            prefChild.lovDisRealMap.clear();
		                            prefChild.list.clear();

		                            if (cities != null && !cities.isEmpty()) {
		                                for (String city : cities) {
		                                    OptionItem optionItem = new OptionItem(city, "");
		                                    prefChild.comboBox.addItem(optionItem);
		                                    prefChild.opHashMap.put(city, optionItem);
		                                    prefChild.lovDisRealMap.put(city, city);
		                                    prefChild.list.add(city);
		                                }
		                                //  关键：不自动选中任何项
		                                prefChild.comboBox.setSelectedIndex(-1);
		                            } else {
		                                // 没有子项时也确保无选中
		                                prefChild.comboBox.setSelectedIndex(-1);
		                            }
		                        } else {
		                            prefChild.comboBox.removeAllItems();
		                            prefChild.comboBox.setSelectedIndex(-1); // 确保无选中
		                        }
		                    }
		                });
		            }
		        }
		    }
		}
		
		
		{
			String[] prefVals2 = KUtil.getPrefVals(session, PREF_PROCTYPE_SYMBOL);
			int len2 = KUtil.getLen(prefVals2);
			for (int i = 0; i < len2; i++) {
				String pref = prefVals2[i];
				int ind = pref.indexOf('=');
				if (ind > 0) {
					String type = pref.substring(0, ind);
					String symbol = pref.substring(ind + 1);
					System.out.println("Type Symbol: " + type + " -> " + symbol);
					this.procTypeSymbolMap.put(type, symbol);
				}
			}
		}
		if (this.symbolCompMap.size() > 0 && this.objectTypeComp != null && this.objectTypeComp.comboBox != null) {
			this.objectTypeComp.comboBox.addActionListener(new ActionListener() {
				@Override
				public void actionPerformed(ActionEvent arg0) {
					String type = objectTypeComp.getValue();
					String symbol = procTypeSymbolMap.containsKey(type) ? procTypeSymbolMap.get(type) : "";
					System.out.println("Select Type: " + type + " -> " + symbol);
					for (PrefComponent c : symbolCompMap.keySet()) {
						String text = symbolCompMap.get(c);
						System.out.println(text);
						text = text.replace(FLAG_TYPE_SYMBOL, symbol);
						c.textField.setText(text);
					}

				}
			});
		}
		return true;
	}

	public void doCreate() throws Exception {
		if (this.objectTypeComp == null) {
			throw new Exception(REG.getString("typecompnotfound.ERROR"));
		}
		String type = this.objectTypeComp.getValue();
		System.out.println("Select Type: " + type);
		if (KUtil.isEmpty(type)) {
			throw new Exception(REG.getString("selectType.INFO"));
		}
		String relName = this.objectTypeComp.getAddtionalValue();
		System.out.println("Create Relation: " + relName);
		String archiveRelation = "";
		if(KUtil.isEmpty(relName)) {
			throw new Exception(REG.getString("typecompnotfound.ERROR"));
		}
		int ind = relName.indexOf('-');
		if (ind > 0) {
			archiveRelation = relName.substring(ind + 1);
			relName = relName.substring(0, ind);
		}
		if (KUtil.isEmpty(archiveRelation)) {
			throw new Exception(REG.getString("typecompnotfound.ERROR"));
		}
		if(type.equals("LD6_MEProcessCr")) {
			AIFComponentContext[] cs = ((TCComponent)targetRev.getChildren(archiveRelation)[0].getComponent()).getChildren();
			System.out.println("getChildren: " + cs.length);
			int n = 0;
			for(AIFComponentContext c : cs) {
				if(c.getComponent().getType().equals("LD6_MEProcessCr"))
					n++;
			}
			if(n >= 3) {
				throw new Exception(REG.getString("relation.ERROR"));
			}
		}
		TCComponentItemType itemType = (TCComponentItemType) session.getTypeComponent(type);
		if (itemType == null) {
			throw new Exception(String.format(REG.getString("typenotfound.ERROR1"), type));
		}
		String checkRequire = checkRequire();
		
		
		if (!checkRequire.equals("")) {
			
			throw new Exception(String.format(REG.getString("requireprop.INFO1"), checkRequire));
		}
		
		String checkCombox = checkCombox();
		
	
		
		
System.out.println("checkCombox==="+checkCombox);
		
		if (!checkCombox.equals("")) {
			
			throw new Exception(checkCombox);
		}
		
		
		
		boolean addedToNewRev = false;
		try {
			KUtil.setByPassItk(session, true);
			TCComponentItemRevisionType revType = itemType.getItemRevisionType();
			String revTypeName = revType.getName();
			String itemMasterTypeName = type + " Master";
			String revMasterTypeName = revTypeName + " Master";
			if (session.getTypeComponent(itemMasterTypeName) == null) {
				itemMasterTypeName = type + "Master";
			}
			if (session.getTypeComponent(revMasterTypeName) == null) {
				revMasterTypeName = revTypeName + "Master";
			}
			System.out.println("Revision Type: " + type);
			System.out.println("Item Master Type: " + itemMasterTypeName);
			System.out.println("Revision Master Type: " + revMasterTypeName);
			Map<String, String> revPropMap = new HashMap<>();
			Map<String, String> revMasterPropMap = new HashMap<>();
			Map<String, String> itemPropMap = new HashMap<>();
			Map<String, String> itemMasterPropMap = new HashMap<>();
			for (PrefComponent prefComponent : itemComps) {
				KUtil.initPropMap(prefComponent.propConfig, prefComponent.getValue(), itemPropMap, itemMasterPropMap, revPropMap, revMasterPropMap);
			}
			for (PrefComponent prefComponent : procComps) {
				KUtil.initPropMap(prefComponent.propConfig, prefComponent.getValue(), itemPropMap, itemMasterPropMap, revPropMap, revMasterPropMap);
			}
			CreateInput revMasterInput = new CreateInput();
			revMasterInput.boName = revMasterTypeName;
			revMasterInput.stringProps = revMasterPropMap;
			if ("NHL8_AssemblyPro".equals(type) && "NHL8_VirtualPart".equals(targetRev.getItem().getType())) {
				System.out.println(">> set nhl8_isFcheck = true");
				System.out.println(">> set nhl8_isfPass = true");
				revMasterInput.boolProps = new HashMap<>();
				revMasterInput.boolProps.put("nhl8_isFcheck", true);
				revMasterInput.boolProps.put("nhl8_isfPass", true);
			}
			CreateInput itemMasterInput = new CreateInput();
			itemMasterInput.boName = itemMasterTypeName;
			itemMasterInput.stringProps = itemMasterPropMap;
			CreateInput revInput = new CreateInput();
			revInput.boName = revTypeName;
			revInput.stringProps = revPropMap;
			Map<String, CreateInput[]> revMasterInfoMap = new HashMap<>();
			revMasterInfoMap.put("IMAN_master_form_rev", new CreateInput[] { revMasterInput });
			revInput.compoundCreateInput = revMasterInfoMap;
			// create rev
			CreateInput itemInput = new CreateInput();
			itemInput.boName = type;
			itemInput.stringProps = itemPropMap;
			Map<String, CreateInput[]> revInfoMap = new HashMap<>();
			revInfoMap.put("revision", new CreateInput[] { revInput });
			revInfoMap.put("IMAN_master_form", new CreateInput[] { itemMasterInput });
			itemInput.compoundCreateInput = revInfoMap;
			// create info
			CreateIn cI = new CreateIn();
			cI.clientId = "CreateItem";
			cI.data = itemInput;
			// service
			DataManagementService service = DataManagementService.getService(session);
			// create
			CreateResponse resp = service.createObjects(new CreateIn[] { cI });
			SoaUtil.checkPartialErrors(resp.serviceData);
			CreateOut[] cOs = resp.output;
			TCComponentItem newItem = null;
			if (cOs.length > 0) {
				for (TCComponent s : cOs[0].objects) {
					if (s instanceof TCComponentItem) {
						newItem = (TCComponentItem) s;
					}
				}
			}
			System.out.println("New Item: " + newItem);
			if (newItem == null) {
				throw new Exception(REG.getString("createprocess.ERROR"));
			}
			newItem.refresh();
			TCComponentItemRevision newRev = newItem.getLatestItemRevision();
			System.out.println("New Rev: " + newRev);
			ProcessUtil.switchToPrecise(session, newRev);
			addedToNewRev = false;
			if (newRev != null) {
				try {
					newRev.add(relName, this.targetRev);
					newRev.refresh();
					this.targetRev.add(archiveRelation, newItem);
					this.targetRev.refresh();
					addedToNewRev = true;
				} catch (Exception e) {
					e.printStackTrace();
					MessageBox.post(dialog, e.getMessage(), "错误", MessageBox.ERROR);
				}
			}
			if (!addedToNewRev) {
				TCComponentFolder folder = session.getUser().getNewStuffFolder();
				folder.add("contents", newItem);
				folder.refresh();
			}
			MessageBox.post(dialog, addedToNewRev ? REG.getString("newprocesscomplete.INFO") : REG.getString("newprocesscomplete.ERROR"), "", MessageBox.INFORMATION);
		} catch (Exception e) {
			e.printStackTrace();
			MessageBox.post(dialog, e.getMessage(), "错误", MessageBox.ERROR);
		} finally {
			KUtil.setByPassItk(session, false);
		}
	}

	private String checkRequire() {
		List<String> requireTitles = new ArrayList<String>();
		for (PrefComponent prefComponent : itemComps) {
			if (!prefComponent.checkRequire()) {
				requireTitles.add(prefComponent.title.replace(" ", "").replace(":", "").replace(REG.getString("CN_SYMBEL4"), "").replace(REG.getString("CN_SYMBEL5"), ""));
			}
		}
		for (PrefComponent prefComponent : procComps) {
			if (!prefComponent.checkRequire()) {
				requireTitles.add(prefComponent.title.replace(" ", "").replace(":", "").replace(REG.getString("CN_SYMBEL4"), "").replace(REG.getString("CN_SYMBEL5"), ""));
			}
		}
		if (requireTitles.size() > 0) {
			//MessageBox.post(dialog, String.format(REG.getString("requireprop.INFO1"), requireTitles.toString()), "", MessageBox.WARNING);
			return requireTitles.toString();
		}
		return "";
	}
	
	private String checkCombox() {
		List<String> requireTitles = new ArrayList<String>();
		for (PrefComponent prefComponent : itemComps) {
			if (!prefComponent.checkCombox()) {
				requireTitles.add(prefComponent.title+"请选择下拉值!");
			}
		}
		for (PrefComponent prefComponent : procComps) {
			if (!prefComponent.checkCombox()) {
				requireTitles.add(prefComponent.title+"请选择下拉值!");			}
		}
		if (requireTitles.size() > 0) {
			//MessageBox.post(dialog, String.format(REG.getString("requireprop.INFO1"), requireTitles.toString()), "", MessageBox.WARNING);
			return requireTitles.toString();
		}
		return "";
	}

}
