void UpdateFormula(bool textChangedOnly = false) { Logger.WindowWatcher.Verbose($">>>> FormulaEditWatcher.UpdateFormula on thread {Thread.CurrentThread.ManagedThreadId}"); CurrentPrefix = XlCall.GetFormulaEditPrefix(); // What thread do we have to use here ...? Logger.WindowWatcher.Verbose($">>>> FormulaEditWatcher.UpdateFormula CurrentPrefix: {CurrentPrefix}"); OnStateChanged(textChangedOnly ? new StateChangeEventArgs(StateChangeType.TextChange) : StateChangeEventArgs.Empty); }
void UpdateEditStateImpl(bool moveOnly = false) { Logger.WindowWatcher.Verbose($"> FormulaEdit UpdateEditState - Thread {Thread.CurrentThread.ManagedThreadId}"); Logger.WindowWatcher.Verbose($"FormulaEdit UpdateEditState - Focus: {_formulaEditFocus} Window: {(_formulaEditFocus == FormulaEditFocus.FormulaBar ? _hwndFormulaBar : _hwndInCellEdit)}"); IntPtr hwnd = IntPtr.Zero; bool prefixChanged = false; if (_formulaEditFocus == FormulaEditFocus.FormulaBar) { hwnd = _hwndFormulaBar; } else if (_formulaEditFocus == FormulaEditFocus.InCellEdit) { hwnd = _hwndInCellEdit; } else { // Neither have the focus, so we don't update anything Logger.WindowWatcher.Verbose("FormulaEdit UpdateEditState End formula editing"); CurrentPrefix = null; if (IsEditingFormula) { UninstallLocationMonitor(); } IsEditingFormula = false; prefixChanged = true; // Debug.Print("#### FormulaEditWatcher - No Window " + Environment.StackTrace); } if (hwnd != IntPtr.Zero) { EditWindowBounds = Win32Helper.GetWindowBounds(hwnd); if (!IsEditingFormula) { IntPtr hwndTopLevel = Win32Helper.GetRootAncestor(hwnd); InstallLocationMonitor(hwndTopLevel); IsEditingFormula = true; } var newPrefix = XlCall.GetFormulaEditPrefix(); // What thread do we have to use here ...? if (CurrentPrefix != newPrefix) { CurrentPrefix = newPrefix; prefixChanged = true; } Logger.WindowWatcher.Verbose($"FormulaEdit UpdateEditState Formula editing: CurrentPrefix {CurrentPrefix}, EditWindowBounds: {EditWindowBounds}"); } // TODO: Smarter (or more direct) notification...? if (moveOnly && !prefixChanged) { StateChanged?.Invoke(this, new StateChangeEventArgs(StateChangeType.Move)); } else { OnStateChanged(StateChangeType.Multiple); } }
void UpdateFormula() { _syncContext.Post(delegate { // CurrentFormula = ""; CurrentPrefix = XlCall.GetFormulaEditPrefix(); StateChanged(this, new StateChangeEventArgs()); }, null); }
// Called on some ThreadPool thread... void FormulaPollingCallback(object _unused_) { // Logger.WindowWatcher.Verbose($"FormulaEdit - FormulaPollingCallback"); // Check for Disposed already // TODO: Check again whether System.Timers.Timer can fire after Dispose()... if (_formulaPollingTimer == null) { return; } var oldPrefix = CurrentPrefix; var newPrefix = XlCall.GetFormulaEditPrefix(); if (oldPrefix != newPrefix) { // CONSIDER: What to do if newPrefix is null (not editing...) CurrentPrefix = newPrefix; OnStateChanged(new StateChangeEventArgs(StateChangeType.TextChange)); } }
// Switches to our Automation thread, updates current state and raises StateChanged event void UpdateEditState(bool moveOnly = false) { Logger.WindowWatcher.Verbose("> FormulaEdit UpdateEditState - Posted"); _syncContextAuto.Post(moveOnlyObj => { Logger.WindowWatcher.Verbose($"FormulaEdit UpdateEditState - Focus: {_formulaEditFocus}"); //// TODO: This is not right yet - the list box might have the focus... ? //AutomationElement focused; //try //{ // focused = AutomationElement.FocusedElement; //} //catch (ArgumentException aex) //{ // Debug.Print($"!!! ERROR: Failed to get Focused Element: {aex}"); // // Not sure why I get this - sometimes with startup screen // return; //} AutomationElement focusedEdit = null; bool prefixChanged = false; if (_formulaEditFocus == FormulaEditFocus.FormulaBar) { focusedEdit = _formulaBar; } else if (_formulaEditFocus == FormulaEditFocus.InCellEdit) { focusedEdit = _inCellEdit; } else { // Neither have the focus, so we don't update anything Logger.WindowWatcher.Verbose("FormulaEdit UpdateEditState End formula editing"); CurrentPrefix = null; if (IsEditingFormula) { UninstallLocationMonitor(); } IsEditingFormula = false; prefixChanged = true; // Debug.Print("Don't have a focused text box to update."); } if (focusedEdit != null) { EditWindowBounds = (Rect)focusedEdit.GetCurrentPropertyValue(AutomationElement.BoundingRectangleProperty); IntPtr hwnd = (IntPtr)(int)focusedEdit.GetCurrentPropertyValue(AutomationElement.NativeWindowHandleProperty); var pt = Win32Helper.GetClientCursorPos(hwnd); if (!IsEditingFormula) { InstallLocationMonitor(GetTopLevelWindow(focusedEdit)); } IsEditingFormula = true; var newPrefix = XlCall.GetFormulaEditPrefix(); // What thread do we have to use here ...? if (CurrentPrefix != newPrefix) { CurrentPrefix = newPrefix; prefixChanged = true; } Logger.WindowWatcher.Verbose($"FormulaEdit UpdateEditState Formula editing: CurrentPrefix {CurrentPrefix}, EditWindowBounds: {EditWindowBounds}"); } // TODO: Smarter notification...? if ((bool)moveOnlyObj && !prefixChanged) { StateChanged?.Invoke(this, new StateChangeEventArgs(StateChangeType.Move)); } else { OnStateChanged(new StateChangeEventArgs(StateChangeType.Multiple)); } }, moveOnly); }