Portal SAMP
[Tutorial] Implementando um Sistema de Missões Dinâmicas - Versão de Impressão

+- Portal SAMP (https://portalsamp.com)
+-- Fórum: SA-MP (https://portalsamp.com/forumdisplay.php?fid=5)
+--- Fórum: Guias e Tutoriais (https://portalsamp.com/forumdisplay.php?fid=7)
+--- Tópico: [Tutorial] Implementando um Sistema de Missões Dinâmicas (/showthread.php?tid=4455)



Implementando um Sistema de Missões Dinâmicas - strelo - 24/01/2024

Descrição Geral:
Vamos desenvolver um sistema de missões dinâmicas onde os jogadores podem aceitar missões variadas, completá-las e receber recompensas. As missões serão geradas aleatoriamente e terão diferentes objetivos, como entregar itens, competir em corridas, ou combater NPCs.



Passo 1: Configurando a Estrutura Básica do mission_system.pwn

Primeiro, criaremos a estrutura básica do arquivo mission_system.pwn. Este arquivo será o núcleo do nosso sistema de missões, onde inicializaremos e gerenciaremos as diferentes missões.

Código PHP:
// mission_system.pwn
#include <a_samp>

// Constantes e variáveis globais
#define MAX_MISSIONS 10
new MissionData[MAX_MISSIONS][3]; // Array para armazenar dados das missões
new bool:IsMissionActive[MAX_MISSIONS] = {false, ...};

// Protótipos de funções
forward InitializeMissions();
forward ActivateMission(playeridmissionid);
forward CompleteMission(playeridmissionid);

public 
OnGameModeInit() {
    InitializeMissions();
    return 1;
}

public 
OnPlayerConnect(playerid) {
    // Código para inicializar dados do jogador
    return 1;
}

// Função para inicializar missões
InitializeMissions() {
    // Inicialização das missões
}

// Função para ativar uma missão
ActivateMission(playeridmissionid) {
    // Código para ativar a missão para o jogador
}

// Função para completar uma missão
CompleteMission(playeridmissionid) {
    // Código para marcar a missão como completada



Esse é apenas o começo da estrutura do script. Aqui, definimos algumas constantes, variáveis globais para gerenciar as missões, e protótipos de funções importantes como InitializeMissions, ActivateMission e CompleteMission.

No próximo passo, detalharemos a lógica de inicialização e gerenciamento das missões.




Passo 2: Implementando a Função de Inicialização das Missões

Agora, vamos detalhar a função InitializeMissions, que será responsável por configurar as missões iniciais no jogo. Vamos supor que cada missão tenha um tipo (por exemplo, entrega, corrida, combate), uma descrição e um status de ativação.

Código PHP:
// Função para inicializar missões
InitializeMissions() {
    // Exemplo de inicialização de missões
    // MissionData[missionid][0] = tipo da missão
    // MissionData[missionid][1] = descrição da missão
    // MissionData[missionid][2] = recompensa da missão

    // Missão 1: Entrega
    MissionData[0][0] = 1// Tipo 1 para entrega
    MissionData[0][1] = "Entregue pacotes em Los Santos"// Descrição
    MissionData[0][2] = 1000// Recompensa

    // Missão 2: Corrida
    MissionData[1][0] = 2// Tipo 2 para corrida
    MissionData[1][1] = "Vença a corrida em San Fierro"// Descrição
    MissionData[1][2] = 1500// Recompensa

    // Adicione mais missões conforme necessário
    // ...


Essa função define os tipos, descrições e recompensas de várias missões. Estamos utilizando um array multidimensional MissionData para armazenar essas informações. Claro, isso é apenas um exemplo; você pode expandir e personalizar conforme a necessidade do seu servidor.



Passo 3: Implementando as Funções para Ativar e Completar Missões

Agora, vamos desenvolver as funções ActivateMission e CompleteMission. A função ActivateMission será usada para ativar uma missão para um jogador específico, e CompleteMission para marcar uma missão como completada.

Código PHP:
// Função para ativar uma missão
ActivateMission(playeridmissionid) {
    if(missionid || missionid >= MAX_MISSIONS) {
        SendClientMessage(playerid, -1"Missão inválida.");
        return 0;
    }

    if(IsMissionActive[missionid]) {
        SendClientMessage(playerid, -1"Esta missão já está ativa.");
        return 0;
    }

    // Marcar a missão como ativa
    IsMissionActive[missionid] = true;
    // Código para iniciar a missão (ex: criar waypoints, NPCs, etc.)
    // ...

    SendClientMessage(playerid, -1"Missão ativada!");
    return 1;
}

// Função para completar uma missão
CompleteMission(playeridmissionid) {
    if(missionid || missionid >= MAX_MISSIONS || !IsMissionActive[missionid]) {
        SendClientMessage(playerid, -1"Missão inválida ou não ativa.");
        return 0;
    }

    // Marcar a missão como completada
    IsMissionActive[missionid] = false;
    // Código para finalizar a missão (ex: dar recompensa, limpar objetos, etc.)
    // ...

    SendClientMessage(playerid, -1"Missão completada!");
    return 1;


Essas funções gerenciam o estado das missões para os jogadores. ActivateMission verifica se a missão é válida e se não está ativa antes de ativá-la. CompleteMission também verifica a validade e o estado da missão antes de marcá-la como completada e executar a lógica de conclusão.


Passo 4: Adicionando Lógica Específica para Diferentes Tipos de Missões

Agora, vamos expandir a funcionalidade do nosso sistema adicionando lógica específica para diferentes tipos de missões. Vamos usar a função ActivateMission como exemplo para implementar a lógica de uma missão de entrega.

Código PHP:
// Função para ativar uma missão
ActivateMission(playeridmissionid) {
    // ... código anterior ...

    switch(MissionData[missionid][0]) {
        case 1// Missão de entrega
            // Código para configurar a missão de entrega
            // Exemplo: criar um veículo de entrega, definir localização de entrega, etc.
            CreateDeliveryMission(playeridmissionid);
            break;
        case 2// Missão de corrida
            // Código para configurar a missão de corrida
            // Exemplo: definir ponto de partida e chegada, criar checkpoints, etc.
            CreateRaceMission(playeridmissionid);
            break;
        // Adicionar mais tipos de missão conforme necessário
    }

    // ... restante do código ...
}

// Função para criar uma missão de entrega
CreateDeliveryMission(playeridmissionid) {
    // Implementar a lógica de criação da missão de entrega
    // Exemplo: definir local de coleta e entrega, criar itens para entregar, etc.
    // ...
}

// Função para criar uma missão de corrida
CreateRaceMission(playeridmissionid) {
    // Implementar a lógica de criação da missão de corrida
    // Exemplo: definir percurso da corrida, criar veículo, etc.
    // ...


Neste passo, usamos a estrutura switch para tratar diferentes tipos de missões. Cada caso no switch corresponde a um tipo de missão, e cada um desses casos chama uma função específica que configura a missão. Isso permite uma expansão fácil e organizada do sistema de missões.


Passo 5: Adicionando Interações com Jogadores

Vamos implementar a interação com os jogadores para que eles possam aceitar e acompanhar o progresso das missões. Para isso, adicionaremos comandos e funções relacionadas à interação do jogador com o sistema de missões.

Código PHP:
// Comando para listar missões disponíveis
CMD:missões(playeridparams[]) {
    new string[128];
    format(stringsizeof(string), "Missões disponíveis:\n");
    for(new 0MAX_MISSIONSi++) {
        if(!IsMissionActive[i]) {
            strcat(stringMissionData[i][1]); // Adiciona descrição da missão
            strcat(string"\n");
        }
    }
    SendClientMessage(playerid, -1string);
    return 1;
}

// Comando para aceitar uma missão
CMD:aceitarmissao(playeridparams[]) {
    new missionid;
    if(sscanf(params"d", &missionid) || missionid || missionid >= MAX_MISSIONS) {
        SendClientMessage(playerid, -1"ID de missão inválido.");
        return 0;
    }

    ActivateMission(playeridmissionid);
    return 1;
}

// Comando para verificar o progresso da missão
CMD:progressomissao(playeridparams[]) {
    new missionid;
    if(sscanf(params"d", &missionid) || missionid || missionid >= MAX_MISSIONS) {
        SendClientMessage(playerid, -1"ID de missão inválido.");
        return 0;
    }

    // Código para mostrar o progresso da missão
    // Exemplo: "Missão 1: Entrega - Progresso: 50%"
    // ...

    return 1;


Esses comandos permitem que os jogadores vejam as missões disponíveis, aceitem uma missão e verifiquem o progresso de uma missão ativa. Isso cria uma interação direta entre o jogador e o sistema de missões, aumentando a imersão e a jogabilidade.


Passo 6: Implementando a Lógica de Progresso e Conclusão das Missões

Agora, vamos adicionar a lógica para o progresso e a conclusão das missões. Isso inclui atualizar o status da missão para o jogador e conceder recompensas após a conclusão.

Código PHP:
// Suponha que temos uma variável global ou um array para rastrear o progresso da missão
// Exemplo: new MissionProgress[MAX_PLAYERS][MAX_MISSIONS];

// Função para atualizar o progresso da missão
UpdateMissionProgress(playeridmissionidprogress) {
    if(missionid || missionid >= MAX_MISSIONS) {
        return 0;
    }

    MissionProgress[playerid][missionid] = progress;

    // Código para informar ao jogador sobre o progresso atualizado
    // Exemplo: "Missão 1: Entrega - Progresso: 80%"
    // ...
}

// Completar a missão e conceder recompensa
CompleteMission(playeridmissionid) {
    // ... código anterior ...

    // Conceder recompensa ao jogador
    new reward MissionData[missionid][2];
    GivePlayerMoney(playeridreward);
    SendClientMessage(playerid, -1"Missão completada! Recompensa recebida.");

    // Resetar o progresso da missão para o jogador
    MissionProgress[playerid][missionid] = 0;

    return 1;


Neste passo, implementamos funções para atualizar o progresso das missões e para completá-las, incluindo a lógica de recompensa. A função UpdateMissionProgress atualiza o progresso da missão para um jogador específico, enquanto CompleteMission agora também concede a recompensa ao jogador.


Passo 7: Revisão e Teste do Sistema de Missões

Para finalizar, vamos revisar e testar nosso sistema de missões para garantir que tudo está funcionando corretamente. Aqui estão algumas etapas para testar e validar o sistema:



1. Testar Comandos Individuais:

  • Verificar se o comando /missões lista as missões disponíveis corretamente.
  • Testar o comando /aceitarmissao para diferentes missões e garantir que elas são ativadas.
  • Usar o comando /progressomissao para verificar o progresso das missões ativas.

2. Simular Cenários de Missão:
  • Simular a execução de diferentes tipos de missões (entrega, corrida, etc.) e verificar se o progresso e a conclusão estão funcionando como esperado.
  • Testar a lógica de recompensa ao completar missões.

3. Verificar Robustez do Sistema:
  • Testar situações de erro, como tentar ativar uma missão já ativa ou completar uma missão não iniciada.
  • Verificar o comportamento do sistema com múltiplos jogadores.
4. Revisão do Código:
  • Revisar o código para garantir que não há erros de lógica ou de sintaxe.
  • Otimizar o código, se necessário, para melhorar a performance.
5. Feedback dos Jogadores:

Após implementar o sistema no servidor, coletar feedback dos jogadores para futuras melhorias.

Você agora tem um sistema de missões dinâmicas, que inclui:
  • Estrutura básica do sistema de missões.
  • Funções para inicializar, ativar e completar missões.
  • Lógica específica para diferentes tipos de missões.
  • Comandos para interação do jogador com o sistema de missões.
  • Estratégias para revisão e teste do sistema.



RE: Implementando um Sistema de Missões Dinâmicas - xbruno1000x - 26/01/2024

Muito bom o seu tutorial! +Rep


RE: Implementando um Sistema de Missões Dinâmicas - NelsonC. - 26/01/2024

Muito bacana!