wenn der Server Crasht
Na, sowas sollte jetzt nicht jeden Tag passieren ![]()
Ansonsten kannst du die Leute ja zwischenspeichern...alle 10-15min...
Und eventuell vermehrt darauf achten, nichts zu skripten, was deinen Server crasht ![]()
wenn der Server Crasht
Na, sowas sollte jetzt nicht jeden Tag passieren ![]()
Ansonsten kannst du die Leute ja zwischenspeichern...alle 10-15min...
Und eventuell vermehrt darauf achten, nichts zu skripten, was deinen Server crasht ![]()
Man kann auch einfach einen freundlichen Stop Befehl in den Server einbauen, der alle User speichert und dann den Server mit einer kurzen Verzögerung über [wiki]SendRconCommand[/wiki] ausschaltet. (dort dann exit oder gmx verwenden)
Nutz doch bspw. Textdraws die du nur ganz kurz anzeigen lässt. Dann Spammst du den Chat damit nicht voll.
Das wäre auch mein Vorschlag gewesen, das Keyword hier lautet "InfoBox samp" ![]()
Hey,
Kann ich abfragen, ob die letzte Nachricht im Chat == einer Nachricht ist?
Habe nichts gefunden im guten Internet
Sowas brauch man auch eigentlich nicht.
Gehe smarter an die Sache ran.
Wenn es um eine Nachricht geht, die ein Spieler geschrieben hat, dann nutze einfach [wiki]OnPlayerText[/wiki].
Ist es eine spezielle Info Nachricht, gesendet vom Server (dann schau, wo diese gesendet wird und dann weißt du ja, dass diese gesendet wurde...) ![]()
Theoretisch kann man SCM und SCMTA hooken und dann immer die letzte Nachricht zwischenspeichern. Dann weiß man, was die letzte Nachricht war.
Aber das muss man ja theoretisch nicht, da es smarter wäre, einfach die Aktion, die man ausführen mag, an die Gegebenheiten im Skript anzupassen.
Kann auch sein, dass deine Festplatte in mehrere Bereiche partitioniert ist.
Einfach mal auf Computerverwaltung > Datenspeicher > Datenträgerverwaltung gehen und schauen, ob da mehrere Partitionen angezeigt werden ![]()
Hmmm, bei dem Befehl stimmt so einiges nicht.
Schau dir eventuell nochmal ein paar Tutorials zu format etc an.
if(sscanf(params, "us", PID, str, rank))
"us" sagt du hast 2 Variablen. Eine die was mit einer spielerid zu tun hat und einen string. Dann gibst du aber 3 an...wozu das mit dem str?
Und wieso rank als String, wenn du es als Integer nutzen magst?
Dann fragst du per switch & case den Rang ab, noch bevor du ihn überhaupt gesetzt hast.
Und im Format unten, hast du wieder unnötig str stehen.
und dann weist du einer Integer Variable...einen String mit dem Inhalt "Moderator" z.B. zu.........
Also, dass dir da keine Errors/Warnings angezeigt werden grenzt schon nahezu an ein Wunder ![]()
Besser wäre sowas (orientiert sich an der 2. Version von dem, was ich oben geschrieben hatte):
CMD:setadmin(playerid,params[])
{
if(PlayerInfo[playerid][pAdmin] < 1)return SendClientMessage(playerid, -1,"Du bist kein Admin. Du kannst den Befehl nicht nutzen!");
new PID, str[128], rank;
if(sscanf(params, "ud", PID, rank))return SendClientMessage(playerid, -1 ,"[Benutze] /setadmin [playerid][rank]");
if(!PlayerInfo[PID][pLoggedIn])return SendClientMessage(playerid, -1, "Spieler ist nicht eingeloggt!");
format(str, sizeof(str), "'%s' wurde zu einem Admin ernannt mit dem Rank: %s",getName(PID),GetAdminRangName(rank));
SendClientMessageToAll(-1, str);
PlayerInfo[PID][pAdmin] = rank;
SaveUserStats(PID);
return 1;
}
Alles anzeigen
Schreibe es mal so:
CMD:admins(playerid, params[])
{
new string[256],rank[22];
for(new i = GetPlayerPoolSize(),name[MAX_PLAYER_NAME+1]; i != -1; i--)
{
if(!IsPlayerConnected(i) || !PlayerInfo[i][pAdmin]) continue;
switch(PlayerInfo[i][pAdmin])
{
case 1: rank = "Moderator";
case 2: rank = "Anfänger Admin";
case 3: rank = "Anwärter Admin";
case 4: rank = "Administrator";
case 5: rank = "Server-Administrator";
}
GetPlayerName(i, name, sizeof(name));
format(string, sizeof(string), "%s{FFFFFF}%s: {1B8AE4}%s (%d)\n", string, rank, name, i);
}
if(!string[0]) return SendClientMessage(playerid, -1, "Keine Admins Online");
ShowPlayerDialog(playerid, DIALOG_ADMINONLINE, DIALOG_STYLE_LIST, "Team Online:", string, "Close", "");
return 1;
}
Alles anzeigen
Oder hier nochmal eine Version, wo die AdminNamen etwas ausgelagert sind:
#define GetAdminRangName(%0) admin_rang_namen[(%0)-1]
stock const admin_rang_namen[][] = {
"Moderator",
"Anfänger Admin",
"Anwärter Admin",
"Administrator",
"Server-Administrator"
};
CMD:admins(playerid, params[])
{
new string[256];
for(new i = GetPlayerPoolSize(),name[MAX_PLAYER_NAME+1]; i != -1; i--)
{
if(!IsPlayerConnected(i) || !PlayerInfo[i][pAdmin]) continue;
GetPlayerName(i, name, sizeof(name));
format(string, sizeof(string), "%s{FFFFFF}%s: {1B8AE4}%s (%d)\n", string, GetAdminRangName(PlayerInfo[i][pAdmin]), name, i);
}
if(!string[0]) return SendClientMessage(playerid, -1, "Keine Admins Online");
ShowPlayerDialog(playerid, DIALOG_ADMINONLINE, DIALOG_STYLE_LIST, "Team Online:", string, "Close", "");
return 1;
}
Alles anzeigen
aber es flackert jetzt bei mir, woran kann es liegen?
Dass du zu oft [wiki]PlayerTextDrawShow[/wiki] aufrufst ![]()
Gut, nur ist es nicht Transparent, also sehe immer noch das schwarze hintergrund
Dann, den Hintergrund transparent machen:
PlayerTextDrawBackgroundColor(playerid, TachoDraw[playerid][8], 0x00000000);
Normalerweise sollte es so zeigen
Es fehlt diese Zeile:
PlayerTextDrawSetPreviewModel(playerid, TachoDraw[playerid][8], 1650);
Ansonsten wird das Objekt-Model nicht gesetzt ![]()
bin iwi total durch und kriege es nicht gebacken diesen komplett simplen Timer zu basteln.
Mach es dir nicht so kompliziert:
Aber wenn ich float klein schreibe, dann wird es mir Blau gefärbt & ich kriege eine Warnung dass ich es falsch verwende.. was steckt dahinter?
In der PAWN Syntax gibt es viele Relikte von Keywords ![]()
Wie private, float, class, auto, struct, ....
Diese kommen von der Sprache C.
Allerdings haben diese Keywords nicht zwingend eine Bedeutung bzw sind in die Sprache implementiert.
Dass diese als Keywords angezeigt werden, hat also keine Bedeutung.
Allerdings ist float in diesem Fall wirklich eine Funktion: https://wiki.sa-mp.com/wiki/Float
Diese verwandelt Integer (also ganze Zahlen) in Floats ![]()
Muss ich das floatdiv nutzen? -> vehTankVerbrauch wird als Float:vehTankVerbrauch definiert.
Und vehFuel ist auch ein Float?
Wenn ja, dann evtl mal so schreiben:
Vehicle[i][vehFuel] -= floatdiv(Vehicle[i][vehTankVerbrauch], 1000.0);
Inwiefern lässt sich das irgendwo noch einsetzen.
Ich meine, könnte ich z.B anstatt if(!strlen(string)) auch if(string[0] == EOS) einsetzen? Und inwiefern macht das dann auch Sinn? Dann könnte ich ja auch if(!string[0]) einsetzen oder nicht?
Wo lässt sich EOS wo verwenden?
Alles korrekt.
Das prüft quasi nur, ob das erste Zeichen im String das NULL Zeichen ist und wenn dem so ist, dann ist der String leer. Das ist einfach nur etwas schneller und performanter, als strlen zu nutzen ![]()
Ein krass ausführliches Tutorial zu Strings gibt es hier: https://forum.sa-mp.com/showthread.php?t=654471
Wie LeonMrBonnie schon korrekt erklärt hat ist das % Zeichen der Modulo Operator: https://de.wikipedia.org/wiki/Division_mit_Rest
Naja, man es kann aber sicherlich einrichten, das sobald einmal auf Weiter geklickt wurde, der Schließen Button als Zurück benutzt werden kann.
Natürlich, ich wollte dich lediglich darauf hinweisen, dass das bei diesem System (deinem Grundsystem) nicht vorhanden war/ist.
Probiere es mal so (nicht getestet):
case PLAYER_QUERY_PPROTOCOL:
{
if(!rows) return SCM(playerid, COLOR_LESSRED, "Es wurde kein Eintrag gefunden.");
new str[1024] = "Datum\tUhrzeit\tInhalt\n",end = GetPVarInt(playerid,"ProtocolEnd"),btnA[32] = "Schließen",btnB[32]="";
for(new i,date[11],time[9],data[128]; i<rows; i++)
{
cache_get_value_name(i, "Datum", date, sizeof(date)),
cache_get_value_name(i, "Uhrzeit", time, sizeof(time)),
cache_get_value_name(i, "Inhalt", data, sizeof(data));
if(data[0] != EOS) format(str, sizeof str, "%s%s\t%s\t%s\n", str, date, time, data);
}
if(end != 0) btnA = "Zurück",SetPVarInt(playerid,"ProtocolBtnA",1);
if(rows%10 == 0) btnB = "Weiter",SetPVarInt(playerid,"ProtocolBtnB",1);
else if(end != 0) btnB = "Schließen",SetPVarInt(playerid,"ProtocolBtnB",2);
ShowPlayerDialog(playerid, D_PP, DIALOG_STYLE_TABLIST_HEADERS, "Spielerprotokoll", str, btnA, btnB);
}
case D_PP:
{
new end = GetPVarInt(playerid,"ProtocolEnd"),btnA = GetPVarInt(playerid,"ProtocolBtnA"),btnB = GetPVarInt(playerid,"ProtocolBtnB");
DeletePVar(playerid,"ProtocolEnd"),DeletePVar(playerid,"ProtocolBtnA"),DeletePVar(playerid,"ProtocolBtnB");
if(response) //Left Button
{
switch(btnA)
{
case 0: DeletePVar(playerid,"ProtocolName"),SCM(playerid,COLOR_GREY,"Fenster geschlossen.");
case 1: ShowPlayerProtocol(playerid,end-10);
}
}
else
{
switch(btnB)
{
case 1: ShowPlayerProtocol(playerid,end+10);
case 2: DeletePVar(playerid,"ProtocolName"),SCM(playerid,COLOR_GREY,"Fenster geschlossen.");
}
}
}
Alles anzeigen
Naja der Tankverbrauch ist ja bei jeden Fahrzeug verscheiden ist schon etwas seltsam wen ich da alles umändern muss.
Musst du doch nicht.
Ich habe dir doch die Formel gegeben:
Vehicle[i][vehFuel] -= floatdiv(Vehicle[i][Verbrauch], 1000);
Egal was der Verbrauch ist (solange du ihn in L auf 100km angibst) wird der so umgerechnet, dass alle 100m das richtige abgezogen wird.
Das Ding ist halt, wenn ich eine oder mehrere Seiten zurück gehe, schließt er und sagt dass nichts mehr sei.
Ich habe keine Ahnung, was du meinst.
Aber dir ist klar, es gibt nur 2 Buttons.
Entweder Schließen oder Weiter. Es gibt kein zurück ![]()
Vehicle[i][vehKMStand] += 0.1;
Das ist Zeile 15, da hat er also 100m zurückgelegt, da kannst du also Ansetzen mit dem Abziehen:
Das ist einfacher Dreisatz:
100km = 13.1L
1km = 0.131L
//Ergo
1000m = 0.131L
100m = 0.0131L (oder eben 13.1ml)
Wir gehen also davon aus, dass Vehicle[i][Verbrauch] = 13.1 ist.
Dann könntest du das in Zeile 16 z.B. einfach so abziehen:
Vehicle[i][vehFuel] -= floatdiv(Vehicle[i][Verbrauch], 1000);
Dann würde er alle 100m 13.1ml verbrauchen.
Wenn das nicht zu frequentiert ist, einfach auf 50 oder 10m gehen.
Einfach mit dem Dreisatz umrechnen ![]()
Dann teste mal aus Spaß if(!response) das tauscht die Funktion der Buttons ![]()