1476 lines
43 KiB
C#

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Data;
using System.Text;
using System.Windows.Forms;
using System.IO;
using VEPROMS.CSLA.Library;
using DevComponents.DotNetBar;
using DevComponents.AdvTree;
using System.Text.RegularExpressions;
using Volian.Base.Library;
namespace Volian.Controls.Library
{
public partial class DisplayReports : UserControl
{
#region Public Events/Handlers
public event DisplayReportsEvent PrintRequest;
private void OnPrintRequest(DisplayReportsEventArgs args)
{
if (PrintRequest != null)
PrintRequest(this, args);
}
#endregion
#region Fields
// B2022-026 RO Memeory reduction logic change - defined dummy node text variable to ensure consistancy
private const string DummyNodeText = "VLN_DUMMY_NODE";
private List<DocVersionInfo> lstCheckedDocVersions = new List<DocVersionInfo>();
private List<object> lstCheckedROs = new List<object>();
private List<ItemInfoList> lstReportResults = new List<ItemInfoList>();
private List<string> ROList = new List<string>();
private List<object> lstROObj = new List<object>();
private int _MyRODbID;
private DocVersionInfo _MyDocVersion;
private ROFSTLookup _MyROFSTLookup;
private ItemInfoList _ReportResult;
private Dictionary<string, string> AccIDROIDdic = new Dictionary<string, string>();
static int blankKeyCnt = 0;
#endregion
#region Properties
private string DocVersionList
{
get
{
// append list of document versions to search
if (lstCheckedDocVersions.Count > 0)
{
string strRtnStr = "";
// get list of doc versions to search
foreach (DocVersionInfo dvi in lstCheckedDocVersions)
{
strRtnStr += string.Format(",{0}", dvi.VersionID.ToString());
}
return strRtnStr.Substring(1);
}
return "";
}
}
public DocVersionInfo Mydocversion
{
get { return _MyDocVersion; }
set
{
if (DesignMode) return; // B2019-043 need to check if we are just saving changes to the user interface
_MyDocVersion = value;
if (_MyDocVersion != null)
{
if (_MyDocVersion.DocVersionAssociationCount > 0)
{
// if the count variable is not consistent with the actual list count,
// do a refresh. There was a bug, B2012-040, that was not reproducable..
// so this is an attempt to fix it.
if (_MyDocVersion.DocVersionAssociations.Count == 0)
{
_MyDocVersion.RefreshDocVersionAssociations();
if (_MyDocVersion.DocVersionAssociations.Count == 0) return;
}
MyROFSTLookup = _MyDocVersion.DocVersionAssociations[0].MyROFst.GetROFSTLookup(_MyDocVersion);
_MyRODbID = _MyDocVersion.DocVersionAssociations[0].MyROFst.RODbID;
}
}
}
}
public ROFSTLookup MyROFSTLookup
{
get { return _MyROFSTLookup; }
set
{
if (DesignMode) return; // B2019-043 need to check if we are just saving changes to the user interface
//if (!Visible) return; // don't reset anything if the form is invisible.
_MyROFSTLookup = value; // define the tree nodes based on this rofst
advTreeROFillIn(true);
//LoadROComboTree();
}
}
public ItemInfoList ReportResult
{
get { return _ReportResult; }
set
{
_ReportResult = value;
}
}
#endregion
#region Constructors
public DisplayReports()
{
InitializeComponent();
EnableOrDisablePrintButton();
cmbxROUsageSort.SelectedIndex = 0;
tabTransitionReports.Visible = false;
cbxComplete.Enabled = true;
cbxSummary.Enabled = true;
if (cbxROUsage.Checked)
cbxIncldMissingROs.Text = "Include Missing ROs (red ? in the editor)";
else if (cbxComplete.Checked)
cbxIncldMissingROs.Text = "Include Empty RO Fields";
cbxIncldMissingROs.Checked = false;// !cbxSummary.Checked;
cbxIncldMissingROs.Visible = cbxROUsage.Checked || cbxComplete.Checked;
cbxSortBySetpointID.Checked = false;
cbxSortBySetpointID.Visible = cbxComplete.Checked || cbxSummary.Checked;
}
#endregion
#region Public Methods
public void SelectReferencedObjectTab()
{
tabROReports.PerformClick();
}
public void advTreeROFillIn(bool blSeachTabClicked)
{
DevComponents.AdvTree.Node topnode = null;
advTreeRO.Nodes.Clear();
if (_MyROFSTLookup == null) return;
advTreeRO.BeforeExpand += new AdvTreeNodeCancelEventHandler(advTreeRO_BeforeExpand);
advTreeRO.AfterExpand += new AdvTreeNodeEventHandler(advTreeRO_AfterExpandorCollapse);
advTreeRO.AfterCollapse += new AdvTreeNodeEventHandler(advTreeRO_AfterExpandorCollapse);
topnode = new DevComponents.AdvTree.Node();
topnode.Text = "All Referenced Objects";
topnode.Tag = null;
topnode.CheckBoxVisible = true;
advTreeRO.Nodes.Add(topnode);
ROFSTLookup.rodbi[] dbs = _MyROFSTLookup.GetRODatabaseList(true);
if (dbs != null && dbs.Length > 0)
{
for (int i = 0; i < dbs.Length; i++)
{
DevComponents.AdvTree.Node tn = new DevComponents.AdvTree.Node();
ROFSTLookup.rodbi db = dbs[i];
tn.Text = db.dbiTitle;
tn.Tag = db;
tn.CheckBoxVisible = true;
topnode.Nodes.Add(tn);
AddDummyGroup(db, tn);
}
}
}
public void advTreeProcSetsFillIn(bool blSeachTabClicked)
{
DevComponents.AdvTree.Node topnode = null;
int cntnd = 0;
VETreeNode vtn = VETreeNode.GetFolder(1);
FolderInfo fi = vtn.VEObject as FolderInfo;
int fiCount = fi.ChildFolderCount;
advTreeProcSets.Nodes.Clear();
lstCheckedDocVersions.Clear();
topnode = new DevComponents.AdvTree.Node();
topnode.Text = "Available Procedure Sets";
topnode.Tag = fi;
advTreeProcSets.Nodes.Add(topnode);
//advTreeProcSets.AfterNodeInsert += new TreeNodeCollectionEventHandler(advTreeProcSets_AfterNodeInsert);
foreach (FolderInfo fic in fi.SortedChildFolders)
{
DevComponents.AdvTree.Node newnode = new DevComponents.AdvTree.Node();
newnode.Text = fic.ToString();
newnode.Tag = fic;
//int tmp;
//if (topnode == null)
//{
// newnode.Text = "Available Procedure Sets";
// tmp = advTreeProcSets.Nodes.Add(newnode);
// topnode = newnode;
//}
//else
//{
// newnode.Selectable = true;
// newnode.CheckBoxAlignment = DevComponents.AdvTree.eCellPartAlignment.NearCenter;
// newnode.CheckBoxStyle = eCheckBoxStyle.CheckBox;
// newnode.CheckBoxThreeState = false;
// newnode.CheckBoxVisible = true;
// tmp = topnode.Nodes.Add(newnode);
//}
cntnd++;
if (fic.ChildFolderCount > 0 || fic.FolderDocVersionCount > 0) // allow for '+' for tree expansion
{
DevComponents.AdvTree.Node tnt = new DevComponents.AdvTree.Node();
tnt.Text = DummyNodeText;
newnode.Nodes.Add(tnt);
topnode.Nodes.Add(newnode);
}
}
// if nothing was added to the tree, just put in the node above the docversions...
if (advTreeProcSets.Nodes.Count == 0)
{
cntnd++;
fi = Mydocversion.MyFolder;
topnode = new DevComponents.AdvTree.Node();
topnode.Text = fi.ToString();
advTreeProcSets.Nodes.Add(topnode);
topnode.Tag = fi;
}
advTreeProcSets.BeforeExpand += new DevComponents.AdvTree.AdvTreeNodeCancelEventHandler(advTreeProcSets_BeforeExpand);
// position to the procedure set in the tree if we have a procedure open
if (Mydocversion != null)
advTreeProcSetsPreSelect();
else
advTreeProcSets.Nodes[0].SelectedCell = advTreeProcSets.Nodes[0].Cells[0]; // select the first node - fixes cosmetic problem
//if (blSeachTabClicked)
// cbxTextSearchText.Focus(); // set initial focus to enter search text
}
#endregion
#region Private Methods
private void GenerateAccIDSortedROList()
{
//Dictionary<string, string> AccIDROIDdic = new Dictionary<string, string>();
List<string> AccPgIDsList = new List<string>();
AccIDROIDdic.Clear();
string rtnStr = "";
ROFSTLookup.rochild[] chld = null;
ROFSTLookup.rochild ch;
ROList.Clear();
foreach (object rolkup in lstCheckedROs)
{
if (rolkup == null) // All Referenced Objects selected, return list of RO databases
{
foreach (ROFSTLookup.rodbi rodbi in _MyROFSTLookup.GetRODatabaseList(true))
{
rtnStr = _MyRODbID.ToString() + ":" + string.Format("{0}", rodbi.dbiID.ToString("X4"));
if (rodbi.children != null)
{
foreach (ROFSTLookup.rochild roc in rodbi.children)
{
PutROChildrenInDictionary(_MyRODbID.ToString() + ":", roc);
}
}
else
{
ROList.Add(rtnStr);
}
}
continue;
}
else if (rolkup is ROFSTLookup.rodbi)
{
ROFSTLookup.rodbi rodbi = (ROFSTLookup.rodbi)rolkup;
//Try to lazy load the children - B2022-026 RO Memory Reduction code
if (rodbi.children == null || rodbi.children.Length <= 0)
rodbi.children = MyROFSTLookup.GetRoChildrenByID(rodbi.ID, rodbi.dbiID, true);
if (rodbi.children != null)
{
foreach (ROFSTLookup.rochild roc in rodbi.children)
{
PutROChildrenInDictionary(_MyRODbID.ToString() + ":", roc);
}
}
else
{
ROList.Add(_MyRODbID.ToString() + ":" + string.Format("{0}", rodbi.dbiID.ToString("X4")));
}
}
else if (rolkup is ROFSTLookup.rochild)
{
ch = (ROFSTLookup.rochild)rolkup;
chld = ch.children;
//Try to lazy load the children - B2022-026 RO Memory Reduction code
if (ch.children == null || ch.children.Length <= 0)
ch.children = MyROFSTLookup.GetRoChildrenByRoid(ch.roid, true);
PutROChildrenInDictionary(_MyRODbID.ToString() + ":", rolkup);
}
}
foreach (string k in AccIDROIDdic.Keys)
{
AccPgIDsList.Add(k);
}
string[] AccPgIdListArray = AccPgIDsList.ToArray();
Array.Sort(AccPgIdListArray, new AlphanumComparatorFast());
foreach (string accid in AccPgIdListArray)
{
ROList.Add(AccIDROIDdic[accid]);
}
}
private string GetNextBlankKey()
{
return string.Format(" _{0}", blankKeyCnt++);
}
private void PutROChildrenInDictionary(string rodbidPrefix, object roObj)
{
ROFSTLookup.rochild chld = (ROFSTLookup.rochild)roObj;
string rtnstr = rodbidPrefix;// "";
string keystr = ((chld.appid == "") ? GetNextBlankKey() : chld.appid) + chld.roid.Substring(0,4);
//Try to lazy load the children - B2022-026 RO Memory Reduction
if (chld.children == null || chld.children.Length <= 0)
chld.children = MyROFSTLookup.GetRoChildrenByRoid(chld.roid, true);
// If still no children - B2022-026 RO Memory Reduction code - check children length
if (chld.children == null || chld.children.Length <= 0) // get a single ROID
{
rtnstr = rodbidPrefix + string.Format("{0}", chld.roid);
if (rtnstr.Length == 12) rtnstr += "0000"; // last four digits are used for multiple return values
// B2023-094: Don't crash when trying to add another ro if it has same key. Note that this is coming in as an RO but is really a group.
if (!AccIDROIDdic.ContainsKey(keystr))AccIDROIDdic.Add(keystr, rtnstr);
}
else if (!cbxROUsage.Checked && chld.children[0].ParentID == 0)
{
rtnstr = rodbidPrefix + string.Format("{0},", chld.roid); // doing a RO Summary or RO Complete report - don't want children that are multiple return values
AccIDROIDdic.Add(keystr, rtnstr);
}
else
{
// spin through the child list and get the ROIDs.
// if the child has children, then call this function recursively
for (int i = 0; i < chld.children.Length; i++)
{
ROFSTLookup.rochild roc = chld.children[i];
//Try to lazy load the children - B2022-026 RO Memory Reduction code
if (roc.children == null || roc.children.Length <= 0)
roc.children = MyROFSTLookup.GetRoChildrenByRoid(roc.roid, true);
// Don't get the children if we are doing a RO Summary or RO Complete report & children are the multiple return values
if (roc.children != null && roc.children.Length > 0 && (cbxROUsage.Checked || roc.children[0].ParentID != 0))
{
PutROChildrenInDictionary(rodbidPrefix, roc);
}
else if (roc.appid != null && roc.appid != "")
{
rtnstr = rodbidPrefix + string.Format("{0}", roc.roid);
keystr = ((roc.appid == "") ? GetNextBlankKey() : roc.appid) + chld.roid.Substring(0, 4);
if (AccIDROIDdic.ContainsKey(keystr)) // For duplicates, append the parent title (B2017-011) so adding to dictionary doesn't crash.
{
keystr = keystr + "|" + chld.title;
}
AccIDROIDdic.Add(keystr, rtnstr);
}
}
}
}
private void GenerateROList()
{
string rtnStr = "";
ROFSTLookup.rochild[] chld = null;
ROFSTLookup.rochild ch;
ROList.Clear();
foreach (object rolkup in lstCheckedROs)
{
if (rolkup == null) // All Referenced Objects selected, return list of RO databases
{
// B2022-026 RO Memory Reduction code - added flag to load all children
foreach (ROFSTLookup.rodbi rodbi in _MyROFSTLookup.GetRODatabaseList(true))
{
rtnStr = _MyRODbID.ToString() + ":" + string.Format("{0}", rodbi.dbiID.ToString("X4"));
ROList.Add(rtnStr);
}
continue;
}
else if (rolkup is ROFSTLookup.rodbi)
{
rtnStr = _MyRODbID.ToString() + ":" + string.Format("{0}", ((ROFSTLookup.rodbi)rolkup).dbiID.ToString("X4"));
}
else if (rolkup is ROFSTLookup.rochild)
{
ch = (ROFSTLookup.rochild)rolkup;
//Try to lazy load the children - B2022-026 RO Memory Reduction code
if (ch.children == null || ch.children.Length <= 0)
ch.children = MyROFSTLookup.GetRoChildrenByRoid(ch.roid, true);
chld = ch.children;
rtnStr = _MyRODbID.ToString() + ":" + GetROChildren(rolkup).TrimEnd(','); // GetROChildren(rolkup).TrimEnd(',') grabs the children of the selected item
}
ROList.Add(rtnStr);
}
}
// same function as GetROsToSearch in DisplaySearch.cs
private string GetROChildren(object roObj)
{
ROFSTLookup.rochild chld = (ROFSTLookup.rochild)roObj;
string rtnstr = "";
//Try to lazy load the children - B2022-026 RO Memory Reduction code
if (chld.children == null || chld.children.Length <= 0)
chld.children = MyROFSTLookup.GetRoChildrenByRoid(chld.roid, true);
// If still no children
if (chld.children == null || chld.children.Length <= 0) // get a single ROID
{
rtnstr += string.Format("{0}", chld.roid);
if (rtnstr.Length == 12) rtnstr += "0000"; // last four digits are used for multiple return values
}
else if (!cbxROUsage.Checked && chld.children[0].ParentID == 0)
{
rtnstr += string.Format("{0},", chld.roid); // doing a RO Summary or RO Complete report - don't want children that are multiple return values
}
else
{ // spin through the child list and get the ROIDs.
// if the child has children, then call this function recursivly
foreach (ROFSTLookup.rochild roc in chld.children)
{
// Don't get the children if we are doing a RO Summary or RO Complete report & children are the multiple return values
// B2022-062: Proms crashes on Complete or Summary RO report without 'Sort by SetpointID'. With new ROfst logic,
// need to check for children length > 0 also.
if (roc.children != null && roc.children.Length > 0 && (cbxROUsage.Checked || roc.children[0].ParentID != 0))
rtnstr += GetROChildren(roc);
else
rtnstr += string.Format("{0},", roc.roid);
}
}
return rtnstr;
}
private string GetListOfROs(bool keepRODbID)
{
string rtnStr = "";
string strRODbID = "";
int cnt = 0;
foreach (string rostr in ROList)
{
int ndxOf = rostr.IndexOf(":");
if (ndxOf > 0)
{
string tstr = rostr.Substring(0, ndxOf + 1);
if (tstr != strRODbID && keepRODbID)
{
strRODbID = tstr;
rtnStr += rostr;
}
else
rtnStr += rostr.Substring(ndxOf + 1);
}
else
rtnStr += rostr;
if (rtnStr.EndsWith(",")) rtnStr = rtnStr.Substring(0, rtnStr.Length - 1);
if (++cnt < ROList.Count)
rtnStr += ",";
}
return rtnStr;
}
private void AddSelectedROChildren(DevComponents.AdvTree.NodeCollection chldrn)
{
if (chldrn.Count > 0)
{
foreach (DevComponents.AdvTree.Node n in chldrn)
{
if (n.Checked)
lstCheckedROs.Add(n.Tag);
else
AddSelectedROChildren(n.Nodes);
}
}
}
private void BuildCheckedROsList()
{
lstCheckedROs.Clear();
if (advTreeRO.Nodes.Count == 0) return;
DevComponents.AdvTree.Node node = advTreeRO.Nodes[0];
if (node.Checked) // top node (all Referenced Objects) selected
lstCheckedROs.Add(node.Tag);
else
AddSelectedROChildren(node.Nodes);
}
private void EnableOrDisablePrintButton()
{
switch (tctrlReports.SelectedTabIndex)
{
case 0: // Transition Reports
btnPrintReport.Enabled = (lstCheckedDocVersions.Count > 0);
break;
case 1: // Referenced Objects Reports
BuildCheckedROsList(); // this list is sent to the report generator
if (cbxROUsage.Checked)
btnPrintReport.Enabled = (lstCheckedDocVersions.Count > 0 && lstCheckedROs.Count > 0);
else
btnPrintReport.Enabled = ((cbxComplete.Checked || cbxSummary.Checked) && lstCheckedROs.Count > 0);
break;
}
if (cbxROUsage.Checked)
cbxIncldMissingROs.Text = "Include Missing ROs (red ? in the editor)";
else if (cbxComplete.Checked)
cbxIncldMissingROs.Text = "Include Empty RO Fields";
//cbxIncldMissingROs.Checked = cbxROUsage.Checked || cbxComplete.Checked;
cbxIncldMissingROs.Visible = cbxROUsage.Checked || cbxComplete.Checked;
cbxSortBySetpointID.Visible = cbxComplete.Checked || cbxSummary.Checked;
labelX1.Visible = cmbxROUsageSort.Visible = !cbxSortBySetpointID.Visible;
}
private void tabTransitionReports_Click(object sender, EventArgs e)
{
xpSetToReport.Enabled = true;
xpSetToReport.Expanded = true;
xpSelROs.Expanded = false;
xpSelROs.Enabled = false;
EnableOrDisablePrintButton();
}
private void tabROReports_Click(object sender, EventArgs e)
{
xpSetToReport.Enabled = cbxROUsage.Checked;
xpSetToReport.Expanded = cbxROUsage.Checked;
labelX1.Visible = cmbxROUsageSort.Visible = cbxROUsage.Checked;
xpSelROs.Enabled = true;
xpSelROs.Expanded = true;
cbxIncldMissingROs.Checked = false;// !cbxSummary.Checked;
cbxSortBySetpointID.Checked = false;
cbxSortBySetpointID.Visible = !cbxROUsage.Checked;
EnableOrDisablePrintButton();
}
private void cbxROUsage_CheckedChanged(object sender, EventArgs e)
{
xpSetToReport.Enabled = cbxROUsage.Checked;
xpSetToReport.Expanded = cbxROUsage.Checked;
labelX1.Visible = cmbxROUsageSort.Visible = cbxROUsage.Checked;
// reset the RO tree and clear anything that was selected
advTreeROFillIn(true);
lstCheckedROs.Clear();
cbxIncldMissingROs.Checked = false;// !cbxSummary.Checked;
cbxSortBySetpointID.Checked = false;
cbxSortBySetpointID.Visible = !cbxROUsage.Checked;
EnableOrDisablePrintButton();
}
private void DisplayReports_Load(object sender, EventArgs e)
{
tabTransitionReports.PerformClick();
}
// when a node is checked (selected) then uncheck any of its children
private void UncheckChildren(DevComponents.AdvTree.NodeCollection chldrn)
{
if (chldrn.Count > 0)
{
foreach (DevComponents.AdvTree.Node n in chldrn)
{
if (n.Checked)
n.Checked = false;
else
UncheckChildren(n.Nodes);
}
}
}
// when a node is checked (selected), uncheck the parents, grand parents, great grand parents, etc.
private void UncheckParents(DevComponents.AdvTree.Node pNode)
{
while (pNode != null)
{
if (pNode.Checked) pNode.Checked = false;
pNode = pNode.Parent;
}
}
private void advTreeRO_AfterCheck(object sender, AdvTreeCellEventArgs e)
{
DevComponents.AdvTree.Node n = advTreeRO.SelectedNode;
if (n.Checked)
{
UncheckChildren(n.Nodes);
UncheckParents(n.Parent);
}
EnableOrDisablePrintButton();
}
private void cbxTransToProcs_CheckedChanged(object sender, EventArgs e)
{
EnableOrDisablePrintButton();
}
private void cbxTransFromProcs_CheckedChanged(object sender, EventArgs e)
{
EnableOrDisablePrintButton();
}
private void cbxComplete_CheckedChanged(object sender, EventArgs e)
{
cbxIncldMissingROs.Checked = false;// !cbxSummary.Checked;
cbxSortBySetpointID.Checked = false;
EnableOrDisablePrintButton();
}
private void cbxSummary_CheckedChanged(object sender, EventArgs e)
{
EnableOrDisablePrintButton();
}
private string BuildRODataFile(string ROList)
{
DocVersionInfo MyDVI = Mydocversion;
string roDataFile = "PRINT.TMP";
if (VlnSettings.ReleaseMode.Equals("DEMO"))
{
MessageBox.Show("Referenced Object Reports not available in the Demo version.", "PROMS Demo Version");
return "";
}
//string roapp = Environment.GetEnvironmentVariable("roapp");
string roapp = Volian.Base.Library.ExeInfo.GetROEditorPath(); // get the path to the RO Editor Executable
if (roapp == null)
{
MessageBox.Show("Could not find path to Ro Editor, check 'roapp' environment variable");
return "";
}
if (MyDVI == null || MyDVI.DocVersionAssociationCount < 1)
{
MessageBox.Show("Could not find associated path for ro data.", "No RO Data", MessageBoxButtons.OK, MessageBoxIcon.Information);
return "";
}
//string roloc = "\"" + MyDVI.DocVersionAssociations[0].MyROFst.MyRODb.FolderPath + "\" " + "\"" + ROList + "\"";
if (!Directory.Exists(MyDVI.DocVersionAssociations[0].MyROFst.MyRODb.FolderPath))
{
MessageBox.Show(string.Format("RO Database directory does not exist: {0}", MyDVI.DocVersionAssociations[0].MyROFst.MyRODb.FolderPath));
return "";
}
string cmpRptExePath = roapp.Substring(0, roapp.LastIndexOf("\\")) + "\\CmpRpt.exe ";
roDataFile = MyDVI.DocVersionAssociations[0].MyROFst.MyRODb.FolderPath + "\\" + roDataFile;
try
{
if (File.Exists(roDataFile)) File.Delete(roDataFile);
Application.DoEvents();
string fname = VlnSettings.TemporaryFolder + "\\ROCompleteRprt.txt";
FileInfo fi = new FileInfo(fname);
using (StreamWriter sw = fi.CreateText())
{
sw.Write(ROList);
sw.Close();
}
string roloc = "\"" + MyDVI.DocVersionAssociations[0].MyROFst.MyRODb.FolderPath + "\" \"/f=" + fname + "\"";
// C2017-003: ro data in sql server, check for sql connection string
if (MyDVI.DocVersionAssociations[0].MyROFst.MyRODb.DBConnectionString != "cstring") roloc = roloc + " \"/sql=" + MyDVI.DocVersionAssociations[0].MyROFst.MyRODb.DBConnectionString + "\"";
// C2021-026 pass in Parent/Child information (list of the children)
// B2022-019 look at all DocVersions to find ParentChild information
// to ensure we pass in Parent/Child even when not coming from a Parent/Child procedure set
DocVersionInfoList dvil = DocVersionInfoList.Get();
foreach (DocVersionInfo dvi in dvil)
{
DocVersionConfig dvc = dvi.DocVersionConfig as DocVersionConfig;
if (dvc != null && dvc.Unit_Name != "" && dvc.Unit_Count > 1) // B2021-089 only pass in applicability info if defined for more than one unit
roloc += " \"/PC=" + dvc.Unit_Name + "\"";
break;
}
System.Diagnostics.Process p = System.Diagnostics.Process.Start(cmpRptExePath, roloc);
// need to wait, sometimes the Print.tmp file that is generated is not available
p.WaitForExit(); // without arguments, this will wait indefinitely
Application.DoEvents();
}
catch (Exception ex)
{
while (ex.InnerException != null)
ex = ex.InnerException;
string tmpmsg = ex.Message;
MessageBox.Show(tmpmsg, "RO Report Error: " + ex.GetType().Name);
}
return roDataFile;
}
private void btnPrintReport_Click(object sender, EventArgs e)
{
string paperSize = "Letter";
if (Mydocversion != null && Mydocversion.ActiveFormat != null)
paperSize = Mydocversion.ActiveFormat.PlantFormat.FormatData.PDFPageSize.PaperSize; // C2020-002 paper size is now set in the format files
//B2019-144 Set the document text color to Red (overlay) or Black (normal)
Color lastColor = MSWordToPDF.OverrideColor;// B2019-144 Remember override color
if (MSWordToPDF.OverrideColor != Color.Black)
MSWordToPDF.OverrideColor = Color.Black;
Cursor curcur = Cursor;
Cursor = Cursors.WaitCursor;
if (cbxSummary.Checked) // RO Summary Report
{
if (cbxSortBySetpointID.Checked)
GenerateAccIDSortedROList();
else
GenerateROList();
OnPrintRequest(new DisplayReportsEventArgs("RO Summary Report", "RO Summary Report", MyROFSTLookup, ROList, paperSize));
}
else if (cbxComplete.Checked) // Complete RO Report
{
if (cbxSortBySetpointID.Checked)
GenerateAccIDSortedROList();
else
GenerateROList();
string ROList = GetListOfROs(false);//don't include the RODbID in the RO list
string roDataFile = BuildRODataFile(ROList);
// B2023-028: RO report generates report with error when RO path not set. Return if datafile is not set
// by BuildRODataFile
if (roDataFile == null || roDataFile == "")
{
Cursor = curcur; // B2023-094: restore cursor (was wait). Not part of bug, found during fix
return;
}
if (Mydocversion != null)
OnPrintRequest(new DisplayReportsEventArgs("Complete RO Report", "Complete RO Report", roDataFile, MyROFSTLookup, cbxComplete.Checked, Mydocversion.ActiveFormat.PlantFormat.FormatData.SectData.ConvertCaretToDelta, cbxIncldMissingROs.Checked, paperSize));
}
else if (cbxROUsage.Checked)
{
bool usageSortedByProcedure = (cmbxROUsageSort.SelectedIndex == 1);
GenerateROList();
string SearchString = GetListOfROs(true);// Include the RODbID in the RO list
ItemInfoList SearchResults = ItemInfoList.GetListFromROReport(DocVersionList, "", SearchString, "");
List<ItemInfo> sortedResults = SearchResults.SortedList(!usageSortedByProcedure);
OnPrintRequest(new DisplayReportsEventArgs("Referenced Objects Usage By RO", "RO Usage", sortedResults, usageSortedByProcedure, cbxIncldMissingROs.Checked, paperSize));
}
else if (cbxTransFromProcs.Checked)
{
}
else if (cbxTransToProcs.Checked)
{
}
Cursor = curcur;
//B2019-144 Set the document text color to Red (overlay) or Black (normal)
if (MSWordToPDF.OverrideColor != lastColor)// B2019-144 Restore override color
MSWordToPDF.OverrideColor = lastColor;
}
#region (Procedure List)
private DevComponents.AdvTree.Node NewAdvTreeNode(string nodetext, bool selectable, bool chxbxvisable)
{
DevComponents.AdvTree.Node newnode;
newnode = new DevComponents.AdvTree.Node();
newnode.Text = nodetext;
newnode.Selectable = selectable;
newnode.CheckBoxAlignment = DevComponents.AdvTree.eCellPartAlignment.NearCenter;
newnode.CheckBoxStyle = eCheckBoxStyle.CheckBox;
newnode.CheckBoxThreeState = false;
newnode.CheckBoxVisible = chxbxvisable;
return newnode;
}
private void advTreeProcSets_BeforeExpand(object sender, DevComponents.AdvTree.AdvTreeNodeCancelEventArgs e)
{
DevComponents.AdvTree.Node par = e.Node;
// get first child's text, if it has one & if the text is "VLN_DUMMY_NODE", load children
DevComponents.AdvTree.Node tn = null;
if (par.Nodes.Count > 0) tn = par.Nodes[0];
if (tn.Text == DummyNodeText) // 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.SortedChildFolders)
{
DevComponents.AdvTree.Node newnode = new DevComponents.AdvTree.Node();
newnode.Text = fic.ToString();
newnode.Tag = fic;
par.Nodes.Add(newnode);
if (fic.HasChildren) // allow for '+' for tree expansion
{
DevComponents.AdvTree.Node tnt = new DevComponents.AdvTree.Node();
tnt.Text = DummyNodeText;
newnode.Nodes.Add(tnt);
}
}
}
else if (fi.FolderDocVersionCount > 0)
{
foreach (DocVersionInfo dv in fi.FolderDocVersions)
{
DevComponents.AdvTree.Node newnode = new DevComponents.AdvTree.Node();
newnode.Text = dv.ToString();
newnode.Tag = dv;
newnode.Selectable = true;
newnode.CheckBoxAlignment = DevComponents.AdvTree.eCellPartAlignment.NearCenter;
newnode.CheckBoxStyle = eCheckBoxStyle.CheckBox;
newnode.CheckBoxThreeState = false;
newnode.CheckBoxVisible = true;
par.Nodes.Add(newnode);
}
}
}
}
private void advTreeProcSets_AfterCheck(object sender, DevComponents.AdvTree.AdvTreeCellEventArgs e)
{
DevComponents.AdvTree.Node n = advTreeProcSets.SelectedNode;
if (n.Checked)
{
n.Style = DevComponents.AdvTree.NodeStyles.Apple;
lstCheckedDocVersions.Add((DocVersionInfo)n.Tag);
if (lstCheckedDocVersions.Count == 1)//Mydocversion == null)
{
Mydocversion = (DocVersionInfo)n.Tag;
}
}
else
{
n.Style = null;
lstCheckedDocVersions.Remove((DocVersionInfo)n.Tag);
if (lstCheckedDocVersions.Count == 1)
{
if (Mydocversion != lstCheckedDocVersions[0])
{
Mydocversion = lstCheckedDocVersions[0];
}
}
else
{
if (lstCheckedDocVersions.Count == 0)
Mydocversion = null;
// do this if either none, or more than one procedure set selected
//advTreeStepTypes.Nodes.Clear();
//lstCheckedStepTypes.Clear();
//lstCheckedStepTypesStr.Clear();
//Node newnode = new DevComponents.AdvTree.Node();
//newnode.Text = "....select a procedure set for types to appear...";
//advTreeStepTypes.Nodes.Add(newnode);
//buildStepTypePannelTitle();
}
}
//// Enable the RO combo list only if at least one procedure set node
//// is selected
//cmboTreeROs.Enabled = (lstCheckedDocVersions.Count > 0);
//gpFindROs.Enabled = cmboTreeROs.Enabled;
//SetupContextMenu();
//buildSetToSearchPanelTitle();
EnableOrDisablePrintButton();
}
private void advTreeProcSets_AfterNodeSelect(object sender, AdvTreeNodeEventArgs e)
{
DevComponents.AdvTree.Node n = advTreeProcSets.SelectedNode;
}
private void advTreeProcSetsPreSelect()
{
bool keeplooking = true;
//build a stack (bread crumb trail) of where is procedure set came from within the tree.
Stack<string> crumbs = new Stack<string>();
crumbs.Push(Mydocversion.Name); // ex: "working draft"
crumbs.Push(Mydocversion.MyFolder.Name); // ex: "Emergency Procedures"
FolderInfo fi = Mydocversion.MyFolder.MyParent;
while (fi != null)
{
if (fi.MyParent != null)
crumbs.Push(fi.Name);
fi = fi.MyParent;
}
crumbs.Push(advTreeProcSets.Nodes[0].Text); //top node of my tree
// now walk the tree, looking for the node names we saved in the stack.
NodeCollection monkeys = advTreeProcSets.Nodes;
while (keeplooking)
{
Node climber = LookInTree(monkeys, crumbs.Pop());
keeplooking = (climber != null && crumbs.Count > 0);
if (keeplooking)
monkeys = climber.Nodes;
if (!keeplooking && climber != null)
{
climber.Checked = true;
}
}
}
private Node LookInTree(NodeCollection monkeys, string bananna)
{
Node foundit = null;
foreach (Node chimp in monkeys)
{
if (chimp.Text.Equals(bananna))
{
foundit = chimp;
// need to select the node (cell) for it to be checked
chimp.SelectedCell = chimp.Cells[0];
if (chimp.Nodes.Count > 0)
chimp.Expand();
break;
}
chimp.Collapse();
}
return foundit;
}
#endregion
#region (RO Tree)
private void AddDummyGroup(ROFSTLookup.rodbi rodbi, DevComponents.AdvTree.Node tn)
{
if (rodbi.children != null && rodbi.children.Length > 0)
{
DevComponents.AdvTree.Node tmp = new DevComponents.AdvTree.Node();
tmp.Text = DummyNodeText;
tn.Nodes.Add(tmp);
}
}
private void advTreeRO_BeforeExpand(object sender, DevComponents.AdvTree.AdvTreeNodeCancelEventArgs e)
{
LoadChildren(e.Node);
}
private void LoadChildren(DevComponents.AdvTree.Node tn)
{
//Check if node has already been loaded
if (tn.HasChildNodes && tn.Nodes[0].Text != DummyNodeText) return; // already loaded.
if (tn.HasChildNodes && tn.Nodes[0].Text == DummyNodeText) tn.Nodes[0].Remove();
object tag = tn.Tag;
ROFSTLookup.rochild[] chld = null;
if (tn.Tag is ROFSTLookup.rodbi)
{
ROFSTLookup.rodbi db = (ROFSTLookup.rodbi)tn.Tag;
//Try to lazy load the children - B2022-026 RO Memory Reduction code
if (db.children == null || db.children.Length <= 0)
db.children = MyROFSTLookup.GetRoChildrenByID(db.ID, db.dbiID, true);
chld = db.children;
}
else if (tn.Tag is ROFSTLookup.rochild)
{
ROFSTLookup.rochild ch = (ROFSTLookup.rochild)tn.Tag;
//Try to lazy load the children - B2022-026 RO Memory Reduction code
if (ch.children == null || ch.children.Length <= 0)
ch.children = MyROFSTLookup.GetRoChildrenByRoid(ch.roid, true);
chld = ch.children;
}
else
{
Console.WriteLine("error - no type");
return;
}
// if children, add dummy node
// B2022-026 RO Memory Reduction code - check child length
if (chld != null && chld.Length > 0)
{
//ProgressBar_Initialize(chld.Length, tn.Text);
for (int i = 0; i < chld.Length; i++)
{
//ProgressBar_SetValue(i);
DevComponents.AdvTree.Node tmp = null;
// Try to Lazy Load children - B2022-026 RO Memory Reduction code
if (chld[i].children == null || chld[i].children.Length <= 0)
chld[i].children = MyROFSTLookup.GetRoChildrenByRoid(chld[i].roid, true);
// if this is a group, i.e. type 0, add a dummy node
if (chld[i].type == 0 && chld[i].children == null)
{
// Ignore: Junk Scenario
continue;
}
// B2023-094: don't crash if chld[i].children count is 0, signals an empty group
else if (chld[i].value == null && (cbxROUsage.Checked || (chld[i].children != null && chld[i].children.Length > 0 && chld[i].children[0].ParentID != 0)))
{
tmp = new DevComponents.AdvTree.Node();
tmp.Text = chld[i].title;
tmp.Tag = chld[i];
tmp.CheckBoxVisible = true;
int index = FindIndex(tn.Nodes, tmp.Text);
tn.Nodes.Insert(index, tmp);
DevComponents.AdvTree.Node sub = new DevComponents.AdvTree.Node();
sub.Text = DummyNodeText;
tmp.Nodes.Add(sub);
}
else
{
tmp = new DevComponents.AdvTree.Node();
tmp.Text = chld[i].title;
tmp.Tag = chld[i];
tmp.CheckBoxVisible = true;
int index = FindIndex(tn.Nodes, tmp.Text);
tn.Nodes.Insert(index, tmp);
}
}
}
}
private void advTreeRO_AfterExpandorCollapse(object sender, AdvTreeNodeEventArgs e)
{
Node bottomNode = BottomTreeNode(advTreeRO.Nodes);
Node lastNode = advTreeRO.Nodes[advTreeRO.Nodes.Count - 1];
int top = advTreeRO.Nodes[0].Bounds.Top;
int bottom = bottomNode.Bounds.Bottom + 5;
int hScrollBarHeight = advTreeRO.HScrollBar != null ? advTreeRO.HScrollBar.Height : 0;
bottom = bottomNode.Bounds.Bottom + 5;
advTreeRO.Size = new Size(advTreeRO.Size.Width, Math.Min(525, bottom - top + hScrollBarHeight));
if (advTreeRO.VScrollBar != null && bottom < advTreeRO.Size.Height)
{
int yLookFor = (bottom - advTreeRO.Size.Height) + 2 * hScrollBarHeight;
Node topNode = FindTreeNodeAt(advTreeRO.Nodes, yLookFor);
if (topNode != null)
topNode.EnsureVisible();
}
}
private Node FindTreeNodeAt(NodeCollection nodes, int y)
{
foreach (Node node in nodes)
{
if (node.Bounds.Top <= y && node.Bounds.Bottom >= y)
return node;
if (node.Bounds.Top > y)
{
if (node.PrevNode != null && node.PrevNode.Expanded)
return FindTreeNodeAt(node.PrevNode.Nodes, y);
return node;
}
}
return null;
}
private Node BottomTreeNode(NodeCollection nodes)
{
Node bottomNode = nodes[nodes.Count - 1]; // Return bottom node in collection
if (bottomNode.Expanded) // If expanded return bottom child
return BottomTreeNode(bottomNode.Nodes);
return bottomNode;
}
private int FindIndex(NodeCollection nodes, string value)
{
int index = 0;
foreach (Node node in nodes)
{
if (GreaterValue(node.Text, value)) return index;
index++;
}
return index;
}
private bool GreaterValue(string value1, string value2)
{
return DisplayRO.GreaterValue(value1, value2);
}
#endregion
#endregion
}
#region DisplayReportsEventArgs Class
public class DisplayReportsEventArgs
{
#region Fields
private string _ReportTitle;
private string _TypesSelected;
private ICollection<ItemInfo> _MyItemInfoList;
private bool _SortUsageByProcedure;
private string _RODataFile = "";
private bool _CompleteROReport = true;
private ROFSTLookup _rofstLookup;
private List<string> _ROListForReport;
private bool _IncludeMissingROs = true;
private bool _ConvertCaretToDelta = true;
private bool _IncludeEmptyROFields = true;
private string _PaperSize = "Letter";
#endregion
#region Properties
public string ReportTitle
{
get { return _ReportTitle; }
set { _ReportTitle = value; }
}
public string TypesSelected
{
get { return _TypesSelected; }
set { _TypesSelected = value; }
}
public ICollection<ItemInfo> MyItemInfoList
{
get { return _MyItemInfoList; }
set { _MyItemInfoList = value; }
}
public bool SortUsageByProcedure
{
get { return _SortUsageByProcedure; }
set { _SortUsageByProcedure = value; }
}
public string RODataFile
{
get { return _RODataFile; }
set { _RODataFile = value; }
}
public bool CompleteROReport
{
get { return _CompleteROReport; }
set { _CompleteROReport = value; }
}
public ROFSTLookup RofstLookup
{
get { return _rofstLookup; }
set { _rofstLookup = value; }
}
public List<string> ROListForReport
{
get { return _ROListForReport; }
set { _ROListForReport = value; }
}
public bool IncludeMissingROs
{
get { return _IncludeMissingROs; }
set { _IncludeMissingROs = value; }
}
public bool ConvertCaretToDelta
{
get { return _ConvertCaretToDelta; }
set { _ConvertCaretToDelta = value; }
}
public bool IncludeEmptyROFields
{
get { return _IncludeEmptyROFields; }
set { _IncludeEmptyROFields = value; }
}
public string PaperSize // C2020-002 paper size is now set in the format files
{
get { return _PaperSize; }
set { _PaperSize = value; }
}
#endregion
#region Constructors
/// <summary>
/// RO Usage Report
/// </summary>
/// <param name="reportTitle"></param>
/// <param name="typesSelected"></param>
/// <param name="myItemInfoList"></param>
/// <param name="sortByProcedure"></param>
/// <param name="includeMissingROs"></param>
/// <param name="paperSize"></param>
public DisplayReportsEventArgs(string reportTitle, string typesSelected, ICollection<ItemInfo> myItemInfoList, bool sortByProcedure, bool includeMissingROs, string paperSize)
{
_ReportTitle = reportTitle;
_TypesSelected = typesSelected;
_MyItemInfoList = myItemInfoList;
_SortUsageByProcedure = sortByProcedure;
_IncludeMissingROs = includeMissingROs;
_PaperSize = paperSize; // C2020-002 paper size is now set in the format files
}
/// <summary>
/// RO Complete
/// </summary>
/// <param name="reportTitle"></param>
/// <param name="typesSelected"></param>
/// <param name="roDataFile"></param>
/// <param name="rofstLookUp"></param>
/// <param name="completeROReport"></param>
/// <param name="convertCaretToDelta"></param>
/// <param name="includeEmptyROFields"></param>
/// <param name="paperSize"></param>
public DisplayReportsEventArgs(string reportTitle, string typesSelected, string roDataFile, ROFSTLookup rofstLookUp, bool completeROReport, bool convertCaretToDelta, bool includeEmptyROFields, string paperSize)
{
_ReportTitle = reportTitle;
_TypesSelected = typesSelected;
_RODataFile = roDataFile;
_CompleteROReport = completeROReport;
_ConvertCaretToDelta = convertCaretToDelta;
_rofstLookup = rofstLookUp;
_IncludeEmptyROFields = includeEmptyROFields;
_PaperSize = paperSize; // C2020-002 paper size is now set in the format files
}
/// <summary>
/// RO Summary Report
/// </summary>
/// <param name="reportTitle"></param>
/// <param name="typesSelected"></param>
/// <param name="rofstLookUp"></param>
/// <param name="roListForReport"></param>
/// <param name="paperSize"></param>
public DisplayReportsEventArgs(string reportTitle, string typesSelected, ROFSTLookup rofstLookUp, List<string> roListForReport, string paperSize)
{
_ReportTitle = reportTitle;
_TypesSelected = typesSelected;
_rofstLookup = rofstLookUp;
_ROListForReport = roListForReport;
_PaperSize = paperSize; // C2020-002 paper size is now set in the format files
}
#endregion
}
#endregion
public delegate void DisplayReportsEvent(object sender, DisplayReportsEventArgs args);
#region AlphanumComparatorFast Class
public class AlphanumComparatorFast : IComparer<string>
{
#region Public Methods
public List<string> GetList(string s1)
{
List<string> SB1 = new List<string>();
string st1, st2, st3;
st1 = "";
bool flag = char.IsDigit(s1[0]);
foreach (char c in s1)
{
if (flag != char.IsDigit(c) || !(char.IsDigit(c) || char.IsLetter(c)))// || c == '\'')
{
if (st1 != "")
SB1.Add(st1);
st1 = "";
flag = char.IsDigit(c);
}
if (char.IsDigit(c))
{
st1 += c;
}
if (char.IsLetter(c))
{
st1 += c;
}
}
SB1.Add(st1);
return SB1;
}
public int Compare(string x, string y)
{
string s1 = x;// as string;
if (s1 == null)
{
return 0;
}
string s2 = y;// as string;
if (s2 == null)
{
return 0;
}
if (s1 == s2)
{
return 0;
}
int len1 = s1.Length;
int len2 = s2.Length;
int marker1 = 0;
int marker2 = 0;
// Walk through two the strings with two markers.
List<string> str1 = GetList(s1);
List<string> str2 = GetList(s2);
while (str1.Count != str2.Count)
{
if (str1.Count < str2.Count)
{
str1.Add("");
}
else
{
str2.Add("");
}
}
int x1 = 0; int res = 0; int x2 = 0; string y2 = "";
bool status = false;
string y1 = ""; bool s1Status = false; bool s2Status = false;
//s1status ==false then string ele int;
//s2status ==false then string ele int;
int result = 0;
for (int i = 0; i < str1.Count && i < str2.Count; i++)
{
status = int.TryParse(str1[i].ToString(), out res);
if (res == 0)
{
y1 = str1[i].ToString();
s1Status = false;
}
else
{
x1 = Convert.ToInt32(str1[i].ToString());
s1Status = true;
}
status = int.TryParse(str2[i].ToString(), out res);
if (res == 0)
{
y2 = str2[i].ToString();
s2Status = false;
}
else
{
x2 = Convert.ToInt32(str2[i].ToString());
s2Status = true;
}
//checking --the data comparision
if (!s2Status && !s1Status) //both are strings
{
result = str1[i].CompareTo(str2[i]);
}
else if (s2Status && s1Status) //both are intergers
{
if (x1 == x2)
{
if (str1[i].ToString().Length < str2[i].ToString().Length)
{
result = 1;
}
else if (str1[i].ToString().Length > str2[i].ToString().Length)
result = -1;
else
result = 0;
}
else
{
int st1ZeroCount = str1[i].ToString().Trim().Length - str1[i].ToString().TrimStart(new char[] { '0' }).Length;
int st2ZeroCount = str2[i].ToString().Trim().Length - str2[i].ToString().TrimStart(new char[] { '0' }).Length;
if (st1ZeroCount > st2ZeroCount)
result = -1;
else if (st1ZeroCount < st2ZeroCount)
result = 1;
else
result = x1.CompareTo(x2);
}
}
else
{
result = str1[i].CompareTo(str2[i]);
}
if (result == 0)
{
continue;
}
else
break;
}
return result;
}
#endregion
}
#endregion
}