Beiträge von IPrototypeI


    Sizeof ist ein Opperator und kein Macro, also macht es daraus keinen Konstanten Wert und ist somit nicht zwingend schneller als eine Variable ;)


    BlackAce der Satz gebe ich zu ist etwas undeutlich ich meinte nicht das die verwendung von sizeof() schneller ist sondern die eines konstanten Wertes.
    Also bezieht sich der nachfolgende Satz darauf das die verwendung von sizeof langsamer ist als ein konstanter Wert, auch wenn der Unterschied in die tausendstel geht. :D
    "Das macht man weil konstante werte schneller sind als erstmal die Größe über einen Operator zu ermitteln."

    Was bring 3DZone Und wie kann ich es machen, dass ich einfach jedes abfragen kann ohne die länge anzugeben (was ich rigendiwe nicht ganz checke?!)


    L.G.
    heyho :)


    Was ist der Unterschied zwischen einem Rechteck und einem Quader(2D vs 3D) ?
    ( noch ein kleiner tipp a*b(Flächeninhalt) und a*b*c(Volumen)).


    Die länge wird für format genutzt
    format(zone, len, SanAndreasZones[i][Zone_Name], 0);


    kannst du auch natürlich entfernen als argument und hier len durch sizeof(zone) ersetzen.
    Das macht man weil konstante werte schneller sind als erstmal die Größe über eine funktion abzurufen.

    if (!strcmp("/wobinich", cmdtext)){
    new ZName[28];
    if(!GetPlayer2DZone(playerid,ZName,28))return SendClientMessage(playerid,-1,"Du bist in keiner bekannten Zone!");
    SendClientMessage(playerid,-1,ZName);
    return 1;
    }


    Der Name der Zone wird zurück gegeben an den string der für das argument zone[] eingesetzt wurde da dieser formatiert wird. sollte nix gefunden werden gibt die funktion 0 zurück, sollte ein eintrag gefunden werden so ist der rückgabewert 1.

    Zum ersten hast du das hier schonmal gefragt
    Kennzeichen Hilfe


    enum MainZone {
    Zone_Name[28],
    Float:Zone_Area[6]
    };


    Die 3 Koordinate ist die höhe damit kannst du einen würfel um die Zone erstellen


    stock GetPlayer3DZone(playerid, zone[], len) {
    new Float:x, Float:y, Float:z;
    GetPlayerPos(playerid, x, y, z);
    for(new i = 0; i != sizeof(SanAndreasZones); i++ ){
    if(x >= SanAndreasZones[i][Zone_Area][0] && x <= SanAndreasZones[i][Zone_Area][3] && y >= SanAndreasZones[i][Zone_Area][1] && y <= SanAndreasZones[i][Zone_Area][4] && z >= SanAndreasZones[i][Zone_Area][2] && z <= SanAndreasZones[i][Zone_Area][5]){return format(zone, len, SanAndreasZones[i][Zone_Name], 0); }
    }
    return false;
    }
    stock GetPlayer2DZone(playerid, zone[], len) {
    new Float:x, Float:y, Float:z;
    GetPlayerPos(playerid, x, y, z);
    for(new i = 0; i != sizeof(SanAndreasZones); i++ ){
    if(x >= SanAndreasZones[i][Zone_Area][0] && x <= SanAndreasZones[i][Zone_Area][3] && y >= SanAndreasZones[i][Zone_Area][1] && y <= SanAndreasZones[i][Zone_Area][4]){
    return format(zone, len, SanAndreasZones[i][Zone_Name], 0);}
    }
    return false;
    }


    Was google so alles bewirkt.


    //edit


    Das ganz ist letztendlich je nach Verwendungszweck mit dem streamer plugin zu kombinieren und darüber die Zonen zu erstellen da es dafür sogar ein callback gibt welches aufgerufen wird wenn du die zone betritst.

    Das ganze funktioniert nur, wenn du zuerst nur diese autos erstellen lässt, da die ID Vergabe bei den Autos nach einem Slotsystem geht.
    Du kannst auch auf eine nummer sicher gehen und die Fahrzeugid auch noch speichern.



    ahja
    Veh_Frak[i] = vInfo[i][v_Frak];
    Veh_Job[i] = vInfo[i][v_Job];
    brauchst du nichtmal das hast du schon alles in deinem array vInfo enthalten

    static bedeutet das du es nur dort verwenden kannst wo du es implementiert hast also zum beispiel nur in einer include.
    const bedeutet das es ein konstanter wert ist er lässt sich nicht ändern.(damit kann man auch den beanspruchten memoryverbrauch einer funktion reduzieren)


    was man auch machen könnte wäre wenn man lüstig wäre.


    stock static const SanAndreasZones[][MainZone]



    nun zur der zweiten zeile


    {"The Big Ear", {-410.00,1403.30,-3.00,-137.90,1681.20,200.00}},


    en dem enum befindet sich ein array mit 6 Elementen wo für jede Zelle ein wert initalisiert wird.


    also ist das damit gleichzusetzen


    new array[6] = {-410.00,1403.30,-3.00,-137.90,1681.20,200.00};


    //edit
    Um ein klares Anwendungsbeispiel zu machen solltest du das enum MainZone posten.

    Daher brauchst du noch eine zusätzliche Abfrage frag die virtuelle Welt noch ab zusätzlich zu den koordinaten beim rausgehen.
    else if(IsPlayerInRangeOfPoint(playerid, 5.0, 362.9045,-75.2025,1001.5078) && GetPlayerVirtualWorld(playerid) == 100){
    ...
    }

    Das Level, wird in meiner Datenbank als INT abgespeichert, weshalb es doch nicht als string ausgegeben werden dürfte.
    Oder meinen sie, dass ich die Variable als INT speichern soll?


    Gruß - Kazuto


    PS: Meine Scripting Erfahrung ist noch nicht so hoch, deshalb bitte ich hier um Entschuldigung.


    Du kannst auch integer als varchar abspeichern das ist egal mit dem zuweißen von dem richtigen Datentyp in MySQL tust du dir selbst nur einen gefallen da die Verarbeitung dadurch schneller ist und weniger memory in anspruch genommen wird beim speichern auf dem MySQL-Server.


    Sobald du etwas ausließt wird das immer als string zurück gegeben nur die Funktionen

    native cache_get_field_content_int(row, const field_name[], connectionHandle = 1);
    native Float:cache_get_field_content_float(row, const field_name[], connectionHandle = 1);


    erleichtern dir das konvertieren da die funktion das ganze nach dem auslesen umwandelt und zurück gibt.


    native cache_get_field_content(row, const field_name[], destination[], connectionHandle = 1, max_len=sizeof(destination));


    Bei 2 Dimensionalen Arrays ist es hier sinvoll die länge anzugeben sonst wird das auslesen zu einem Problem.

    Ich möchte speziell das, dass Lotto um 20 Uhr beginnt


    Was natürlich auch möglich ist das du die Zeit zu dem Punkt hin berechnest ist natürlich auch möglich ^^ oder du verknüpfst das mit deinem Uhrzeitsystem
    falls du eins hast.


    Zum Berechnen würde das so gehen.


    new Times[3];
    gettime(Times[0], Times[1], Times[2]);
    Die Berechnung:
    ((Times[0] < timemin)?(((timemin-(Times[0]+1))*60*60*1000) +((60-(Times[1]+1))*60*1000)+((60-Times[2])*1000)):(((24-(Times[0]+1))*60*60*1000) +((60-(Times[1]+1))*60*1000)+((60-Times[2])*1000)+(timemin*60*60*1000)))


    Aber das würde ich davor mal testen mit eine timerfix include.
    http://forum.sa-mp.com/showthread.php?t=289675
    oder das Plugin was noch besser sein soll
    http://forum.sa-mp.com/showthread.php?t=375925


    Es kommt immer noch nicht wirklich zum Vorschein was du genau möchtest.
    Wenn du nur abprüfen willst das ein spieler eine aktion ausführen kann erst zu einer bestimmten zeit dann Arbeitest du am besten mit gettime.


    new Hour;
    gettime(Hour);
    if(Hour >= 20){


    }


    die weiteren parameter musst du nicht zwingend angeben da diese optional sind.


    Wenn du nun die Uhrzeit anzeigen möchtest als Textdraw.
    Dan kommst du um den Timer nicht herum. Hier musst du selbst entscheiden wie du das angeben willst ob mit stunde,minuten und sekunden(interval für den Timer 1000(1sekunde))
    oder nur die Stunden und die minuten(interval für den Timer 60000( 60 Sekunden)) oder nur die Stunden(Interval 3600000( 3600 Sekunden)) musst du entscheiden nur solltest du dazu noch eine Timerfix include verwenden weil die Timer nicht akkurat laufen also es kommt zu größeren Zeitabständen je nach Intervall.

    Mal abgesehen davon sowas kann man auch alles über MySQL regeln find ich persönlich am praktischen aber nun gut das ist eine subjektive Meinungsbild.


    format(query,sizeof(query),"UPDATE `user` SET `Timeban` = DATE_ADD(NOW(),INTERVAL %d MINUTE) WHERE `username` = '%s';",dauer,bannername);


    Zu dem kann man das auch formatiert auslesen

    DATE_FORMAT(`Timeban`, 'Am %%d.%%m.%%Y um %%T Uhr') AS `LoadTimeban`

    Mit der Funktion GetPlayerSurfingVehicleID(playerid);
    kannst du überprüfen ob der Spieler auf einem Fahrzeug surft
    http://wiki.sa-mp.com/wiki/GetPlayerSurfingVehicleID


    Du kannst das entweder in einen bestehenden Timerpacken oder in OnPlayerUpdate und daher immer abprüfen ob der spieler auf einem auto ist.
    Als Info die Funktion gibt die Fahrzeugid zurück daher kannst du noch abprüfen ob sich das Fahrzeug bewegt


    new Float:Speed[3];
    GetVehicleVelocity(GetPlayerSurfingVehicleID(playerid),Speed[0],Speed[1],Speed[2]);
    if((Speed[0]+Speed[1]+Speed[2]) != 0.0){
    ....
    }

    Danke und wie überprüfe ich das? Also ich weiß auch nicht wie man das macht, habe so etwas noch nie ausprobiert also Kommas überprüfen etc. hoffe, dass du mir helfen kannst oder auch andere User auf diesem Forum



    Die Funktion kannst du in einer if-Abfrage verwenden.
    Beispiel:
    if(!ReturnInputDate(string))return SendClientMessage(playerid,-1,"Deine Eingabe entspricht nicht dem Format: 00.00.0000!");


    Wie du siehst gibt es hier ein Argument mit dem namen inputtext[] welches ein 1dimensionales Array ist
    stock ReturnInputDate(inputtext[])


    bedeutet das du für das Argument einen string einsetzt. ( string = 1 Dimensionales Array)
    Beispiel für ein string.


    new text[10];


    Was passiert in der Funktion ?
    es wird als erstes überprüft ob der string leer ist
    if(!inputtext[0])return 0;
    sollte das so sein so gibt die funktion 0 zurück und auch bei der nächsten überprüfung ob hier nur Zahlen von 0 - 9 und punkte verwendet wurden wird 0 zurück gegeben
    wenn es der Bedingung nicht entspricht.
    Zuletzt wird noch geprüft ob die Punkte auch am richtigen Platz sind und nur dann wird 1 zurück gegeben.


    Wiederholtes Verwendungsbeispiel:
    new txt[10] = "10.01.1992";
    if(!ReturnInputDate(txt))return SendClientMessage(playerid,-1,"Deine Eingabe entspricht nicht dem Format: 00.00.0000!");
    return SendClientMessage(playerid,-1,"Deine Eingabe war richtig!");


    da nun die Funktion 1 zurück gibt und in der if-Abfrage überprüft wird ob der wert alles außer 1 ist wird die Nachricht "Deine Eingabe war richtig!"
    an den Spieler über SendClientMessage geschickt.


    statt Irgendwas einfach ein Datum?


    Nur bringt deine FUnktion so gut wie nix du kannst auch ..1 eingeben


    Ich hab mir mal die freiheit genommen das neu zu schreiben bei dem code wird geprüft ob das Datum dem genannten Format entspricht
    00.00.0000
    daher wird sowas auch als fehler erkannt
    1.1.1992
    so jedoch nicht
    01.01.1992

    stock ReturnInputDate(inputtext[])
    {
    if(!inputtext[0])return 0;
    for(new i, j= strlen(inputtext); i != j; ++i)if(inputtext[i] != '.' && (0 > inputtext[i] > 0x39))return 0;
    if(inputtext[2] =='.' && inputtext[5] =='.')return 1;
    return 0;
    }

    mehr steht nicht drinne normal ist das auch vermerkt wenn ein Query Ausgeführt wird und welches Callback dazu aufgerufen wird.
    Daher kann ich dir immer noch nicht sagen wo der Fehler liegt normal sollte es funktionieren.
    Beispiel:



    [16:36:55] [DEBUG] mysql_tquery - scheduling query "SELECT * FROM `fractions`"..
    [16:36:55] [DEBUG] CMySQLQuery::Execute[()] - query was successful
    [16:36:55] [DEBUG] CMySQLQuery::Execute[()] - no callback specified, skipping result saving
    [16:36:55] [DEBUG] CMySQLQuery::Execute[@Load_Fraction_DATA()] - starting query execution
    [16:36:55] [DEBUG] CMySQLQuery::Execute[@Load_Fraction_DATA()] - query was successful
    [16:36:55] [DEBUG] CMySQLQuery::Execute[@Load_Fraction_DATA()] - data being passed to ProcessCallbacks()
    [16:36:55] [DEBUG] Calling callback "@Load_Fraction_DATA"..

    Am besten ist wenn du den debug modus anschaltest und die mysql_log postest
    also unter OnGameModeInit ganz oben
    mysql_log(LOG_DEBUG,LOG_TYPE_TEXT);


    Zu dem benutzt du mehrer Verbindungshandler ?
    Du baust die Verbindung als erstes auf bevor du ihrgend was lädst?
    Sowas wäre völliger bullshit :


    Load_Frak_Vehicle();
    con_Handle = mysql_connect(HOST, USER, DATABASE, PASSWORD, PORT);


    Was du ausschließen kannst ist das Query an sich auch wenn du keine backtricks benutzt bei den spaltennamen. Da frakveh kein Schlüsselwort ist.


    Ich lade die Fahrzeuge doch nicht über OnGameModeExit ? Sie werden da nur gespeichert ?(


    Da hab ich mich kurzerhand verlesen aber Load_Frak_Vehicle() befindet sich schon unter OnGameModeInit und wird somit aufgerufen
    zu dem ist das formatieren sinnlos in der funktion Load_Frak_Vehicle genau wie schon erwähnt das verwenden eines argumentes bei der funktion LoadFrakVehicle


    mysql_function_query(dbhandle, "SELECT * FROM frakveh", true, "LoadFrakVehicle", "");

    Jap. Hab auch gerade gesehen. Danke.


    //edit
    Funktioniert nicht. Die anzeige bleibt bei 100. Egal wieviele ich einsammel. Auch wenn ich eins im Script raus nehme, bleibt die Anzahl konstant auf 100.



    #define MAX_PAKETE 100
    new Paket[MAX_PAKETE+1]={MAX_PAKETE,...};


    updateanzeige(){
    new string[3];
    format(string, 3, "%d",--Paket[MAX_PAKETE]);
    TextDrawHideForAll (Textdraw2);
    TextDrawSetString(Textdraw2, string);
    TextDrawShowForAll(Textdraw2);
    return 1;
    }
    public OnPlayerPickUpPickup(playerid, pickupid){
    new i;
    for(; i != MAX_PAKETE; ++i)if(Paket[i] == pickupid)return DestroyPickup(pickupid),updateanzeige();
    return 1;
    }


    Das Problem ist das zu einen die FUnktion nicht aufgerufen wird und zum anderen musst du erst TextDrawHideForAll benutzen danach den string
    setzen und erneut anzeigen lassen


    //edit an sich reicht es das textdraw nochmal erneut anziegen zulassen ohne davor TextDrawHideForAll zu benutzen.

    Den extra parameter bei LoadFrakVehicle brauchst du nicht ist ja unnötig .


    Zu dem es ist klar das nix erstellt wurde du willst die Fahrzeuge über OnGameModeExit laden und OnGameModeExit wird aufgerufen wenn der Gamemode beendet wird(durch eingabe von gmx,exit oder changemode in die Konsole).
    Daher solltest du das auch unter OnGameModeInit packen.