Novo

Forum kao aplikacija na telefonu

Dodajte forum na početni ekran i koristite ga kao aplikaciju, sa menijem na dnu ekrana.

  • 11 odgovora
  • 3.238 pregleda

Najnovija ↓

Dobijanje IDispatch iz procesa ili aplikacije 12.11.2010. u 23:09 · pre 194 meseca #1
Ono što pokušavam da uradim je da preko COM (Component Objject Model) pristupim aplikaciji koju nisam otvorio preko COM-a. Recimo, konkretno želim da zatvorim word proces. Znam preko COM-a lepo da otvorim proces word-a i da mu šaljem komande da piše, ubacuje slike, prepoznaje tekst itd. E sad bi mi trebalo takođe da uhvatim kontrolu word-u čiji proces nisam kreirao. Da li je to moguće uraditi, tj da li je moguće dohvatiti IDispatch tog procesa. Da li je možda moguće zatvoriti proces worda na neki drugi način? I kako se to radi?
Hvala unapred na odgovoru.
Potpis
www.starisloveni.com
www.inspiratron.org
Re: Dobijanje IDispatch iz procesa ili aplikacije 15.11.2010. u 21:42 · pre 194 meseca #2
Dobijanje IDispatch interfejsa nije moguce u svim slucajevima. Treba da imas na umu da kada se instancira word za manipulisanje preko COM metoda pokrece se nova instanca sa <word.exe> /automation.

Ono sto mozes je da izlistas sve procese koji se trenutno izvrsavaju i da na osnovu nekog parametra odredis koji bi hteo da zatvoris.

Na primer:

Single interface for enumerating processes and modules under NT and Win9x/2K
http://www.codeguru.com/Cpp/W-...essesmodules/article.php/c5729

Pa onda koriscenjem API funkcije TerminateProcess ubijes na silu zeljeni proces
http://msdn.microsoft.com/en-us/library/ms686714(v=VS.85).aspx

ili nadjes glavni prozor tog procesa sa EnumerateWindows API funkcijom i posaljes mu WM_CLOSE poruku sa SendNotifyMessage
http://msdn.microsoft.com/en-us/library/ms644953%28VS.85%29.aspx
Potpis
Tko leti vrijedi
Re: Dobijanje IDispatch iz procesa ili aplikacije 06.12.2010. u 04:40 · pre 193 meseca #4
Zasto mu dajes lose savete?

Je'l se ovde bavimo c++om ili programiranjem skripti?

Nema nista gore nego pisati programe koji pozivaju externe CLI aplikacije samo zato sto je to "lakse i brze" (a ne i najbolje). Ako je vec cilj lakse i brze onda uzmi lepo notepad i pishi batch script.

Potpis
Tko leti vrijedi
Re: Dobijanje IDispatch iz procesa ili aplikacije 06.12.2010. u 10:49 · pre 193 meseca #5
Ne vidim zasto je los savet? Covek je lepo pitao "Da li je možda moguće zatvoriti proces worda na neki drugi način? I kako se to radi?".

Ja ne bi tako uradio ali to ne znaci da ne moze a i prosto je za iskodirati

Potpis
Sloba je za 12 godina promenio antropološki kod srpskog naroda. On je od jednog
naroda koji je bio veseo, pomalo površan, od jednog naroda koji je bio znatiželjan, koji
je voleo da vidi, da putuje, da upozna,
od naroda koji je bio kosmopolitski napravio narod koji je namršten, mrzovoljan,
sumnjicav, zaplašen, narod koji se stalno nešto žali, kome je stalno neko kriv - Z.Đinđić
Re: Dobijanje IDispatch iz procesa ili aplikacije 06.12.2010. u 15:14 · pre 193 meseca #6
Savet je los zato sto stvara naviku da se sve "krpi" gomilom pokupljenih delova koda koji posle cine nekog frankenstajna. Naravno da sve moze. Ali valjda je cilj i neka konzistencija i kvalitet a ne samo - "daj da ga resim za 45 sekundi".
Potpis
Tko leti vrijedi
Re: Dobijanje IDispatch iz procesa ili aplikacije 07.12.2010. u 17:02 · pre 193 meseca #7
Naziv topika "Dobijanje IDispatch iz procesa ili aplikacije" zaista nema mnogo veze sa onim što je autor na kraju pojasnio da želi da ubije word.

Savjeti možda jesu loši jer podrazumjevaju nasilno gašenje worda ali vjerovatno bi to trebala biti zadnja solucija ako ostalo zakaže.

