Atualizar criar-plugin.md

This commit is contained in:
tony committed 2026-09-25 10:54:12 -03:00
1 parent fa85b6ee0c
commit cb3731232b
1 file changed
+19 -19
+19 -19
View File
@@ -11,7 +11,7 @@ O repositório contém projetos Java **independentes**:
| Projeto | O que é | | Projeto | O que é |
|---|---| |---|---|
| `pitiupi` | A ferramenta principal — P2P, janela, rede, e o "motor" que carrega plugins | | `pitiupi` | A ferramenta principal : P2P, janela, rede, e o "motor" que carrega plugins |
| `pitiupi.chat` | Um plugin que adiciona um chat | | `pitiupi.chat` | Um plugin que adiciona um chat |
| `pitiupi.screenCast` | Outro plugin que adiciona compartilhamento de tela | | `pitiupi.screenCast` | Outro plugin que adiciona compartilhamento de tela |
@@ -22,9 +22,9 @@ Quando o pitiupi principal inicia, ele varre essa pasta e **carrega dinamicament
Isso é possível graças a três partes que trabalham juntas: Isso é possível graças a três partes que trabalham juntas:
1. A **interface `Plugin`** — o contrato que todo plugin deve cumprir. 1. A **interface `Plugin`** : o contrato que todo plugin deve cumprir.
2. O **`PluginLoader`** — a classe do pitiupi que varre a pasta `plugins/` e carrega os `.jar`. 2. O **`PluginLoader`** : a classe do pitiupi que varre a pasta `plugins/` e carrega os `.jar`.
3. O **arquivo de registro do `ServiceLoader`** — um arquivo de texto dentro do `.jar` que diz "esta classe aqui implementa `Plugin`". 3. O **arquivo de registro do `ServiceLoader`** : um arquivo de texto dentro do `.jar` que diz "esta classe aqui implementa `Plugin`".
--- ---
@@ -45,10 +45,10 @@ public interface Plugin {
O que cada método faz: O que cada método faz:
- **`getName()` / `getAuthor()` / `getVersion()`** — indentificação de dados básicos. - **`getName()` / `getAuthor()` / `getVersion()`** : indentificação de dados básicos.
- **`createPlugin(MainWindow window)`** — É aqui que o plugin cria sua interface gráfica, adiciona itens de menu na janela principal, etc. - **`createPlugin(MainWindow window)`** : É aqui que o plugin cria sua interface gráfica, adiciona itens de menu na janela principal, etc.
- **`getMessage()`** — Serve como modelo para a camada de rede saber que tipo de mensagem esse plugin envia. - **`getMessage()`** : Serve como modelo para a camada de rede saber que tipo de mensagem esse plugin envia.
- **`receiveMessage(byte[] message)`** — recebe as mensagens que chegam pela rede e permite que o plugin interprete esses dados. - **`receiveMessage(byte[] message)`** : recebe as mensagens que chegam pela rede e permite que o plugin interprete esses dados.
--- ---
@@ -57,7 +57,7 @@ O que cada método faz:
A classe `PluginLoader` (`pitiupi/src/pitiupi/control/PluginLoader.java`) faz o seguinte: A classe `PluginLoader` (`pitiupi/src/pitiupi/control/PluginLoader.java`) faz o seguinte:
1. Olha dentro da pasta `plugins/` e lista todos os arquivos `.jar`. 1. Olha dentro da pasta `plugins/` e lista todos os arquivos `.jar`.
2. Cria um `URLClassLoader` — um "carregador de classes" isolado, que sabe ler código de dentro desses `.jar`. 2. Cria um `URLClassLoader` : um "carregador de classes" isolado, que sabe ler código de dentro desses `.jar`.
3. Usa `ServiceLoader.load(Plugin.class, pluginClassLoader)` para perguntar: *"dentre essas classes, quais implementam `Plugin`?"* 3. Usa `ServiceLoader.load(Plugin.class, pluginClassLoader)` para perguntar: *"dentre essas classes, quais implementam `Plugin`?"*
4. Para cada plugin encontrado, chama `createPlugin(mainWindow)` e guarda o plugin numa lista. 4. Para cada plugin encontrado, chama `createPlugin(mainWindow)` e guarda o plugin numa lista.
```java ```java
@@ -69,7 +69,7 @@ for (Plugin plugin : serviceLoader) {
} }
``` ```
**Obs:** o `ServiceLoader` do Java **não escaneia o bytecode procurando quem implementa a interface**. Ele lê um arquivo de texto simples dentro do `.jar`. Se esse arquivo não existir ou estiver errado, o plugin é ignorado — mesmo que o código esteja perfeito. **Obs:** o `ServiceLoader` do Java **não escaneia o bytecode procurando quem implementa a interface**. Ele lê um arquivo de texto simples dentro do `.jar`. Se esse arquivo não existir ou estiver errado, o plugin é ignorado : mesmo que o código esteja perfeito.
--- ---
@@ -89,7 +89,7 @@ Repare em duas coisas:
``` ```
pitiupi.chat.plugin.ChatPlugin pitiupi.chat.plugin.ChatPlugin
``` ```
----
- O`Plugin` diz **"eu sei fazer o trabalho"**. - O`Plugin` diz **"eu sei fazer o trabalho"**.
- O arquivo em `META-INF/services` diz **"aqui está quem sabe fazer o trabalho"**. - O arquivo em `META-INF/services` diz **"aqui está quem sabe fazer o trabalho"**.
- Sem o segundo, o pitiupi nunca fica sabendo que a classe existe. - Sem o segundo, o pitiupi nunca fica sabendo que a classe existe.
@@ -97,7 +97,7 @@ pitiupi.chat.plugin.ChatPlugin
## 5. Exemplo real: o `ChatPlugin` ## 5. Exemplo real: o `ChatPlugin`
Veja como o plugin de chat implementa o contrato — use isso como referência ao escrever o seu: Veja como o plugin de chat implementa o contrato : use isso como referência ao escrever o seu:
```java ```java
public class ChatPlugin implements Plugin { public class ChatPlugin implements Plugin {
@@ -148,7 +148,7 @@ Em `createPlugin` é onde o bum de "aparecer na tela" acontece: ele cria a janel
Vamos chamar o plugin de exemplo de `SeuPlugin`. Vamos chamar o plugin de exemplo de `SeuPlugin`.
### Passo 1 — Criar a estrutura do projeto ### Passo 1 : Criar a estrutura do projeto
Se você quiser um jeito mais facil sem se aprofundar, você pode criar o projeto de duas formas: Se você quiser um jeito mais facil sem se aprofundar, você pode criar o projeto de duas formas:
@@ -165,7 +165,7 @@ pitiupi.seuplugin/
└── pitiupi/seuplugin/plugin/ └── pitiupi/seuplugin/plugin/
``` ```
### Passo 2 — Adicionar o `pitiupi.jar` como dependência ### Passo 2 : Adicionar o `pitiupi.jar` como dependência
O plugin precisa do arquivo **`pitiupi/dist/pitiupi.jar`** para acessar `Plugin` e `MainWindow`. O plugin precisa do arquivo **`pitiupi/dist/pitiupi.jar`** para acessar `Plugin` e `MainWindow`.
@@ -174,7 +174,7 @@ O plugin precisa do arquivo **`pitiupi/dist/pitiupi.jar`** para acessar `Plugin`
- **Se criou pelo NetBeans:** **Properties → Libraries → Add JAR/Folder** → selecione `pitiupi/dist/pitiupi.jar`. - **Se criou pelo NetBeans:** **Properties → Libraries → Add JAR/Folder** → selecione `pitiupi/dist/pitiupi.jar`.
### Passo 3 — Implementar a interface `Plugin` ### Passo 3 : Implementar a interface `Plugin`
Crie `src/pitiupi/seuplugin/plugin/SeuPlugin.java`: Crie `src/pitiupi/seuplugin/plugin/SeuPlugin.java`:
@@ -212,7 +212,7 @@ public class SeuPlugin implements Plugin {
} }
``` ```
### Passo 4 — Registrar o plugin no `ServiceLoader` ### Passo 4 : Registrar o plugin no `ServiceLoader`
Crie o arquivo (sem extensão): Crie o arquivo (sem extensão):
@@ -227,7 +227,7 @@ pitiupi.seuplugin.plugin.MeuPlugin
``` ```
### Passo 5 — Compilar com Ant ### Passo 5 : Compilar com Ant
```bash ```bash
cd pitiupi.seuplugin cd pitiupi.seuplugin
@@ -236,7 +236,7 @@ ant jar
Isso gera o `.jar` em `pitiupi.seuplugin/dist/`. Isso gera o `.jar` em `pitiupi.seuplugin/dist/`.
### Passo 6 — Linkar o `.jar` na pasta de plugins ### Passo 6 : Linkar o `.jar` na pasta de plugins
```bash ```bash
cd pitiupi/plugins cd pitiupi/plugins
@@ -255,4 +255,4 @@ META-INF/services/pitiupi.plugin.Plugin → "aqui está quem faz o trabalho" (
PluginLoader.java → "eu procuro registros e chamo quem se registrou" (o carregador, já pronto no pitiupi) PluginLoader.java → "eu procuro registros e chamo quem se registrou" (o carregador, já pronto no pitiupi)
``` ```
Entendendo essas quatro peças, criar qualquer plugin novo — chat, screencast, ou algo totalmente diferente (arquivos, jogos, sensores) — é sempre o mesmo padrão: implementar a interface, registrar no `META-INF/services`, compilar e linkar. Entendendo essas quatro peças, criar qualquer plugin novo : chat, screencast, ou algo totalmente diferente (arquivos, jogos, sensores) : é sempre o mesmo padrão: implementar a interface, registrar no `META-INF/services`, compilar e linkar.