Portal SAMP
[Ajuda] BUG ARMAS DUPLICADAS - Versão de Impressão

+- Portal SAMP (https://portalsamp.com)
+-- Fórum: SA-MP (https://portalsamp.com/forumdisplay.php?fid=5)
+--- Fórum: Área de suporte (https://portalsamp.com/forumdisplay.php?fid=6)
+--- Tópico: [Ajuda] BUG ARMAS DUPLICADAS (/showthread.php?tid=4277)



BUG ARMAS DUPLICADAS - diggao - 06/12/2023

Olá pessoal, na minha gamemode ao morrer o jogador dropa todo o loot inclusive as armas, só que as armas está tendo um problema..

Ao morrer com uma arma com 10 munições por exemplo ela multiplica diversas vezes em vez de ser apenas uma vez '-'
Print: https://i.imgur.com/3uAH49h.png


Código:
        for(new i; i < MAX_LOOTS; i++){

            if(!Loots[i][Existe]){

                for(new x; x < MAX_SLOTS_INV; x++){

                    if(Inventarios[playerid][Item][x] == -1){

                        for(new z; z < 13; z++){

                           
                            GetPlayerWeaponData(playerid, z, A[z], M[z]);

                            if(A[z] != 0){
               


                                switch(A[z]){

                                    case 8: convert_id = 339;
                                    case 9: convert_id = 341;
                                    case 22: convert_id = 346;
                                    case 23: convert_id = 347;
                                    case 25: convert_id = 349;
                                    case 26: convert_id = 350;
                                    case 29: convert_id = 353;
                                    case 31: convert_id = 356;
                                    case 30: convert_id = 355;
                                    case 34: convert_id = 358;
                                    case 35: convert_id = 359;
                                    default: convert_id = -1;
                                }


                                Loots[i][Item][x] = convert_id;
                                Loots[i][Qtd][x] = M[z];

                                printf("loot %i | slot inv %i | slot arma %i | item loot %i | conversao %i", i, x, z, Loots[i][Item][x], convert_id);
                                RemoverArma(playerid, A[z]);
                                break;
                            }
                        }
                        continue;
                    }

                    Loots[i][Item][x] = Inventarios[playerid][Item][x];
                    Loots[i][Qtd][x] = Inventarios[playerid][Qtd][x];

                    Inventarios[playerid][Item][x] = -1;
                    Inventarios[playerid][Qtd][x] = 0;
                }

                Loots[i][Existe] = true;

                Loots[i][Pos][0] = TRT[0];
                Loots[i][Pos][1] = TRT[1];
                Loots[i][Pos][2] = TRT[2];

                Loots[i][ObjectID_L] = CreateDynamicObject(11745, TRT[0], TRT[1], TRT[2]-1, 0.0, 0.0, 0.0);
                Loots[i][Label] = CreateDynamic3DTextLabel(msg, -1, TRT[0], TRT[1], TRT[2]-1, 10);

                SetTimerEx("DestruirLoot", 1000 * 60 * 10, false, "d", i);
                break;
            }
        }



RE: BUG ARMAS DUPLICADAS - pushline - 06/12/2023

Acho que tem algo a ver com o break (dentro do for) / continue (fora do for | dentro do if, nao faz muito sentido existir mas blz)


RE: BUG ARMAS DUPLICADAS - Carlos Victor - 07/12/2023

É possível observar que o seu código é meio confuso, se eu fosse você criaria algumas funções que tornariam o código mais simples e bem melhor para compreensão.

O problema do que você diz, provavelmente é o continue e o break que tem no código, se estiverem posicionados de forma errada, vai afetar completamente o looping.

Você poderia criar uma função para criar loots apenas passando o jogador, item e quantidade, ao invés do looping abaixo.

Você também poderia criar uma função para retornar o modelo da arma, ao invés de usar o switch no looping.

Também, poderia criar uma função que dropasse todos os itens do jogador ao morrer, assim pouparia um código extenso e desnecessário no seu gamemode.

Código PHP:
for(new iMAX_LOOTSi++) {
    if(!
Loots[i][Existe]){

        for(new 
xMAX_SLOTS_INVx++){

            if(
Inventarios[playerid][Item][x] == -1){
                for(new 
z13z++){
                    
GetPlayerWeaponData(playeridzA[z], M[z]);
                    if(
A[z] != 0) {
                        switch(
A[z]){
                            case 
8convert_id 339;
                            case 
9convert_id 341;
                            case 
22convert_id 346;
                            case 
23convert_id 347;
                            case 
25convert_id 349;
                            case 
26convert_id 350;
                            case 
29convert_id 353;
                            case 
31convert_id 356;
                            case 
30convert_id 355;
                            case 
34convert_id 358;
                            case 
35convert_id 359;
                            default: 
convert_id = -1;
                        }


                        
Loots[i][Item][x] = convert_id;
                        
Loots[i][Qtd][x] = M[z];

                        
printf("loot %i | slot inv %i | slot arma %i | item loot %i | conversao %i"ixzLoots[i][Item][x], convert_id);
                        
RemoverArma(playeridA[z]);
                        break;
                    }
                }                
            }

            
Loots[i][Item][x] = Inventarios[playerid][Item][x];
            
Loots[i][Qtd][x] = Inventarios[playerid][Qtd][x];
        }
    }




RE: BUG ARMAS DUPLICADAS - diggao - 07/12/2023

Provavel seja isso msm, se eu retirar o continue igual o Carlos fez não dropa mais nos loots as armas.


RE: BUG ARMAS DUPLICADAS - Carlos Victor - 07/12/2023

Eu fiquei analisando seu sistema e não compreendi a matriz no enumerador Loots, esse sistema de loot seria como se fosse um corpo do jogador caído no chão?

Quando eu digo em relação a otimização de código, eu falo sobre isso:

Percebe que criei algumas funções para me ajudar a manipular os drops no server? Evitando ficar criando loops atoa sem necessidade... O código não sei se é funcional, não testei e fiz aqui agora, mas pega de exemplo, pode usar como base e fazer o seu sistema, só queria deixar um exemplo de como ficaria melhor e menos confuso o código. Você pode criar uma função para retornar o modelo das armas e verificar se o item que está sendo dropado for arma, e se sim remove a arma do jogador, tem uma função chamada RemovePlayerWeaponID no tópico de códigos úteis, eu que mandei lá, pega esse código e usa ao seu favor. Qualquer dúvida só enviar aqui.

Código PHP:
#define MAX_DROPS (1000)

#define PRESSED(%0) \
    
(((newkeys & (%0)) == (%0)) && ((oldkeys & (%0)) != (%0)))

enum droppedData
{
    
bool:droppedExists,

    
droppedModel,
    
droppedAmount,

    
Float:droppedPos[3],
    
droppedInterior,
    
droppedVirtualWorld,

    
droppedObject,
    
Text3D:droppedText
};
new 
DroppedItems[MAX_DROPS][droppedData];

Drop_Item(playeriditemidamount)
{
    new 
        
id Drop_FreeID();

    if(
id == -1)
        return 
SendClientMessage(playerid, -1"* O limite de itens dropados foi atingido.");

    
DroppedItems[id][droppedExists] = true;
    
DroppedItems[id][droppedModel] = itemid;
    
DroppedItems[id][droppedAmount] = amount;

    
GetPlayerPos(playeridDroppedItems[id][droppedPos][0], DroppedItems[id][droppedPos][1], DroppedItems[id][droppedPos][2]);
    
DroppedItems[id][droppedInterior] = GetPlayerInterior(playerid);
    
DroppedItems[id][droppedVirtualWorld] = GetPlayerVirtualWorld(playerid);

    
Drop_Refresh(id);    
    return 
id;
}

Drop_Refresh(id)
{
    if((
id || id MAX_DROPS) || !DroppedItems[id][droppedExists])
        return 
0;

    if(
IsValidDynamicObject(DroppedItems[id][droppedObject]))
        
DestroyDynamicObject(DroppedItems[id][droppedObject]);

    if(
IsValidDynamic3DTextLabel(DroppedItems[id][droppedText]))
        
DestroyDynamic3DTextLabel(DroppedItems[id][droppedText]);

    
DroppedItems[id][droppedObject] = CreateDynamicObject(DroppedItems[id][droppedModel], DroppedItems[id][droppedPos][0], DroppedItems[id][droppedPos][1], DroppedItems[id][droppedPos][2], 0.00.00.0DroppedItems[id][droppedVirtualWorld], DroppedItems[id][droppedInterior]);
    
DroppedItems[id][droppedText] = CreateDynamic3DTextLabel("(( Pressione 'F' para coletar o item. ))"0xFFFFFFFFDroppedItems[id][droppedPos][0], DroppedItems[id][droppedPos][1], DroppedItems[id][droppedPos][2], 5.0);
    return 
1;
}

Drop_FreeID()
{
    for(new 
iMAX_DROPSi++) {
        if(!
DroppedItems[i][droppedExists])
            return 
i;
    }
    return -
1;
}

Drop_Nearest(playerid)
{
    for(new 
iMAX_DROPSi++) if(DroppedItems[i][droppedExists])
    {
        if(
IsPlayerInRangeOfPoint(playerid2.5DroppedItems[i][droppedPos][0], DroppedItems[i][droppedPos][1], DroppedItems[i][droppedPos][2]) && GetPlayerVirtualWorld(playerid) == DroppedItems[i][droppedVirtualWorld] && GetPlayerInterior(playerid) == DroppedItems[i][droppedInterior])
            return 
i;
    }
    return -
1;
}

public 
OnPlayerKeyStateChange(playeridnewkeysoldkeys)
{
    static
        
id;

    if(
PRESSED(KEY_SECONDARY_ATTACK))
    {
        if((
id Drop_Nearest(playerid)) != -1)
        {
            
// Coletar o item com o índice 'id'.
        
}
    }
    return 
1;




RE: BUG ARMAS DUPLICADAS - diggao - 07/12/2023

entendi, obrigado!