• Revista PROGRAMAR: Já está disponível a edição #53 da revista programar. Faz já o download aqui!

rjcp

Como verificar se este programa já está aberto?

8 mensagens neste tópico

Boa tarde a todos uma vez mais

O projecto está praticamente a chegar ao fim mas existem algumas arestas a limar.

Como posso verificar se esta aplicação já está aberta não deixando abrir uma nova? É que não faz o mínimo sentido ter duas aplicações iguais a correr. Eu queria evitar que o utilizador abrisse duas janelas iguais, aparecendo um aviso de que já se encontra uma aberta.

Obrigado

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Bom, vim precisamente ver do mesmo, isto é, já consigo saber se a minha aplicação está já aberta só que queria fazer algo diferente: caso a aplicação já estivesse aberta maximizava-a e colocava-a com o foco.. Isso é que ainda não consigo fazer.

Para a tua questão existem duas formas de obter o pretendido.

1ª Com um mutex. Testas a existência de um mutex, se já existir é porque a aplicação já está aberta, se não crias o mutex e carregas a aplicação.

2ª Pelo nome do processo. Pesquisas na árvore de processos em execução e se existir um com o nome do teu, é porque já está aberto ou existe algum programa aberto com o mesmo nome do teu. Esta segunda forma é a que estou a utilizar mas considero que não é a mais perfeita porque caso exista um programa a correr com o mesmo nome que o teu, não vais conseguir correr o teu (penso eu porque não experimentei) e, estou a usar um serviço associado à minha aplicação, isto é, se a minha aplicação for chamada pelo start do service manager corre como um serviço, senão corre como aplicação, o que acontece é que se estiver a correr como serviço aparece na árvore de processos com o nome correcto, mas ao iniciar como aplicação deixa correr à mesma porque parece que se esquece de testar a sub-árvore dos serviços e não mostra a mensagem de aplicação já aberta, no entanto em todas as outras situações que experimentei funcionou *****.

Tens aqui um dos link's que me ajudou e de onde tirei a informação. Podes também procurar no google por - single instance + c#

http://www.ai.uga.edu/mc/SingleInstance.html  :D

Caso alguém tenha uma resposta para a minha dúvida de maximizar a janela agradecia que xutassem pois estou às voltas há já muito tempo sem resposta nenhuma em concreto.  :rant_01:

Caso precises posso aqui deixar o meu código que está um pouco alterado para a minha aplicação.

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Já está. Fiz como o dpeneireiro disse e funciona perfeitamente, tal como eu queria.

Obrigado  :D

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Bom, vim precisamente ver do mesmo, isto é, já consigo saber se a minha aplicação está já aberta só que queria fazer algo diferente: caso a aplicação já estivesse aberta maximizava-a e colocava-a com o foco.. Isso é que ainda não consigo fazer.

Para a tua questão existem duas formas de obter o pretendido.

1ª Com um mutex. Testas a existência de um mutex, se já existir é porque a aplicação já está aberta, se não crias o mutex e carregas a aplicação.

2ª Pelo nome do processo. Pesquisas na árvore de processos em execução e se existir um com o nome do teu, é porque já está aberto ou existe algum programa aberto com o mesmo nome do teu. Esta segunda forma é a que estou a utilizar mas considero que não é a mais perfeita porque caso exista um programa a correr com o mesmo nome que o teu, não vais conseguir correr o teu (penso eu porque não experimentei) e, estou a usar um serviço associado à minha aplicação, isto é, se a minha aplicação for chamada pelo start do service manager corre como um serviço, senão corre como aplicação, o que acontece é que se estiver a correr como serviço aparece na árvore de processos com o nome correcto, mas ao iniciar como aplicação deixa correr à mesma porque parece que se esquece de testar a sub-árvore dos serviços e não mostra a mensagem de aplicação já aberta, no entanto em todas as outras situações que experimentei funcionou *****.

Tens aqui um dos link's que me ajudou e de onde tirei a informação. Podes também procurar no google por - single instance + c#

http://www.ai.uga.edu/mc/SingleInstance.html :D