Ono što bi bio konstruktivan savjet je konkretan primjer dobijanja IDispatch-a od worda koji nisi kreirao - pa da vidimo koliko je to errorprone naspram ostalih rješenja.

Potpis
http://www.padfm.com
Re: Dobijanje IDispatch iz procesa ili aplikacije 07.12.2010. u 17:23 · pre 193 meseca #8
Citat:
ljube:
Ono što bi bio konstruktivan savjet je konkretan primjer dobijanja IDispatch-a od worda koji nisi kreirao - pa da vidimo koliko je to errorprone naspram ostalih rješenja.


OK kad je vec tako evo sta kaze Microsoft

How To Attach to a Running Instance of an Office Application

Potpis
Tko leti vrijedi
Re: Dobijanje IDispatch iz procesa ili aplikacije 07.12.2010. u 20:20 · pre 193 meseca
izmenjeno 1 put, poslednji put kiklop74 07.12.2010. u 20:45
  1. kiklop7407.12.2010. u 20:45zapis iz teksta poruke
#10
A evo i programa koji zatvara word (moze da se kompaljira samo sa msvc)

Code:

// killword.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include <comdef.h>
#include <iostream>

#ifdef UNICODE
#define tclog std::wclog
#else
#define tclog std::clog
#endif

#pragma comment(lib,"comsuppwd.lib")

struct ole {
    ole(void): shouldRelease(false) {
        HRESULT hr = ::CoInitializeEx(NULL, COINIT_MULTITHREADED);
        shouldRelease = ((hr == S_OK) || (hr == S_FALSE));
    }
    ~ole(void) {
        docleanup();
    }
private:
    volatile bool shouldRelease;
    void docleanup(void) {
        if (shouldRelease) {
            shouldRelease = false;
            ::CoUninitialize();
        }
    }
};

/*_com_dispatch_help

L"\x0009" - IDispatch*
L"\x0008" - BSTR
L"\x000b" - boolean
L"\x000c" - enum
L"\x400c" - VARIANT*
*/

HRESULT CloseWord(void) {
    ole ol;
    HRESULT result = S_OK;

    try {

        IUnknownPtr ppunk;
        IDispatchPtr ppdisp;

        result = ppunk.GetActiveObject("Word.Application");
        _com_util::CheckError(result);
        {
        IDispatch *pdisp = NULL;
        result = ppunk.QueryInterface(IID_IDispatch,pdisp);
        _com_util::CheckError(result);
        ppdisp.Attach(pdisp);
        ppunk.Release();
        }

        LPOLESTR name=L"Quit"; 
        DISPID dispid = NULL;
        result = ppdisp->GetIDsOfNames (
                                 IID_NULL,
                                 &name,
                                 1,
                                 LOCALE_USER_DEFAULT,
                                 &dispid);
        _com_util::CheckError(result);

        variant_t save(false);
        variant_t empty;
        result = _com_dispatch_method( ppdisp
                                      ,dispid
                                      ,DISPATCH_METHOD
                                      ,VT_EMPTY
                                      ,NULL
                                      ,L"\x400c\x400c\x400c"
                                      ,&save
                                      ,&empty
                                      ,&empty
                                      );
    } catch(const _com_error& e) {
        tclog << e.ErrorMessage() << std::endl;
    }
    
    return result;
}


int __cdecl _tmain(int /*argc*/, _TCHAR** /*argv[]*/) {

    if ( SUCCEEDED(CloseWord()) ) {
        tclog << TEXT("Closed Word instance.") << std::endl;
    }
    return 0;
}

Potpis
Tko leti vrijedi
Re: Dobijanje IDispatch iz procesa ili aplikacije 07.12.2010. u 21:38 · pre 193 meseca #12
Nije neobicno ponasanje. To je klasicna primena RAII idioma.

http://en.wikipedia.org/wiki/RAII

Time se garantuje da ce COM biti adekvatno zatvoren cak i u slucaju izuzetka. Takodje smanjuje kolicinu koda.

Inace struct i class su sinonimi. Jedina razlika je da su kod deklaratora class svi elementi po defaultu private dok su kod struct svi elementi public iliti:

Code:


class{
public:

};

//je ekvivalentno:

struct {
};




Potpis
Tko leti vrijedi
Prijavite se da biste odgovorili u ovoj temi.PrijavaRegistracija

Premeštanje teme