Как получить экземпляр Excel или экземпляр Excel CLSID с помощью идентификатора процесса?
Я работаю с С#, мне нужно получить конкретный экземпляр excel с помощью идентификатора процесса; Я получаю идентификатор процесса экземпляра, который мне нужен из другого приложения, но я не знаю, что еще делать, я не знаю, как я могу получить исполняемый экземпляр excel с его идентификатором процесса.
Я много исследовал в Интернете, но я вижу только примеры использования Marshal.GetActiveObject(...) или Marshal.BindToMoniker(...), которые я не могу использовать, поскольку первый возвращает первый экземпляр Excel, зарегистрированный в ROT, а не тот, который мне нужен, а второй требует, чтобы вы сохранили файл excel, прежде чем пытаться получить экземпляр.
Кроме того, если я могу получить CLSID экземпляра excel, который мне нужен, используя идентификатор процесса, тогда я могу позвонить
GetActiveObject(ref _guid, _ptr, out objApp);
который в конечном итоге вернет экземпляр excel, который мне нужен.
Ответы
Ответ 1
Как только вы идентифицируете процесс с помощью идентификатора процесса, вы можете получить Process.MainWindowHandle, а затем использовать его вместе с AccessibleObjectFromWindow API, чтобы получить доступ к объектной модели Excel для этого процесса.
В статье "Приобретение объекта приложения в надстроенной надстройке надстройки" Эндрю Уайтчепел подробно описывает эту технику вместе с образцом кода.
key code в этой статье для вас начинается с строки:
int hwnd = (int)Process.GetCurrentProcess().MainWindowHandle
Что в вашем случае может выглядеть больше:
int excelId = 1234; // Change as appropriate!
int hwnd = (int)Process.GetProcessById(excelId).MainWindowHandle
где "excelId" - это номер идентификатора процесса, который вы ищете. В противном случае код должен быть по существу таким же, как в данной статье. (Игнорируйте тот факт, что его код написан для надстройки, этот аспект не повлияет на ваши потребности здесь, поэтому просто игнорируйте его.)
Если у вас нет идентификатора процесса, то вы хотите использовать Process.GetProcessesByName, посредством чего вы можете перечислить каждый из них и захватить управление каждым экземпляром Excel с доступом к объектной модели по мере необходимости.
Надеюсь, что это поможет,
Mike
Ответ 2
Записи ROT не помечены CLSID. ROT возвращает DWORD из Register, который используется как идентификатор для Unregister.
Я столкнулся с этой проблемой раньше, и единственный способ, которым я решил, - это добавить какую-либо надстройку в каждый Excel, с которой вы можете напрямую общаться.
Ответ 3
using System.Diagnostics;
var eProcess = from p in Process.GetProcessesByName("EXCEL")
where p.Id == 3700 //whatever Id you have...
select p;
foreach (var process in eProcess)
process.Kill();
Получает все процессы с именем "EXCEL", где Id процесса равен конкретному значению.