Caso alguém tenha uma resposta para a minha dúvida de maximizar a janela agradecia que xutassem pois estou às voltas há já muito tempo sem resposta nenhuma em concreto.  :rant_01:

Caso precises posso aqui deixar o meu código que está um pouco alterado para a minha aplicação.

A API (GUI) do windows funciona por mensagens....

tens que fazer algo do genero:

public const int WM_SYSCOMMAND = 0x0112;
public const int SC_MAXIMIZE = 0xF030;
[DllImportAttribute ("user32.dll")]
public static extern int SendMessage(IntPtr hWnd, int Msg, intwParam, int lParam);



System.Diagnostics.Process aProcess = System.Diagnostics.Process.GetCurrentProcess();
string aProcName = aProcess.ProcessName;
if (System.Diagnostics.Process.GetProcessesByName(aProcName).Length > 1)				
foreach (System.Diagnostics.Process p in System.Diagnostics.Process.GetProcessesByName(aProcName))				
if (p.Id!=aProcess.Id)										
	SendMessage(p.MainWindowHandle, WM_SYSCOMMAND, SC_MAXIMIZE,0);



}

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Olá inginheiro, a tua solução funcionou bem, mas entretanto já tinha optado por não maximixar a janela, porque fica mal... como não encontrei nada sobre os códigos que tens para subtituir o SC_Maximize (e se souberes onde posso encontrá-los agradecia que partilhasses se puderes), fiz umas pesquisas baseadas no teu código e na página citada por Nazgulled  e já tenho algo que funciona que é os seguinte

     

[DllImport("user32.dll")]
        private static extern bool SetForegroundWindow(IntPtr hWnd);

        [DllImport("user32.dll")]
        private static extern int ShowWindow(IntPtr hWnd, int nCmdShow);

        public const int SW_RESTORE = 9;

        /// <summary>
        /// <para>Dá foco e maximiza todas as janelas correspondentes </para>
        /// <para>a aplicações com o mesmo nome que esta.</para>
        /// </summary>
        /// <param name="p">Processo cuja janena vai ser mostrada.</param>
        public static void MostraInstancia(Process p)
        {            
            ShowWindow(p.MainWindowHandle, SW_RESTORE);
            SetForegroundWindow(p.MainWindowHandle);
        }

Se não estiver bem digam qq coisa.

Obrigado people... até mais tarde.

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Ok, já trabalha como o outro que mostrei atrás e vai servir para outra coisa... Obrigado pela ajuda preciosa  :P.

Logo no primeiro post que escrevi, onde disse que o método que estou a utilizar para identificar se já existia uma instancia já aberta de uma aplicação disse erradamente que

1º Se abrirmos dois programas diferentes com o mesmo nome não vai dar para abrir o segundo e,

2º Este método não pesqusa na árvore dos serviços.

Isto só me aconteceu porque estava a utilizar código parecido com o da página que citei e esse código tem um teste que verifica se a aplicação foi chamada na mesma localização que a anterior

if ((p.Id != corrente.Id) && (p.MainModule.FileName == corrente.MainModule.FileName))

                    return p;

Isto significa que se tivermos a mesma aplicação em duas pastas diferentes, vão abrir as duas sem que uma note a existencia da outra.

Agora estou a utilizar sem o segundo teste e já estou a detectar tudo (o serviço e em qualquer pasta).

Por exemplo, eu crio uma aplicação teste.exe e copio-a para a pasta ambiente de trabalho e para os meus docs. Se correr o teste.exe do ambiente de trabalho e de seguida tentar correr o teste.exe dos meus docs já diz que a aplicação já está a correr.

Atenção, se modificar o nome de teste.exe da pasta os meus docs, já não consigo manter esta coerência e posso abrir duas aplicações iguais (porque têm nomes diferentes). Por este motivo, o mutex funciona melhor para muitas aplicações.

Até...

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Crie uma conta ou ligue-se para comentar

Só membros podem comentar

Criar nova conta

Registe para ter uma conta na nossa comunidade. É fácil!


Registar nova conta

Entra

Já tem conta? Inicie sessão aqui.


Entrar Agora