using System; using System.Collections; using System.Collections.Generic; using System.ComponentModel; using System.Drawing; using System.Data; using System.Text; using System.Windows.Forms; using System.Text.RegularExpressions; using AT.STO.UI.Win; using VEPROMS.CSLA.Library; using Volian.Base.Library; namespace Volian.Controls.Library { public partial class DisplayTransition : UserControl { private static readonly log4net.ILog _MyLog = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); #region Properties private int _TranFmtIndx = -1; // stores selected transition format private ItemInfo _CurItemFrom; // stores what item transition is 'from' private TransitionInfo _CurTrans; // if modify, this is transition to modify public TransitionInfo CurTrans { get { return _CurTrans; } set { if (!Visible) return; if (value == null) // Insert a transition { if (MyRTB == null) return; if (_CurTrans == value && _CurItemFrom == MyRTB.MyItemInfo) return; _CurItemFrom = MyRTB.MyItemInfo; _TranFmtIndx = 0; bool isenh = MyRTB != null && MyRTB.MyItemInfo != null && MyRTB.MyItemInfo.IsEnhancedStep; btnTranSave.Enabled = !isenh && UserInfo.CanEdit(MyUserInfo, Mydvi); //Can Insert Transitons btnTranCancel.Enabled = true; } else // Modify a transition { if (_CurTrans == value) return; _TranFmtIndx = value.TranType; _CurItemFrom = MyRTB.MyItemInfo; btnTranSave.Enabled = btnTranCancel.Enabled = false; } _CurTrans = value; _SavCurItemFrom = _CurItemFrom; _SavTranFmtIndx = _TranFmtIndx; TransitionFillIn(); SaveSettings(); } } private int _II_Format; private bool _II_PageNumber; private bool _II_IncStepNumber; private int _II_Procedure; private int _II_Section; private int _II_ItemID; private void SaveSettings() { _II_Format=listBoxTranFmt.SelectedIndex; _II_PageNumber=cbPageNum.Checked; _II_IncStepNumber=cbIncStepNum.Checked; _II_Procedure=cbTranProcs.SelectedIndex; _II_Section=cbTranSects.SelectedIndex; // Use VEObject if (tvTran.SelectedNode != null && (tvTran.SelectedNode as VETreeNode).VEObject != null) _II_ItemID = ((tvTran.SelectedNode as VETreeNode).VEObject as ItemInfo).ItemID; } private bool SettingsChanged { get { if (_CurTrans == null) return true; if (_II_Format != listBoxTranFmt.SelectedIndex) return true; if (_II_PageNumber != cbPageNum.Checked) return true; if (_II_IncStepNumber != cbIncStepNum.Checked) return true; if (_II_Procedure != cbTranProcs.SelectedIndex) return true; if (_II_Section != cbTranSects.SelectedIndex) return true; // Use VEObject if (_II_ItemID != ((tvTran.SelectedNode as VETreeNode).VEObject as ItemInfo).ItemID) return true; return false; } } // use the following if user selects 'cancel' button private ItemInfo _SavCurItemFrom; private int _SavTranFmtIndx; private bool _ModExistingPageNum = false; private bool _DoingRange = false; // flags if in 'range' transition mode private VETreeNode _RangeNode1; private VETreeNode _RangeNode2; // Use _RangeColor to show highlighting for steps selected in range. This is set from // calling methods from application settings. If not default to aquamarine. private Color _RangeColor = Color.LightGray; public Color RangeColor { get { return _RangeColor; } set { _RangeColor = value; } } private StepRTB _MyRTB; // Current MyDisplayRTB, i.e. insert transition to it. public StepRTB MyRTB { get { return _MyRTB; } set { if (!Visible) return; // add or remove events for if (_MyRTB != null) _MyRTB.LinkChanged -= new StepRTBLinkEvent(_MyRTB_LinkChanged); if (value == null) return; _MyRTB = value; _MyRTB.LinkChanged += new StepRTBLinkEvent(_MyRTB_LinkChanged); if (_MyRTB.MyLinkText == null) { CurTrans = null; } } } void _MyRTB_LinkChanged(object sender, StepPanelLinkEventArgs args) { //if (_MyRTB.MyLinkText == null) // CurTrans = null; //else //{ // StepPanelLinkEventArgs tmp = new StepPanelLinkEventArgs(null, e); CurTrans = args.MyLinkText.MyTransitionInfo; //} } private ItemInfo _CurrentItemProcedure; // the selected item's procedure private ItemInfo _CurrentToProcedure; // the 'to' location's procedure (may be same as _CurrentItemProcedure) private ItemInfo _CurrentProcedure; // current procedure used to set all of the controls (may switch between above two) private int _CurrentProcIndex; private bool _AlwaysDisableSets; // true if there is only 1 item in tree/combo for sets private Color _OrigGroupPanelSets; private Color _OrigGroupPanelProcs; private Color _OrigGroupPanelSects; private Color _OrigGroupPanelSteps; #endregion #region Constructors public DisplayTransition() { InitializeComponent(); } #endregion #region LoadControlData // TransitionFillIn uses other methods to fill in all controls on the transition tab. private bool _InitializingTrans; private void TransitionFillIn() { _InitializingTrans = true; if (_RangeNode1 != null || _RangeNode2 != null) ClearRangeTransition(); InitControls(); btnTranCancel.Enabled = false; _InitializingTrans = false; } private void InitControls() { _OrigGroupPanelSets = groupPanelTransitionSets.Style.BackColor; _OrigGroupPanelProcs = groupPanelTransitionProcs.Style.BackColor; _OrigGroupPanelSects = groupPanelTransitionSect.Style.BackColor; _OrigGroupPanelSteps = groupPanelTranstionSteps.Style.BackColor; ListBoxTranFmtFillIn(); // if new, use _CurItemFrom to setup the initial selections in the controls, // if modify, use the first transition to, _CurTrans // This item will be either a procedure, section or step, never a docversion ItemInfo selitm = _CurTrans==null?_CurItemFrom:_CurTrans.MyItemToID; // If this points to an invalid transtion, make it point to itself. if (selitm.PreviousID == null && selitm.ItemPartCount == 0 && selitm.ItemDocVersionCount == 0) { selitm = _CurItemFrom; } ItemInfo tmpitm = selitm; ItemInfo secitm = null; // Find the procedure level first. if (tmpitm.MyContent.Type == 0) // If at the procedure level then need to set the default section { int scid = FindSectionStart(tmpitm); if(scid > 0) secitm = SectionInfo.Get(scid); } else { while (tmpitm.MyContent.Type != 0) { if (tmpitm.MyContent.Type >= 10000 && tmpitm.MyContent.Type < 20000 && secitm == null) secitm = tmpitm; tmpitm = tmpitm.MyParent; } } _CurrentProcedure = tmpitm; _CurrentToProcedure = _CurrentProcedure; if (_CurTrans == null) _CurrentItemProcedure = _CurrentProcedure; else { // use the transition from to get the procedure 'from'.... ItemInfo curfrom = _CurItemFrom; while (curfrom.MyContent.Type != 0) curfrom = curfrom.MyParent; _CurrentItemProcedure = curfrom; } // set other procedure related private variables. vlnTreeComboSetsFillIn(_CurrentProcedure); cbTranProcsFillIn(_CurrentProcedure); if (_CurrentProcedure.Sections != null) { // if the selected format is using section default, initialize with the section default (find it), // otherwise use current section item. int secStartId = secitm.ItemID; E_TransUI etm = (E_TransUI)_CurrentProcedure.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[_TranFmtIndx].TransUI; if ((etm & E_TransUI.SectDefault) == E_TransUI.SectDefault) { secStartId = FindSectionStart(_CurrentProcedure); if (secStartId > -1) { secitm = ItemInfo.Get(secStartId); selitm = (secitm.Steps != null && secitm.Steps.Count > 0) ? secitm.Steps[0] : null; } else btnTranSave.Enabled = false; // if there is an invalid section start - don't allow save. } cbTranSectsFillIn(secitm, secitm == null ? -1 : secStartId, true); // Fill step items, passing in the active step to the selected item, or the first // step if the selection was not at the step level. ItemInfo stpitm = null; if (selitm != null && selitm.MyContent.Type >= 20000) { if (_DoingRange) { tvInitHiliteRange(); //rangeSameLevel, stpitm, rngitm, (i1 < i2) ? i2 : i1); } else stpitm = selitm; } else if (secitm != null && secitm.Steps != null && secitm.Steps.Count > 0) stpitm = selitm.Steps[0]; if (!_DoingRange) tvTranFillIn(stpitm); // range code fills in tree. //if (_DoingRange) tvInitHiliteRange(rangeSameLevel, stpitm, rngitm, (i1 < i2) ? i2 : i1); } else { cbTranSects.Items.Clear(); tvTran.Nodes.Clear(); } SetControlsEnabling(); } private void tvInitHiliteRange() //bool rangeSameLevel, ItemInfo stpitm, ItemInfo rngitm, int uplevel) { ItemInfo toItm = _CurTrans.MyItemToID; ItemInfo rngItm = null; // figure out whether at same level, have same parent and have same HLS: ItemInfo itm1 = _CurTrans.MyItemToID; ItemInfo itm2 = _CurTrans.MyItemRangeID; // Invalid existing transition if (itm2.ActiveParent == null || itm1.ActiveParent == null) return; //if (_CurTrans.TranType == 2 && itm1.ItemID == itm2.ItemID) itm2 = itm1.LastSibling; bool samHLS = itm1.MyHLS.ItemID == itm2.MyHLS.ItemID; int lev1 = 0; int lev2 = 0; while (!itm1.IsHigh) { lev1++; itm1 = itm1.MyParent; } while (!itm2.IsHigh) { lev2++; itm2 = itm2.MyParent; } bool samLevel = lev1 == lev2; // For each range item, go to common level's parent. int cnt = lev1+1; ItemInfo sameParent1 = _CurTrans.MyItemToID; ItemInfo sameParent2 = _CurTrans.MyItemRangeID; if (_CurTrans.TranType == 2 && sameParent1.ItemID == sameParent2.ItemID) sameParent2 = sameParent1.LastSibling; while (cnt != 0) { if (sameParent1.IsHigh) break; sameParent1 = sameParent1.MyParent; } cnt = lev2+1; while (cnt != 0) { if (sameParent2.IsHigh) break; sameParent2 = sameParent2.MyParent; } tvTranFillIn(sameParent1); // if HLS, fill in from there, or it will fill in from common parent // now add nodes for the subtrees so that highlighting can be done. Do 'to' item // first. If 'range' item is at same level, won't need to do anymore processing. ItemInfo toItem = sameParent1.Ordinal<=sameParent2.Ordinal?_CurTrans.MyItemToID:_CurTrans.MyItemRangeID; ItemInfo rngItem = null; if (_CurTrans.TranType == 2 && _CurTrans.MyItemToID == _CurTrans.MyItemRangeID) { rngItem = sameParent1.Ordinal <= sameParent2.Ordinal ? _CurTrans.MyItemToID.LastSibling : _CurTrans.MyItemToID; } else rngItem = sameParent1.Ordinal <= sameParent2.Ordinal ? _CurTrans.MyItemRangeID : _CurTrans.MyItemToID; List path = new List(); ItemInfo parRng = toItem; for (int i = 0; i < lev1+1; i++) { path.Insert(i, parRng); parRng = (ItemInfo)parRng.ActiveParent; } // Find sameParent1 in tree, expand down to toItem: if (tvTran.Nodes.Count == 0) return; tvFillInRangeNodes(path, (VETreeNode)tvTran.Nodes[0], lev1, true); path.Clear(); parRng = rngItem; for (int i = 0; i < lev2 + 1; i++) { path.Insert(i, parRng); parRng = (ItemInfo)parRng.ActiveParent; } tvFillInRangeNodes(path, (VETreeNode)tvTran.Nodes[0], lev2, false); tvTranRangeHilites(true, _RangeNode1, _RangeNode2); tvTran.SelectedNode = _RangeNode1; } private void tvFillInRangeNodes(List path, VETreeNode tn, int level, bool to) { VETreeNode tnExpand = null; while (tnExpand == null && tn != null) { ItemInfo ii = (ItemInfo)tn.VEObject; if (ii.ItemID == path[level].ItemID) tnExpand = tn; tn = (VETreeNode)tn.NextNode; } tnExpand.LoadChildren(false); if (level > 0) { tnExpand.Expand(); tvFillInRangeNodes(path, (VETreeNode)tnExpand.Nodes[0], level - 1, to); } else { if (to) _RangeNode1 = tnExpand; else _RangeNode2 = tnExpand; } } private void vlnTreeComboSetsFillIn(ItemInfo prcitm) { // from this procedure, walk up the tree storing the FolderInfos. This is done // so that the tree can be expanded highlighting (selecting) the current set. List filist = new List(); DocVersionInfo mydocversion = prcitm.ActiveParent as DocVersionInfo; Mydvi = mydocversion; // used for security check FolderInfo tmpfi = mydocversion.ActiveParent as FolderInfo; while (tmpfi != null) { if (tmpfi.FolderID != 1) filist.Add(tmpfi); // don't add top folder tmpfi = tmpfi.ActiveParent as FolderInfo; } // Now start at the top folder. Continue to get children using the filist to determine // the expanded part of the tree. Note that if there is only 1 item at a level, // the level is not added to the tree, except if there are no sub-folders, i.e. // right before the docversion. Also note that docversions are not displayed // (at least for now - as of 2/14/08), this may change and if so uncomment (& fix/test) // the next section of code where docversions are processed. FolderInfo fi = FolderInfo.GetTop(); DropDownNode topnode = null; int cntnd = 0; while (fi.ChildFolderCount > 0) { // if there is more than 1 child, add this level of children to the // to the tree. The second part of the 'if' covers the last level of // folder. if ((fi.ChildFolders.Count > 1) || (fi.ChildFolders.Count==1 && fi.ChildFolders[0].FolderDocVersionCount>0)) { int indx = -1; int pathid = filist[filist.Count - 1].FolderID; foreach (FolderInfo fic in fi.ChildFolders) { DropDownNode newnode = new DropDownNode(fic.FolderID, fic.ToString()); int tmp = topnode==null?vlnTreeComboSets.DropDownControl.Nodes.Add(newnode):topnode.Nodes.Add(newnode); cntnd++; newnode.Tag = fic; if (fic.FolderID == pathid) indx = tmp; // flag the path to expand. else if (fic.ChildFolderCount > 0) // allow for '+' for tree expansion { DropDownNode tnt = new DropDownNode(0, "VLN_DUMMY"); newnode.Nodes.Add(tnt); } } topnode = topnode==null?(DropDownNode)vlnTreeComboSets.DropDownControl.Nodes[indx]:(DropDownNode)topnode.Nodes[indx]; } fi = (filist.Count > 0) ? FolderInfo.Get(filist[filist.Count - 1].FolderID) : null; if (filist.Count > 0) filist.RemoveAt(filist.Count - 1); } // if nothing was added to the tree, just put in the node above the docversions... if (vlnTreeComboSets.DropDownControl.Nodes.Count == 0) { cntnd++; fi = mydocversion.MyFolder; topnode = new DropDownNode(fi.FolderID, fi.ToString()); vlnTreeComboSets.DropDownControl.Nodes.Add(topnode); topnode.Tag = fi; } // if there is only one node in entire tree, disable selection... if (cntnd == 1) _AlwaysDisableSets = true; else _AlwaysDisableSets = false; // the following selects the set & displays its value in the combo box portion // of the tree combo control. vlnTreeComboSets.Value = topnode; vlnTreeComboSets.DropDownControl.SelectedNode = topnode; vlnTreeComboSets.DropDownControl.BeforeExpand += new TreeViewCancelEventHandler(vlnTreeComboSets_BeforeExpand); #region CheckIfNeeded Commented Out //vlnTreeComboSets.DropDownControl. = vlnTreeComboSets.Width; // The DropDownNode should be at a DocVersion now. The expanded DocVersion // is the one that matches mydocversion //tmpfi = mydocversion.ActiveParent as FolderInfo; //DocVersionInfoList dvlist = tmpfi.FolderDocVersions; //DropDownNode tnDV = null; // Once at a docversions, only allow working // draft sets. Use DocVersion that we're in, to expand it showing the active procedure. // first count how many versions can be displayed, i.e. only workingdraft? // if more than one, put out a tree node for them. //int cntdocv = 0; //foreach (DocVersionInfo dv in dvlist) //{ // if ((VersionTypeEnum)dv.VersionType == VersionTypeEnum.WorkingDraft) cntdocv++; //} //if (cntdocv>1) //{ // foreach (DocVersionInfo dv in dvlist) // { // if ((VersionTypeEnum)dv.VersionType == VersionTypeEnum.WorkingDraft) // { // DropDownNode tn = new DropDownNode(dv.VersionID, dv.ToString()); // tn.Tag = dv; // if (topnode != null) // topnode.Nodes.Add(tn); // else // vlnTreeComboSets.DropDownControl.Nodes.Add(tn); // if (dv.VersionID == mydocversion.VersionID) // { // tnDV = tn; // vlnTreeComboSets.Value = tnDV; // vlnTreeComboSets.DropDownControl.SelectedNode = tnDV; // } // //else if (dv.HasChildren) // allow for '+' for tree expansion // //{ // // DropDownNode tnt = new DropDownNode(0,"VLN_DUMMY"); // // tn.Nodes.Add(tnt); // //} // } // } //} #endregion } private void ListBoxTranFmtFillIn() { TransTypeList ttl = _CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList; listBoxTranFmt.Items.Clear(); for (int i = 0; i < ttl.MaxIndex; i++) listBoxTranFmt.Items.Add(new TransItem(ttl[i].TransMenu.Replace("?.",""),ttl[i].TransFormat.Replace("?.",""))); //listBoxTranFmt.Items.Add(ttl[i].TransFormat.Replace("?.","")); listBoxTranFmt.SelectedIndex = _TranFmtIndx; groupPanelTranFmt.Style.BackColor = (_CurTrans == null && _TranFmtIndx==0) ? Color.Yellow : Color.Orange; E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[_TranFmtIndx].TransUI; _DoingRange = (etm & E_TransUI.StepLast) == E_TransUI.StepLast; } private void tvTranFillIn(ItemInfo startitm) { tvTran.Nodes.Clear(); groupPanelTranstionSteps.Style.BackColor = _OrigGroupPanelSteps; if (startitm == null) return; // if metasections, and the selected section's config item has noneditable data, then don't // display any steps. ItemInfo secitm = (ItemInfo)cbTranSects.SelectedItem; bool hasMetaSubs = secitm.IsSection && secitm.Sections != null && secitm.Sections.Count > 0; bool editSteps = !hasMetaSubs || (secitm.MyConfig is SectionConfig && (secitm.MyConfig as SectionConfig).SubSection_Edit == "Y"); if (!editSteps) return; // if the transition to point is a section or procedure, just return if (startitm.MyContent.Type < 20000) return; groupPanelTranstionSteps.Style.BackColor = Color.Cornsilk; // For the tree view, use parent, unless already at HLS. If at HLS, use this level. ItemInfo selitm = startitm.MyHLS; //if (_CurTrans == null)selitm = startitm.MyHLS; E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[listBoxTranFmt.SelectedIndex].TransUI; if (startitm.IsInRNO) startitm = selitm.FirstSibling; // if in RNO tree, start out with HLS else startitm = selitm!=null? selitm.FirstSibling:startitm.FirstSibling; bool setsel = false; while (startitm != null) { VETreeNode tvn = new VETreeNode(startitm, false); tvn.Tag = startitm; int active = this.tvTran.Nodes.Add(tvn); if (selitm !=null && startitm.ItemID == selitm.ItemID) { tvTran.SelectedNode = tvTran.Nodes[active]; setsel = true; } startitm = (startitm.NextItem != null && startitm.NextItems.Count > 0 ? startitm.NextItems[0] : null); } if (!setsel) tvTran.SelectedNode = tvTran.Nodes[0]; tvTran.BeforeExpand += new TreeViewCancelEventHandler(tvTran_BeforeExpand); // bug fix. TreeView needs the next two lines to properly display the bottom node. jsj 01/08/2010 tvTran.ItemHeight++; tvTran.ItemHeight--; } private int savSecStart; private void cbTranSectsFillIn(ItemInfo secitm, int secstart, bool clear) { if (clear) cbTranSects.Items.Clear(); // if the transition points 'to' procedure, don't list the sections yet. if (secitm == null || secitm.MyContent.Type < 10000) return; // if sectstart is not -1, then use this as the section to select, otherwise // use the id for the item passed in. int startitm = secstart; if (clear && secstart < 0) secstart = secitm.ItemID; ItemInfo selitm = secitm; // this is the selected 'section' secitm = secitm.FirstSibling; while (secitm != null) { // if the selected transition format requires a step be selected (show only step sections), only add step sections E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[listBoxTranFmt.SelectedIndex].TransUI; if (((!((etm & E_TransUI.StepAllowNone) == E_TransUI.StepAllowNone)) && secitm.IsStepSection) || ((etm & E_TransUI.StepAllowNone) == E_TransUI.StepAllowNone)) { int active = cbTranSects.Items.Add(secitm); if (secitm.ItemID == secstart) cbTranSects.SelectedIndex = active; } if (secitm.Sections != null && secitm.Sections.Count > 0) cbTranSectsFillIn(secitm.Sections[0], secstart, false); secitm = (secitm.NextItem != null && secitm.NextItems.Count > 0 ? secitm.NextItems[0] : null); } if (cbTranSects.SelectedIndex == -1) cbTranSects.SelectedIndex = 0; cbTranSects.Refresh(); } private void cbTranProcsFillIn(ItemInfo prcitm) { cbTranProcs.Items.Clear(); ItemInfo selitm = prcitm; // this is the selected 'procedure' prcitm = prcitm.FirstSibling; while (prcitm != null) { int active = cbTranProcs.Items.Add(prcitm); if (_CurrentProcedure.ContentID == prcitm.MyContent.ContentID) _CurrentProcIndex = active; if (prcitm.MyContent.ContentID == selitm.MyContent.ContentID) cbTranProcs.SelectedIndex = active; prcitm = (prcitm.NextItem != null && prcitm.NextItems.Count > 0 ? prcitm.NextItems[0] : null); } } private void SetControlsEnabling() { groupPanelTransitionSets.Style.BackColor = _OrigGroupPanelSets; groupPanelTransitionProcs.Style.BackColor = _OrigGroupPanelProcs; groupPanelTransitionSect.Style.BackColor = _OrigGroupPanelSects; // Based on selection & enum representing the transition format, determine the enabling of associated controls if (_CurItemFrom == null) return; int indx = listBoxTranFmt.SelectedIndex; if (listBoxTranFmt.SelectedIndex < 0 || listBoxTranFmt.SelectedIndex > listBoxTranFmt.Items.Count) indx = 0; E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[indx].TransUI; // do the set tree/combo & procedure combo. in 16-bit system it was types 0, 3, 5 vlnTreeComboSets.Enabled = false; if ((etm & E_TransUI.ProcMenu) == E_TransUI.ProcMenu) { if (!_AlwaysDisableSets) { vlnTreeComboSets.Enabled = true; groupPanelTransitionSets.Style.BackColor = Color.Cornsilk; } cbTranProcs.Enabled = true; groupPanelTransitionProcs.Style.BackColor = Color.Cornsilk; } else { cbTranProcs.SelectedIndex = _CurrentProcIndex > 0 ? _CurrentProcIndex : 0; cbTranProcs.Enabled = false; } // Do section combo, in 16-bit system it was types 0, 3, 4, 5 if (cbTranSects.Items.Count > 0 && ( (((etm & E_TransUI.SectDefault) == E_TransUI.SectDefault && _CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.DoSectionTransitions) || ((etm & E_TransUI.SectMenuAny) == E_TransUI.SectMenuAny) || ((etm & E_TransUI.SectMenuStep) == E_TransUI.SectMenuStep)))) { cbTranSects.Enabled = true; groupPanelTransitionSect.Style.BackColor = Color.Cornsilk; } else { cbTranSects.Enabled = false; } // check for range - if no range, then range button/label & step tree selections should be // 'cleared/invisble'. btnTranRangeClear.Visible = _DoingRange; lblxTranRangeTip.Visible = _DoingRange; if (_DoingRange) { lblxTranRangeTip.BackColor = Color.Yellow; } // if any previous nodes selected for range - clear them here if (!_DoingRange && _RangeNode1 != null) ClearRangeTransition(); // Always allow for step selection if there are items. if (tvTran.Nodes.Count > 0) tvTran.Enabled = true; // if a step doesn't need to be specified, then show the cbIncStepNum which allows // user to define whether a step number is to be included in transition. if ((etm & E_TransUI.StepAllowNone) == E_TransUI.StepAllowNone) { cbIncStepNum.Visible = true; // may or may not allow steps to be selected, i.e. if this is checked then enable // tree view for step selection: cbIncStepNum.Checked = true; if (_CurTrans != null && _CurTrans.MyItemToID.MyContent.Type < 20000) { cbIncStepNum.Checked = false; tvTran.Enabled = false; } // the following test is for Section/Optional Step (type 4 and related). If is a step section and its // the only step section in the procedure then a step number must be selected. int cntsect = 0; foreach (ItemInfo ii in _CurItemFrom.MyProcedure.Sections) if (ii.IsStepSection) cntsect++; if (((etm & E_TransUI.ProcCur) == E_TransUI.ProcCur) && ((etm & E_TransUI.SectMenuAny) == E_TransUI.SectMenuAny) && cntsect==1) { tvTran.Enabled = true; cbIncStepNum.Visible = false; } } else cbIncStepNum.Visible = false; // if this format has the transition flag for UseTransitionModifier, i.e. page numbers included in transition text, // then make visible the checkbox & set based on data. // and transition type has to be (tranType==1||tranType==2||tranType==4)) cbPageNum.Visible = _CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.UseTransitionModifier && (_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[indx].Type == 1 || _CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[indx].Type == 2 || _CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[indx].Type == 4); cbPageNum.Checked = false; if (cbPageNum.Visible) { if (CurTrans != null) { TransitionConfig tc = new TransitionConfig(CurTrans.Config); cbPageNum.Checked = _ModExistingPageNum = tc != null && tc.Transition_Formatted.ToUpper() == "TRUE"; } } } #endregion #region Events private void vlnTreeComboSets_BeforeExpand(object sender, TreeViewCancelEventArgs e) { DropDownNode par = ((DropDownNode)e.Node); // get first child's text, if it has one & if the text is VLN_DUMMY, load children DropDownNode tn = null; if (par.Nodes.Count > 0) tn = (DropDownNode)par.Nodes[0]; if (tn.Text == "VLN_DUMMY") // expand this { par.Nodes.Clear(); Object obj = par.Tag; if (!(obj is FolderInfo)) return; // should always be folderinfo on expand FolderInfo fi = (FolderInfo)obj; if (fi.ChildFolderCount > 0) { foreach (FolderInfo fic in fi.ChildFolders) { DropDownNode newnode = new DropDownNode(fic.FolderID, fic.ToString()); par.Nodes.Add(newnode); newnode.Tag = fic; if (fic.HasChildren) // allow for '+' for tree expansion { DropDownNode tnt = new DropDownNode(0, "VLN_DUMMY"); newnode.Nodes.Add(tnt); } } } else if (fi.FolderDocVersionCount > 0) { foreach (DocVersionInfo dv in fi.FolderDocVersions) { if ((VersionTypeEnum)dv.VersionType == VersionTypeEnum.WorkingDraft) { DropDownNode newnode = new DropDownNode(dv.VersionID, dv.ToString()); newnode.Tag = dv; par.Nodes.Add(newnode); } } } } vlnTreeComboSets.Value = par; vlnTreeComboSets.DropDownControl.SelectedNode = par; } private void DropDown_FinishEditing(object sender, DropDownValueChangedEventArgs e) { DropDownNode selnd = (DropDownNode)vlnTreeComboSets.DropDownControl.SelectedNode; Object obj = selnd.Tag; // only allow selections from proc, sect & step controls if the user has // selected a folder with only 1 working draft docversion or has // selected the docversion itself.... bool defines_set = false; FolderInfo fi = null; if (obj is FolderInfo) { fi = (FolderInfo)obj; if (fi.ChildFolderCount == 0) { // note that the folder may contain more than one docversion, check for // only 1 working draft. int cntwd = 0; foreach (DocVersionInfo dvt in fi.FolderDocVersions) { if ((VersionTypeEnum)dvt.VersionType == VersionTypeEnum.WorkingDraft) cntwd++; } if (cntwd == 1) defines_set = true; } } else if (obj is DocVersionInfo) defines_set = true; if (!defines_set) { MessageBox.Show("Based on your selection, cannot get list of procedures, narrow the procedure set selection."); // disable ALL other controls cbTranProcs.Enabled = false; cbTranSects.Enabled = false; tvTran.Enabled = false; return; } // get to DocVersion node, if at folder... If there are no procedures, notify // the user and return (a transition must at least go to a procedure). // Otherwise, enable/disable controls based on format type of transition. DocVersionInfo dv = null; if (fi != null) { foreach (DocVersionInfo dvt in fi.FolderDocVersions) { if ((VersionTypeEnum)dvt.VersionType == VersionTypeEnum.WorkingDraft) { dv = dvt; break; } } } else dv = (DocVersionInfo)obj; if (dv.Procedures.Count < 1) { MessageBox.Show("There are no procedures in this set. Cannot insert a transition within it."); cbTranProcs.Enabled = false; cbTranSects.Enabled = false; tvTran.Enabled = false; return; } cbTranProcsFillIn(dv.Procedures[0]); cbTranProcs.SelectedIndex = 0; SetControlsEnabling(); } private void listBoxTranFmt_Click(object sender, EventArgs e) { if (_InitializingTrans) return; if (listBoxTranFmt.SelectedIndex == _TranFmtIndx) return; if (_RangeNode1 != null) ClearRangeTransition(); // if this selection needs a step, but not a procedure, use the current procedure & the section list may need to updated // with step only section. List the step sections of the current procedure..... E_TransUI etmprev = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[_TranFmtIndx].TransUI; E_TransUI etmnew = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[listBoxTranFmt.SelectedIndex].TransUI; if (((etmnew & E_TransUI.ProcCur) == E_TransUI.ProcCur) && ((etmprev & E_TransUI.ProcCur) == E_TransUI.ProcCur) != ((etmnew & E_TransUI.ProcCur) == E_TransUI.ProcCur)) { _CurrentProcedure = _CurrentItemProcedure; cbTranProcsFillIn(_CurrentProcedure); ItemInfo tmpitm = _CurItemFrom; ItemInfo secitm = null; while (tmpitm.MyContent.Type != 0) // find current section { if (tmpitm.MyContent.Type >= 10000 && tmpitm.MyContent.Type < 20000 && secitm == null) secitm = tmpitm; tmpitm = tmpitm.MyParent; } int sectstartid = FindSectionStart(_CurrentProcedure); if (sectstartid==-1) btnTranSave.Enabled = false; // if there is an invalid section start - don't allow save. IList chldrn = _CurrentProcedure.GetChildren(); int secIdForCbSect = secitm == null ? sectstartid : secitm.ItemID; // if this transition format requires the default section, use it: if ((etmnew & E_TransUI.SectDefault) == E_TransUI.SectDefault) secIdForCbSect = sectstartid; if (chldrn != null && chldrn.Count > 0) cbTranSectsFillIn((ItemInfo)chldrn[0], secIdForCbSect, true); //sectstartid); } _TranFmtIndx = listBoxTranFmt.SelectedIndex; groupPanelTranFmt.Style.BackColor = (_CurTrans == null && _TranFmtIndx == 0) ? Color.Yellow : Color.Orange; E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[_TranFmtIndx].TransUI; _DoingRange = (etm & E_TransUI.StepLast) == E_TransUI.StepLast; // get section selected and if it's a step section, fill in the treeview of steps if (cbTranSects.Items.Count > 0) { ItemInfo secitm = (ItemInfo)cbTranSects.SelectedItem; if (secitm == null || !secitm.IsStepSection) { tvTran.Nodes.Clear(); tvTran.Enabled = false; } else { _InitializingTrans = true; // just initializing now, don't set any ranges, etc. tvTranFillIn((secitm.Steps==null||secitm.Steps.Count==0)?null:secitm.Steps[0]); tvTran.Enabled = true; _InitializingTrans = false; } } SetControlsEnabling(); // if doing a 'new' range, no node is selected in tree. Without this, the first node in the // tree was the selected node which was throwing off the logic for defining the _RangeNode1 // and _RangeNode2 if (_DoingRange) tvTran.SelectedNode = null; SaveCancelEnabling(); } //private void btnUp1_Click(object sender, EventArgs e) //{ // // if StepAllowNone, then use the second node in the tree view. // int indx = 0; // if (tvTran.Nodes[0].Tag == null) indx = 1; // // if at HLS, don't do anything. // ItemInfo curitm = (ItemInfo)((VETreeNode)tvTran.Nodes[indx]).VEObject; // if (curitm.IsHigh) return; // tvTranFillIn(curitm); //} private void tvTran_BeforeExpand(object sender, TreeViewCancelEventArgs e) { VETreeNode tn = ((VETreeNode)e.Node); // true fixes empty expand, but allows for transitions 'way down' in RNO tree. HVJ & PAL wanted to // allow this (12/2/09). Note that this was changed to not allow transitions // to RNOs (10/2010), this 'feature' will be added at some later date. tn.ChildrenLoaded = false; tn.LoadChildren(false); } private void cbTranSects_SelectedIndexChanged(object sender, EventArgs e) { if (_InitializingTrans) return; // a different section was selected, if step section, update step list, otherwise, empty // it & disable. ItemInfo secitm = (ItemInfo)cbTranSects.SelectedItem; if (!secitm.IsStepSection) { tvTran.Nodes.Clear(); tvTran.Enabled = false; // Set Save & Cancel enabling, depending on whether section can be an endpoint. E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[_TranFmtIndx].TransUI; SaveCancelEnabling(); } else { _InitializingTrans = true; // just initializing now, don't set any ranges, etc. tvTranFillIn((secitm.Steps == null || secitm.Steps.Count == 0) ? null : secitm.Steps[0]); tvTran.Enabled = true; // if doing a 'new' range, no node is selected in tree. Without this, the first node in the // tree was the selected node which was throwing off the logic for defining the _RangeNode1 // and _RangeNode2 if (_DoingRange) { tvTran.SelectedNode = null; // if there was an existing range clear the range because the section selection had changed // and these range values are no longer valid. if (_RangeNode1 != null || _RangeNode2 != null) _RangeNode1 = _RangeNode2 = null; } _InitializingTrans = false; SaveCancelEnabling(); } } private int FindSectionStart(ItemInfo prcitm) { // Steps to get the section start. continue down list until finding a valid id. If none is found // put up a message dialog - and if returns a result of -1, caller should disable the 'ok' button // so that a transition cannot be entered until the default section is defined: // 1) Look in ProcedureConfig/SectionStart // 2) Look in SectionConfig/OriginalSteps // 3) Search through the procedure's sections for 'Procedure Steps' as the title // 4) Display message box telling user to set the default section on section properties/format dialog // (this returns a -1, i.e. error) // 1) Look in ProcedureConfig/SectionStart ProcedureConfig pc = (ProcedureConfig)prcitm.MyConfig; int sectstartid = -1; string ss = pc == null ? null : pc.SectionStart; SectionInfo si = null; if (ss != null && ss != "") { sectstartid = System.Convert.ToInt32(ss); si = SectionInfo.Get(sectstartid); } if (si != null) { if (si.MyProcedure.ItemID == prcitm.ItemID) return sectstartid; // The following code fixes the sectionstart property for the Copy Procedure function. This code will correct // any procedures that were copied prior to the implementation of this the copy procedure function fix. foreach (SectionInfo si1 in prcitm.Sections) { if (si.DisplayNumber == si1.DisplayNumber && si.DisplayText == si1.DisplayText) { using (Procedure p = Procedure.Get(prcitm.ItemID)) { if (p.ProcedureConfig.SectionStart != si1.ItemID.ToString()) { p.ProcedureConfig.SectionStart = si1.ItemID.ToString(); p.Save(); } } return si1.ItemID; } } } // 2) Look in SectionConfig/OriginalSteps = 'Y' if (prcitm.Sections != null) { foreach (SectionInfo sio in prcitm.Sections) { SectionConfig sc = sio.MyConfig as SectionConfig; if (sc != null && sc.Section_OriginalSteps == "Y") { return sio.ItemID; } } // 3) Find if any of the section titles contain 'PROCEDURES STEPS' foreach (SectionInfo sit in prcitm.Sections) { if (sit.DisplayText.ToUpper().Contains("PROCEDURE STEPS")) return sit.ItemID; } } // 4) Display messagebox to tell user to specify which section should be used as the 'default section'. MessageBox.Show("No default step section was found. Set the appropriate Step Section as the default by using the Section Property Page, Format Tab.", "Transition using Default Step Section in Format", MessageBoxButtons.OK,MessageBoxIcon.Error); return -1; } private void cbTranProcs_SelectedIndexChanged(object sender, EventArgs e) { if (_InitializingTrans) return; ItemInfo prcitm = (ItemInfo)cbTranProcs.SelectedItem; if (prcitm == null || prcitm.Sections == null || prcitm.Sections.Count < 1) { cbTranSects.Items.Clear(); tvTran.Nodes.Clear(); return; } int sectstartid = FindSectionStart(prcitm); if (sectstartid == -1) btnTranSave.Enabled = false; // if there is an invalid section start - don't allow save. IList chldrn = prcitm.GetChildren(); cbTranSectsFillIn((ItemInfo)chldrn[0], sectstartid, true); bool isenh = MyRTB != null && MyRTB.MyItemInfo != null && MyRTB.MyItemInfo.IsEnhancedStep; btnTranSave.Enabled = !isenh && UserInfo.CanEdit(MyUserInfo, Mydvi); //Can Insert Transitons SaveCancelEnabling(); } private void tvTran_AfterSelect(object sender, TreeViewEventArgs e) { if (_InitializingTrans) return; E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[listBoxTranFmt.SelectedIndex].TransUI; // Use VEObject if ((etm & E_TransUI.StepAllowNone) == E_TransUI.StepAllowNone && (tvTran.SelectedNode as VETreeNode).VEObject == null) { bool isenh = MyRTB != null && MyRTB.MyItemInfo != null && MyRTB.MyItemInfo.IsEnhancedStep; btnTranSave.Enabled = !isenh && UserInfo.CanEdit(MyUserInfo, Mydvi); //Can Insert Transitons return; } // check if node is a true end-point, i.e. not a 'part' node. If part node, don't // allow selection. VETreeNode vt = tvTran.SelectedNode as VETreeNode; ItemInfo selii = vt.VEObject as ItemInfo; if (selii == null) { MessageBox.Show("Must select a valid step, not a grouping part such as 'RNO', 'Steps', etc"); return; } SaveCancelEnabling(); if (_DoingRange) { if (_RangeNode1 == null || (_RangeNode1 != null && _RangeNode2 != null)) { if (_RangeNode1 != null) tvTranRangeHilites(false, _RangeNode1, _RangeNode2); tvTran.SelectedNode.BackColor = _RangeColor; _RangeNode1 = (VETreeNode)tvTran.SelectedNode; _RangeNode2 = null; lblxTranRangeTip.Text = "Select Last Step \r\nfor Range"; lblxTranRangeTip.BackColor = Color.LightPink; btnTranSave.Enabled = false; } else { if (_RangeNode2 != null) tvTranRangeHilites(false, _RangeNode1, _RangeNode2); _RangeNode2 = (VETreeNode)tvTran.SelectedNode; tvTran.SelectedNode.BackColor = _RangeColor; tvTranRangeHilites(true, _RangeNode1, _RangeNode2); lblxTranRangeTip.Text = "Select First Transition\r\nfor Range"; lblxTranRangeTip.BackColor = Color.Yellow; bool isenh = MyRTB != null && MyRTB.MyItemInfo != null && MyRTB.MyItemInfo.IsEnhancedStep; btnTranSave.Enabled = !isenh && UserInfo.CanEdit(MyUserInfo, Mydvi); //Can Insert Transitons } } } private void SaveCancelEnabling() { //bool hasChanged = _CurItemFrom != _SavCurItemFrom || _TranFmtIndx != _SavTranFmtIndx // || ( selii != null && _CurTrans.ToID != selii.ItemID); bool hasChanged = SettingsChanged; bool isenh = MyRTB != null && MyRTB.MyItemInfo != null && MyRTB.MyItemInfo.IsEnhancedStep; btnTranSave.Enabled = !isenh && hasChanged && UserInfo.CanEdit(MyUserInfo, Mydvi); //Can Insert Transitons btnTranCancel.Enabled = _CurTrans != null && hasChanged; //btnTranSave.Enabled = allowSave; //if (CurTrans != null && selii != null) //{ // if (CurTrans.ToID == selii.ItemID) // { // // if the checkbox for including a page number (UseTransitionModifier flag is true) // // then need to check if this has been changed, and allow a save/cancel if so. // if (cbPageNum.Visible && _ModExistingPageNum != cbPageNum.Checked) // btnTranCancel.Enabled = btnTranSave.Enabled = true; // else // btnTranCancel.Enabled = btnTranSave.Enabled = false; // } // else // { // btnTranCancel.Enabled = true; // btnTranSave.Enabled = allowSave; // } //} //else btnTranCancel.Enabled = btnTranSave.Enabled = allowSave; } private void btnTranCancel_Click(object sender, EventArgs e) { btnTranSave.Enabled = false; btnTranCancel.Enabled = false; _CurItemFrom = _SavCurItemFrom; _TranFmtIndx = _SavTranFmtIndx; TransitionFillIn(); } private void btnTranRangeClear_Click(object sender, EventArgs e) { ClearRangeTransition(); } private void btnTranSave_Click(object sender, EventArgs e) { string trantxt = "(Resolved Transition Text)"; string linktxt = null; E_TransUI etm = (E_TransUI)_CurItemFrom.ActiveFormat.PlantFormat.FormatData.TransData.TransTypeList[listBoxTranFmt.SelectedIndex].TransUI; // if must have a step, test for this first. if (!((etm & E_TransUI.StepAllowNone) == E_TransUI.StepAllowNone)) // _tranitem1 is set from step tree node. { if (tvTran.SelectedNode==null) { MessageBox.Show("Must 'Select Step' for transition 'to'"); return; } } ItemInfo toItem = null; ItemInfo rangeItem = null; if ((etm & E_TransUI.StepLast) == E_TransUI.StepLast) //range { if (_RangeNode1==null) { MessageBox.Show("Must 'Select Step' for transition 'to'"); return; } toItem = (ItemInfo)_RangeNode1.VEObject; if (_RangeNode2 == null && tvTran.SelectedNode == null) { MessageBox.Show("Must 'Select Step' for range transition 'to'"); return; } if (_RangeNode2 == null) _RangeNode2 = (VETreeNode)tvTran.SelectedNode; rangeItem = (ItemInfo)_RangeNode2.VEObject; // The following code was commented out in June 2013 based on a discussion with // HVJ & PAL stating that the range transition should be specific as to what they // enter, not set to end of list. // If this is Transition type 2, then make 'rangenode2' same as rangenode1 // This will get resolved when transition text is resolved. This case represents // range from rangenode1 to last sibling. Note that this is only done if within // the same sibling group. Otherwise, get the second item in the // range, based on current tree view selection. //if (listBoxTranFmt.SelectedIndex == 2) //{ // // if type 2 and not a HLS and the range is within the same hls, then set // // to and range to be equal. When text gets resolved, this case generates // // a list represent the toid,,,lastsibling. // if (!toItem.IsHigh && toItem.MyHLS.ItemID == rangeItem.MyHLS.ItemID) // rangeItem = toItem; // else // rangeItem = rangeItem.MyHLS; //} // Check that the two items are of the below the section type. if (toItem.MyContent.Type < 20000 || rangeItem.MyContent.Type < 20000) { MessageBox.Show("Must select two items at the step level or below, i.e. no sections, procedures, etc."); return; } // be sure that the order is right, i.e. to is before range in list. if (toItem.ItemID != rangeItem.ItemID) { Boolean switchIds = false; // check for order of hls first, then do within sibling list. if (toItem.MyHLS.Ordinal > rangeItem.MyHLS.Ordinal) switchIds = true; else if (toItem.Ordinal > rangeItem.Ordinal) switchIds = true; if (switchIds) { ItemInfo switchItem = toItem; toItem = rangeItem; rangeItem = switchItem; } } linktxt = string.Format("#Link:TransitionRange:{0} {1} {2}", listBoxTranFmt.SelectedIndex, toItem.ItemID, rangeItem.ItemID); } else if ((etm & E_TransUI.StepFirst) == E_TransUI.StepFirst) { if (tvTran.SelectedNode != null && (cbIncStepNum.Visible == false || cbIncStepNum.Checked)) { VETreeNode vtn = (VETreeNode)tvTran.SelectedNode; toItem = (ItemInfo)vtn.VEObject; } else { toItem = (ItemInfo)cbTranSects.SelectedItem; // didn't select a step. if (toItem == null) toItem = (ItemInfo)cbTranProcs.SelectedItem; } if (toItem != null) // this will be null if transition is to a an empty procedure set (sections but no steps) linktxt = string.Format("#Link:Transition:{0} {1}", listBoxTranFmt.SelectedIndex, toItem.ItemID); } // toItem may have been set in the 'Range' selection code above. if (toItem == null && (etm & E_TransUI.SectMenuAny) == E_TransUI.SectMenuAny) { if (tvTran.Enabled == false || (toItem!=null && toItem.IsAccPages)) toItem = (ItemInfo)cbTranSects.SelectedItem; else { VETreeNode vtn = (VETreeNode)tvTran.SelectedNode; if (vtn == null || vtn.Tag == null) toItem = (ItemInfo)cbTranSects.SelectedItem; else toItem = (ItemInfo)vtn.VEObject; } if (toItem==null) { MessageBox.Show("Must 'Select Section' or 'Select Step' for transition 'to'"); return; } linktxt = string.Format("#Link:Transition:{0} {1}", listBoxTranFmt.SelectedIndex, toItem.ItemID); } if (toItem == null && (((etm & E_TransUI.ProcCur) == E_TransUI.ProcCur) || ((etm & E_TransUI.ProcMenu) == E_TransUI.ProcMenu))) { toItem = (ItemInfo)cbTranProcs.SelectedItem; if (toItem == null) { MessageBox.Show("Must select an item for transition 'to'"); return; } linktxt = string.Format("#Link:Transition:{0} {1}", listBoxTranFmt.SelectedIndex, toItem.ItemID); } // Can I build the text right now? ProposedTransition pt = CanTransitionBeCreatedCommand.Execute(MyRTB.MyItemInfo.ItemID, toItem.ItemID); if (pt.Status == 0) { StringBuilder sb = new StringBuilder(); sb.AppendLine("Applicability of source and destination steps will not allow transistion to be created."); sb.AppendLine(); sb.AppendLine(string.Format("Source step {0} has applicability of {1}", pt.FromStep, pt.FromAppl)); sb.AppendLine(string.Format("Destination step {0} has applicability of {1}", pt.ToStep, pt.ToAppl)); MessageBox.Show(sb.ToString()); return; } if(listBoxTranFmt.Text.Contains("{Step Text}") && toItem.ItemID == MyRTB.MyItemInfo.ItemID) { MessageBox.Show("You cannot add a transition to itself for a transition that includes Step Text", "Cannot add recusive transition", MessageBoxButtons.OK, MessageBoxIcon.Exclamation); return; } bool doTranmod = cbPageNum.Visible && cbPageNum.Checked; trantxt = TransitionText.GetResolvedText(MyRTB.MyItemInfo, listBoxTranFmt.SelectedIndex, toItem, rangeItem ?? toItem, doTranmod); int ss = MyRTB.SelectionStart;// Remember where the link is being added int sl = MyRTB.SelectionLength; MyRTB.OnReturnToEditor(this, new EventArgs()); MyRTB.Select(ss, sl); MyRTB.InsertTran(trantxt, linktxt);// Insert the LINK MyRTB.OnDoSaveContents(this, new EventArgs()); //.SaveText();// Save the text with the LINK - This also moves the cursor to the end of the text // By selecting a starting position within a link, StepRTB (HandleSelectionChange) will select the link MyRTB.Select(ss + 7 + trantxt.Length, 0);// Try 7 for i2) { VETreeNode t = node2; node2 = node1; node1 = t; } // Turn Hilighting on/off (depending on bool argument) between the two nodes // they may be at different tree levels. // find common parent level first and save the 'top parent' node for each selection. VETreeNode top1 = node1; VETreeNode top2 = node2; // loop, walking up node2's tree checking against node1. If not found, go to node1 // parent, etc. bool foundcommon = false; while (!foundcommon && top1 != null) { while (!foundcommon & top2 != null) { if (top1.Parent == top2.Parent) foundcommon = true; else top2 = (VETreeNode)top2.Parent; } if (!foundcommon) { top2 = node2; top1 = (VETreeNode)top1.Parent; } } // work down from node1. VETreeNode cur = node1; while (cur != null) { cur.BackColor = on ? _RangeColor : tvTran.BackColor; cur = (VETreeNode)(cur.NextNode == null ? cur.Parent : cur.NextNode); // if these nodes were at the same level, then stop after the current node = range2 if (cur == top1) cur = null; // stop at top if (cur == top2) top1 = cur = null; } // set background for highest level between two nodes. cur = top1==null?null:(VETreeNode)top1.NextNode; while (cur != null) { cur.BackColor = on ? _RangeColor : tvTran.BackColor; cur = (cur == top2) ? null : (VETreeNode)cur.NextNode; } // finish subtree of second node in range. cur = top2==node2?null:node2; while (cur != null) { cur.BackColor = on ? _RangeColor : tvTran.BackColor; cur = (VETreeNode)(cur.PrevNode == null ? cur.Parent : cur.PrevNode); if (cur == top2) cur = null; // stop at top } // hilite last selection.. top2.BackColor = on ? _RangeColor : tvTran.BackColor; } #endregion public DocVersionInfo Mydvi = null; // this is initialized in vlnTreeComboSetsFillIn() private static UserInfo _MyUserInfo = null; public static UserInfo MyUserInfo { get { return _MyUserInfo; } set { _MyUserInfo = value; } } private void cbIncStepNum_CheckedChanged(object sender, EventArgs e) { tvTran.Enabled=cbIncStepNum.Checked; if (!_InitializingTrans) SaveCancelEnabling(); } private void cbPageNum_CheckedChanged(object sender, EventArgs e) { if (_ModExistingPageNum != cbPageNum.Checked) { btnTranCancel.Enabled = true; btnTranSave.Enabled = UserInfo.CanEdit(MyUserInfo, Mydvi); //Can Insert Transitons } } } public class TransItem { private string _ItemDescription; public string ItemDescription { get { return _ItemDescription; } set { _ItemDescription = value; } } private string _Format; public string Format { get { return _Format; } set { _Format = value; } } public TransItem(string desc, string fmt) { _ItemDescription = desc; _Format = fmt; } public override string ToString() { return _ItemDescription; } } }