using System; using System.Collections; using System.Collections.Generic; using System.ComponentModel; using System.Configuration; using System.Data; using System.Diagnostics; using System.Drawing; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.InteropServices; using System.Security.Principal; using System.Text; using System.Threading; using System.Timers; using System.Windows.Forms; namespace QCScanner { public partial class Form1 : Form { private AutoResetEvent _resetEvent = new AutoResetEvent(false); BackgroundWorker scanToFolderThread; BackgroundWorker scanToFolderDoneThread; bool found = false; DateTime autoTime; DirectoryInfo di = new DirectoryInfo(ConfigurationManager.AppSettings["prodDataPath"]); int look = 0; IntPtr invalidHandle = IntPtr.Zero; List jobInfoList = new List(); List uniqueJobList = new List(); List boomerangFormatFile = new List(); string fileName = ""; string folderName = ""; string formatFile = ConfigurationManager.AppSettings["formatFile"]; string logFile = ""; string logFilePath = ConfigurationManager.AppSettings["logFilePath"]; string saveFolderPath = ConfigurationManager.AppSettings["saveFolderPath"]; public static string userID = WindowsIdentity.GetCurrent().Name; #region Window Finders WindowFinder main = new WindowFinder(); WindowFinder scanToFolderButton = new WindowFinder(); WindowFinder scanToFolderWnd = new WindowFinder(); WindowFinder afxMDIFrame = new WindowFinder(); WindowFinder optionsPanel = new WindowFinder(); //WindowFinder specifyFileGrpBox = new WindowFinder(); WindowFinder comboBoxFileName = new WindowFinder(); WindowFinder comboBoxExFileName = new WindowFinder(); WindowFinder comboBoxEditText = new WindowFinder(); //WindowFinder specifyFolderGrpBox = new WindowFinder(); WindowFinder textBoxFolder = new WindowFinder(); WindowFinder saveButton = new WindowFinder(); WindowFinder fileSavedWnd = new WindowFinder(); WindowFinder okButton = new WindowFinder(); #endregion WMPLib.WindowsMediaPlayer player = new WMPLib.WindowsMediaPlayer(); public Form1() { InitializeComponent(); AppDomain currentDomain = AppDomain.CurrentDomain; currentDomain.UnhandledException += new UnhandledExceptionEventHandler(catchAllHandler); } public void catchAllHandler(object sender, UnhandledExceptionEventArgs args) { Exception e = (Exception)args.ExceptionObject; //Console.WriteLine("MyHandler caught : " + e.Message); //Console.WriteLine("Runtime terminating: {0}", args.IsTerminating); MessageBox.Show("ERROR! - Catch-all Handler: " + e.Message + Environment.NewLine + e.ToString(), "Catch-all Handler", MessageBoxButtons.OK, MessageBoxIcon.Error); } public void Form1_Shown(object sender, EventArgs e) { string startupMsg = "QCScanner started."; this.Text = Application.ProductName + " v." + Application.ProductVersion; //Prep initial backgroundworkers scanToFolderThread = new BackgroundWorker(); scanToFolderThread.WorkerSupportsCancellation = true; scanToFolderThread.DoWork += new DoWorkEventHandler(scanToFolderThread_DoWork); scanToFolderDoneThread = new BackgroundWorker(); scanToFolderDoneThread.WorkerSupportsCancellation = true; scanToFolderDoneThread.DoWork += new DoWorkEventHandler(scanToFolderDoneThread_DoWork); cmbBoxJobs.Enabled = false; cmbBoxFiles.Enabled = false; radBtnStart.Enabled = false; if (loadJobs()) { cmbBoxJobs.Enabled = true; //cmbBoxJobs.SelectedIndex = 0; statusStripStatusLabel.Text = Application.ProductName + " v. " + Application.ProductVersion + " ready..."; writeToLog(startupMsg + "\r\n Jobs Loaded." + "\r\n " + statusStripStatusLabel.Text); txtBoxScanner.Focus(); } else { statusStripStatusLabel.Text = Application.ProductName + " v. " + Application.ProductVersion + " NOT ready!"; writeToLog(startupMsg + "\r\n Jobs could not be loaded." + "\r\n " + statusStripStatusLabel.Text); txtBoxScanner.Enabled = false; } } //-------------------------------------------------------------------------------------------------// private void Form1_Resize(object sender, EventArgs e) { if (FormWindowState.Minimized == this.WindowState) { notifyIconQCScanner.Visible = true; this.Hide(); } } private void notifyIconQCScanner_MouseClick(object sender, MouseEventArgs e) { this.Show(); this.WindowState = FormWindowState.Normal; } protected override void OnFormClosing(FormClosingEventArgs e) { if (MessageBox.Show("QCScanner is about to close." + Environment.NewLine + "This application is required for UltraForm jobs." + Environment.NewLine + "Are you SURE you are finished scanning pdf samples? ", "QCScanner - About to Close", MessageBoxButtons.YesNo, MessageBoxIcon.Information) == DialogResult.Yes) { writeToLog("QCScanner is closing."); scanToFolderDoneThread.Dispose(); scanToFolderThread.Dispose(); } } //-------------------------------------------------------------------------------------------------// //-------------------------------------------------------------------------------------------------// //-----Begin primary Code //-------------------------------------------------------------------------------------------------// private bool loadJobs() { jobInfoList.Clear(); uniqueJobList.Clear(); //reset the combo boxes cmbBoxJobs.Items.Clear(); cmbBoxFiles.Items.Clear(); cmbBoxFiles.Enabled = false; try { // load folders from pdfLabelFolderCPS FileInfo[] dif = di.GetFiles(); //return an array of all unique files foreach (FileInfo file in dif) { if (file.Name.EndsWith(".dat") || file.Name.EndsWith(".duf"))//filter available files by extension { cmbBoxFiles.Items.Add(file.Name); } } //get info from boomerang archive openBoomerangArchive(); uniqueJobList.Sort(); // add unique items of the array list to the listBoxJobs foreach (string sortedItem in uniqueJobList) { cmbBoxJobs.Items.Add(sortedItem); } return true; } catch (Exception err) { statusStripStatusLabel.Text = "Can't find data path: " + ConfigurationManager.AppSettings["prodDataPath"]; errorMsg(statusStripStatusLabel.Text, MethodBase.GetCurrentMethod().Name, err.ToString()); return false; } } /// /// Load the file list box with available files /// /// String to hold the unique job number (i.e. J5020) private void loadJobs(string fileFilter) { //reset the combo boxes cmbBoxJobs.Items.Clear(); cmbBoxFiles.Items.Clear(); foreach (string file in jobInfoList) { if (!cmbBoxJobs.Items.Contains(fileFilter)) { cmbBoxJobs.Items.Add(fileFilter); } Application.DoEvents(); } if (cmbBoxJobs.Items.Count > 0) { cmbBoxJobs.SelectedIndex = 0; } cmbBoxFiles.Items.Clear(); foreach (string file in jobInfoList) { if (file.Split(';')[1].Contains(txtBoxScanner.Text)) { cmbBoxFiles.Items.Add(file.Split(';')[1]); } else if (file.Split(';')[0].Contains(txtBoxScanner.Text)) { cmbBoxFiles.Items.Add(file.Split(';')[1]); } } if (cmbBoxFiles.Items.Count > 0) { cmbBoxFiles.SelectedIndex = 0; } } void scanToFolderThread_DoWork(object sender, DoWorkEventArgs e) { writeToLog("Scan Started - Save to Folder button clicked."); timerScanToFolder_Tick(sender, e); } void scanToFolderDoneThread_DoWork(object sender, DoWorkEventArgs e) { writeToLog("File Saved - " + folderName + @"\" + fileName + ".pdf"); clickFileSaveCompleteOk(); } #region Timers private void lookForScanSnap(object sender, EventArgs e) { if (autoTime.AddSeconds(10).Second == DateTime.Now.Second) //We've waited and now the auto-run process begins... { timerAutoMode.Stop(); statusStripStatusLabel.Text = "Looking for ScanSnap Quick Menu..."; timerScanSnap_Tick(this, null); //reset the app if (found) { found = false; player.URL = ConfigurationManager.AppSettings["scanCompleteSound"]; player.controls.play(); player.settings.playCount = 1; } if (look != 0) { look = 0; } autoTime = DateTime.Now.AddSeconds(10); //Next run will be in xD secs timerAutoMode.Start(); } else { statusStripStatusLabel.Text = "Wait a minute..."; } } private void timerAutoMode_Tick(object sender, EventArgs e) { lookForScanSnap(sender, e); } private void timerScanSnap_Tick(object sender, EventArgs e) { //When this timer's interval is up, here is what we do... //We are processing... have the program autosend the file info to ScanSnap QuickMenu if (!found) { look++; statusStripStatusLabel.Text = "Looking for ScanSnap window, attempt #" + look; Application.DoEvents(); if (look > 90) { //Tried to pull up DoPDF window and couldn't find anything. //Tell the user through the status bar and exit Automation Mode statusStripStatusLabel.Text = "ScanSnap Manager window not found. Aborting auto mode."; timerScanSnap.Stop(); } else { //Reset the backgroundworker if it's stuck if (scanToFolderThread.IsBusy) { scanToFolderThread.CancelAsync(); _resetEvent.WaitOne(); scanToFolderThread = new BackgroundWorker(); scanToFolderThread.WorkerSupportsCancellation = true; scanToFolderThread.DoWork += new DoWorkEventHandler(scanToFolderThread_DoWork); } main.Window = main.Find("QuickMenu MainWndClass", "ScanSnap Quick Menu"); if (main.Window == invalidHandle) { //window does not exist statusStripStatusLabel.Text = "Waiting for ScanSnap window..."; Application.DoEvents(); } else { // Step 1. Set the pdf filename fileName = cmbBoxFiles.SelectedItem.ToString().Substring(0, cmbBoxFiles.SelectedItem.ToString().Length - 4) + "_" + DateTime.Now.ToString("yyyyMMdd_HHmm"); lblNamePreview.Text = "Filename preview : " + fileName + ".pdf"; // Step 2. Click the Save to Folder button scanToFolderButton.Window = scanToFolderButton.Find(main.Window, IntPtr.Zero, "Button", "Scan to Folder"); if (scanToFolderButton.Window == invalidHandle) { //unable to hook onto Scan to Folder button statusStripStatusLabel.Text = "Couldn't find Save to Folder button!"; Application.DoEvents(); } else { found = true; timerScanSnap.Stop(); statusStripStatusLabel.Text = "Found Save to Folder button."; scanToFolderThread.RunWorkerAsync(); scanToFolderButton.ClickButton(); } } } } } /// /// Main Timer to look for the ScanSnap Window items /// /// /// private void timerScanToFolder_Tick(object sender, EventArgs e) { //When this timer's interval is up, here is what we do... //We are processing... have the program autosend the file info to ScanSnap QuickMenu Directory.CreateDirectory(saveFolderPath); Thread.Sleep(2000); Application.DoEvents(); //Reset the backgroundworker if it's stuck if (scanToFolderDoneThread.IsBusy) { scanToFolderDoneThread.CancelAsync(); _resetEvent.WaitOne(); scanToFolderDoneThread = new BackgroundWorker(); scanToFolderDoneThread.WorkerSupportsCancellation = true; scanToFolderDoneThread.DoWork += new DoWorkEventHandler(scanToFolderDoneThread_DoWork); } //Step 3. Open and enter info, then click save scanToFolderWnd.Window = scanToFolderWnd.Find("ScanToFolder_Preview_WindowClass", "Scan to Folder"); afxMDIFrame.Window = afxMDIFrame.Find(scanToFolderWnd.Window, IntPtr.Zero, "AfxMDIFrame80", null); optionsPanel.Window = optionsPanel.Find(afxMDIFrame.Window, IntPtr.Zero, "#32770", null); //optionsPanel.SetForegroundWindow(); if (optionsPanel.Window == invalidHandle) { //window does not exist Application.DoEvents(); } else { found = true; timerScanToFolder.Stop(); Thread.Sleep(2000); //statusStripStatusLabel.Text = "Scan to Folder preview window found, entering info."; timerScanSnap.Stop(); comboBoxExFileName.Window = comboBoxExFileName.Find(optionsPanel.Window, IntPtr.Zero, "ComboBoxEx32", null); comboBoxFileName.Window = comboBoxFileName.Find(comboBoxExFileName.Window, IntPtr.Zero, "ComboBox", null); comboBoxEditText.Window = comboBoxEditText.Find(comboBoxFileName.Window, IntPtr.Zero, "Edit", null); if (comboBoxEditText.Window == invalidHandle) { statusStripStatusLabel.Text = "Text box not found yet..."; Application.DoEvents(); } else { timerScanToFolder.Stop(); comboBoxEditText.SetEditText(fileName); writeToLog("Inserting 'File name' text: " + fileName); found = true; Application.DoEvents(); } textBoxFolder.Window = textBoxFolder.Find(optionsPanel.Window, IntPtr.Zero, "Edit", null); if (textBoxFolder.Window == invalidHandle) { //statusStripStatusLabel.Text = "Text box not found yet..."; Application.DoEvents(); } else { //statusStripStatusLabel.Text = "Found save in text box."; textBoxFolder.SetEditText(folderName); writeToLog("Inserting 'Save in' text: " + folderName); Application.DoEvents(); } saveButton.Window = saveButton.Find(optionsPanel.Window, IntPtr.Zero, "Button", "&Save"); if (saveButton.Window == invalidHandle) { //unable to hook onto Save button //statusStripStatusLabel.Text = "Couldn't find Save button!"; Application.DoEvents(); } else { //statusStripStatusLabel.Text = "Found Save button."; scanToFolderDoneThread.RunWorkerAsync(); saveButton.ClickButton(); scanToFolderThread.CancelAsync(); } } } #endregion //-------------------------------------------------------------------------------------------------// //-----Begin secondary Code //-------------------------------------------------------------------------------------------------// private void clickFileSaveCompleteOk() { //Step 4. Ok to close the ScanSnap app Thread.Sleep(2000); fileSavedWnd.Window = fileSavedWnd.Find("#32770", "Scan to Folder"); if (fileSavedWnd.Window == invalidHandle) { //statusStripStatusLabel.Text = "File saved window not found yet..."; Application.DoEvents(); } else { //statusStripStatusLabel.Text = "File saved window found."; okButton.Window = okButton.Find(fileSavedWnd.Window, IntPtr.Zero, "Button", "Ok"); if (okButton.Window == invalidHandle) { //unable to hook onto OK button //statusStripStatusLabel.Text = "Couldn't find Ok button!"; Application.DoEvents(); } else { //statusStripStatusLabel.Text = "Found Ok button."; okButton.ClickButton(); scanToFolderDoneThread.CancelAsync(); writeToLog("Scan Complete - Ok button clicked."); } } } /// /// Formatted error messaging to be written to the log file. /// /// String containing the main message /// String containing the calling method /// String to hold the exception private void errorMsg(string comment, string method, string error) { statusStripStatusLabel.Text = "Error! - " + method + " - " + comment; writeToLog(statusStripStatusLabel.Text + "\r\n" + error); } /// /// Get job name from Boomerang formats file /// private void openBoomerangArchive() { if (boomerangFormatFile.Count == 0)//format file is not loaded { try { using (FileStream fsFr = new FileStream(formatFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite)) using (StreamReader sr1 = new StreamReader(fsFr)) { string s = ""; while ((s = sr1.ReadLine()) != null) { boomerangFormatFile.Add(s); } sr1.Close(); sr1.Dispose(); fsFr.Close(); fsFr.Dispose(); } } catch (Exception err) { if (err is ArgumentOutOfRangeException) { statusStripStatusLabel.Text = "The Boomerang format for " + formatFile + " is missing inforamtion, or argument out of range!"; } else if (err is IndexOutOfRangeException) { statusStripStatusLabel.Text = "The Boomerang format for " + formatFile + " is missing fields and needs to be updated!"; } else { statusStripStatusLabel.Text = "The Boomerang format archive could not be found!"; } errorMsg(statusStripStatusLabel.Text, MethodBase.GetCurrentMethod().Name, err.ToString()); } } foreach (string outFile in cmbBoxFiles.Items) { string jobNumber = ""; { foreach (string s in boomerangFormatFile) { if (outFile.StartsWith("a") && s.Contains(outFile.Substring(0, 5)))//check "a" formats for automation jobs { string[] formatLine = s.Split(';'); jobNumber = formatLine[4]; //get jobnum jobInfoList.Add(jobNumber + ";" + outFile); if (!uniqueJobList.Contains(jobNumber)) { uniqueJobList.Add(jobNumber); } } else if (!outFile.StartsWith("a") && s.Contains(outFile.Substring(0, 4)))//check other formats { string[] formatLine = s.Split(';'); jobNumber = formatLine[4]; //get jobnum; jobInfoList.Add(jobNumber + ";" + outFile); if (!uniqueJobList.Contains(jobNumber)) { uniqueJobList.Add(jobNumber); } } } } } } /// /// Writes information to the job log file /// /// String info to write private void writeToLog(string information) { logFile = logFilePath + "\\" + DateTime.Today.ToString("yyyyMMdd") + "_logfile.txt"; try { using (StreamWriter w = File.AppendText(logFile)) { w.WriteLine("{0} {1}: {2}\n", DateTime.Now, userID, information); w.Close(); w.Dispose(); } } catch { MessageBox.Show("Unable to write to " + logFilePath + "! Please check for a log folder...", "ERROR! - Log Folder Location", MessageBoxButtons.OK, MessageBoxIcon.Error); Application.DoEvents(); } } //-------------------------------------------------------------------------------------------------// //-----Begin tertiary Code //-------------------------------------------------------------------------------------------------// #region Comboboxes private void cmbBoxJobs_SelectedIndexChanged(object sender, EventArgs e) { cmbBoxFiles.Items.Clear(); foreach (string jobListItem in jobInfoList) { if (jobListItem.Contains(cmbBoxJobs.SelectedItem.ToString())) { cmbBoxFiles.Items.Add(jobListItem.Split(';')[1]); } } cmbBoxFiles.SelectedIndex = 0; radBtnStart.Enabled = false; cmbBoxFiles.Enabled = true; } private void cmbBoxFiles_SelectedIndexChanged(object sender, EventArgs e) { folderName = saveFolderPath + cmbBoxJobs.SelectedItem.ToString(); lblFolderPreview.Text = "Save folder preview: " + folderName; radBtnStart.Enabled = true; } #endregion #region Labels private void lblAbout_Click(object sender, EventArgs e) { aboutQCScanner about = new aboutQCScanner(); about.ShowDialog(this); } private void lblAbout_MouseEnter(object sender, EventArgs e) { lblAbout.ForeColor = Color.MediumBlue; lblAbout.Font = new Font(lblAbout.Font.Name, lblAbout.Font.SizeInPoints, FontStyle.Underline); } private void lblAbout_MouseLeave(object sender, EventArgs e) { lblAbout.ForeColor = Color.MidnightBlue; lblAbout.Font = new Font(lblAbout.Font.Name, lblAbout.Font.SizeInPoints, FontStyle.Regular); } private void lblUsing_Click(object sender, EventArgs e) { Process.Start(ConfigurationManager.AppSettings["manualFile"]); } private void lblUsing_MouseEnter(object sender, EventArgs e) { lblUsing.ForeColor = Color.MediumBlue; lblUsing.Font = new Font(lblUsing.Font.Name, lblUsing.Font.SizeInPoints, FontStyle.Underline); } private void lblUsing_MouseLeave(object sender, EventArgs e) { lblUsing.ForeColor = Color.MidnightBlue; lblUsing.Font = new Font(lblUsing.Font.Name, lblUsing.Font.SizeInPoints, FontStyle.Regular); } #endregion #region Radio Buttons private void radBtnStart_Click(object sender, EventArgs e) { panelRadBtnStart.BorderStyle = System.Windows.Forms.BorderStyle.Fixed3D; panelRadBtnStop.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle; txtBoxScanner.Enabled = false; cmbBoxFiles.Enabled = false; cmbBoxJobs.Enabled = false; radBtnStop.Checked = false; writeToLog("//----- Started - Job#: " + cmbBoxJobs.SelectedItem + " - " + "Source File: " + cmbBoxFiles.SelectedItem + "-----\\"); try { if (!Directory.Exists(folderName)) { writeToLog("Creating missing folder - " + folderName); } //make the necessary job folder if it doesn't exist Directory.CreateDirectory(folderName); } catch (Exception err) { MessageBox.Show("Cannot create folder", err.ToString()); } autoTime = DateTime.Now.AddSeconds(10); timerAutoMode.Start(); radBtnStart.Text = "Running"; radBtnStart.ForeColor = Color.Green; radBtnStop.Text = "Stop"; radBtnStop.ForeColor = Color.Black; } private void radBtnStop_Click(object sender, EventArgs e) { panelRadBtnStop.BorderStyle = System.Windows.Forms.BorderStyle.Fixed3D; panelRadBtnStart.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle; txtBoxScanner.Enabled = true; cmbBoxFiles.Enabled = true; cmbBoxJobs.Enabled = true; radBtnStart.Checked = false; writeToLog("//----- Stopped - Job#: " + cmbBoxJobs.SelectedItem + " - " + "Source File: " + cmbBoxFiles.SelectedItem + "-----\\"); timerAutoMode.Stop(); timerScanSnap.Stop(); timerScanToFolder.Stop(); scanToFolderDoneThread.Dispose(); scanToFolderThread.Dispose(); radBtnStart.Text = "Start"; radBtnStart.ForeColor = Color.Black; radBtnStop.Text = "Stopped"; radBtnStop.ForeColor = Color.Red; statusStripStatusLabel.Text = ""; } #endregion #region Textbox private void txtBoxScanner_Click(object sender, EventArgs e) { txtBoxScanner.SelectAll(); txtBoxScanner.Focus(); } private void txtBoxScanner_Enter(object sender, EventArgs e) { txtBoxScanner.SelectAll(); txtBoxScanner.Focus(); } private void txtBoxScanner_KeyDown(object sender, KeyEventArgs e) { //handle return/enter key press or handheld scanner's carriage return if (e.KeyValue == 13) { if (txtBoxScanner.Text != "Type (or scan) to search") { if (!String.IsNullOrEmpty(txtBoxScanner.Text))//text box is not empty { string fileFilter = ""; if (txtBoxScanner.Text.Contains("_PackingSlip"))//scanning the packing slip barcode from a FCCS { txtBoxScanner.Text = txtBoxScanner.Text.Split('_')[0].Replace("J00", "J"); Application.DoEvents(); fileFilter = txtBoxScanner.Text.Split('_')[0].Replace("J00", ""); } else if (txtBoxScanner.Text.Contains("_C") || txtBoxScanner.Text.Contains("_S"))//scanning a label barcode from a FCCS { foreach (string jobInfoItem in jobInfoList) { if (jobInfoItem.Contains(txtBoxScanner.Text)) { fileFilter = jobInfoItem.Split(';')[0]; } else if (jobInfoItem.Contains(txtBoxScanner.Text.Substring(0, 5))) { fileFilter = jobInfoItem.Split(';')[0]; } } txtBoxScanner.Text = fileFilter; Application.DoEvents(); } else { if (txtBoxScanner.Text.StartsWith("J") || txtBoxScanner.Text.StartsWith("a"))//auto jobs { foreach (string jobInfoItem in jobInfoList) { if (jobInfoItem.Contains(txtBoxScanner.Text)) { fileFilter = jobInfoItem.Split(';')[0]; } else if (jobInfoItem.Contains(txtBoxScanner.Text.Substring(0, 5))) { fileFilter = jobInfoItem.Split(';')[0]; } } } else//manual jobs { foreach (string jobInfoItem in jobInfoList) { if (jobInfoItem.Contains(txtBoxScanner.Text)) { fileFilter = jobInfoItem.Split(';')[0]; } else if (jobInfoItem.Contains(txtBoxScanner.Text.Substring(0, 4))) { fileFilter = jobInfoItem.Split(';')[0]; } } } } cmbBoxJobs.Items.Clear(); loadJobs(fileFilter); Application.DoEvents(); } else { txtBoxScanner.Text = "Type (or scan) to search"; } } else if (String.IsNullOrEmpty(txtBoxScanner.Text) || txtBoxScanner.Text == "Type (or scan) to search") { loadJobs(); } } } #endregion } }