Jump to content
DeltaWorlds

Recommended Posts

Posted
#define AW_NO_FUNCTION_MAPPING // for UTF-8 or older single-byte and multi-byte character sets

#include <windows.h>
#include "reasons.h"
#include "aw.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>

#define MAX_AVATARS_IN_SCENE 35
#define MAX_HUD_LINES 10
#define MAX_LINE_LENGTH 50
#define MAX_HUD_LINE_LINES 5
#define HEARTBEAT_INTERVAL 30

struct AVATAR
{
    int session;
    char name[18];
};

struct HUD_LINE
{
    int id;
    int num_lines;
    char lines[MAX_HUD_LINE_LINES][MAX_LINE_LENGTH + 1];
};

struct AVATAR avatars[MAX_AVATARS_IN_SCENE];
struct HUD_LINE hud_lines[MAX_HUD_LINES];

void handle_avatar_add(void);
void handle_avatar_delete(void);
void handle_address(int rc);
void handle_chat(void);
void update_hud_messages(void);
void wrap_line(const char* line, struct HUD_LINE* hud_line, int max_line_length);
void send_heartbeat(void); // Prototype heartbeat function, keeps bot from timing out

int main(int argc, char* argv[])
{
    int rc;

    // Check command line
    if (argc < 4)
    {
        printf("To begin type: DWbot1.exe cit-number password world\n", argv[0]);
        return 1;
    }

    // Initialize Delta Worlds API
    rc = aw_init(AW_BUILD);
    if (rc != RC_SUCCESS)
    {
        printf("Unable to initialize API (reason %d)\n", rc);
        return 1;
    }

    // Variable to track last heartbeat time
    time_t last_heartbeat = time(NULL);

    // Install handler for avatar_add, avatar_delete, and chat events
    aw_event_set(AW_EVENT_AVATAR_ADD, handle_avatar_add);
    aw_event_set(AW_EVENT_AVATAR_DELETE, handle_avatar_delete);
    aw_event_set(AW_EVENT_CHAT, handle_chat);

    /* Install callback for aw_address */
    aw_callback_set(AW_CALLBACK_ADDRESS, handle_address);

    /* create bot instance */
    if ((rc = aw_create("auth.deltaworlds.com", 6671, 0)) != 0) {
        printf("Unable to create bot instance (reason %d)\n", rc);
        exit(1);
    }

    // Log bot into the universe
    aw_int_set(AW_LOGIN_OWNER, atoi(argv[1]));
    aw_string_set(AW_LOGIN_PRIVILEGE_PASSWORD, argv[2]);
    aw_string_set(AW_LOGIN_APPLICATION, "OCMBOTv1");
    aw_string_set(AW_LOGIN_NAME, "HUDchat");
    rc = aw_login();
    if (rc != RC_SUCCESS)
    {
        printf("Unable to login (reason %d)\n", rc);
        return 1;
    }

    // Enter bot into the world
    rc = aw_enter(argv[3]);
    if (rc != RC_SUCCESS)
    {
        printf("Unable to enter world (reason %d)\n", rc);
        return 1;
    }

    // Announce position in the world
    aw_int_set(AW_MY_X, 1000); // 1W
    aw_int_set(AW_MY_Z, -7000); // 7S
    aw_int_set(AW_MY_YAW, 2250); // Face towards GZ
    rc = aw_state_change();
    if (rc != RC_SUCCESS)
    {
        printf("Unable to change state (reason %d)\n", rc);
        return 1;
    }

    // Main event loop
    while (aw_wait(-1) == RC_SUCCESS) {
        if (difftime(time(NULL), last_heartbeat) >= HEARTBEAT_INTERVAL) {
            send_heartbeat();
            last_heartbeat = time(NULL); // Update the last heartbeat time
        }

        // Close everything down
        aw_destroy();
        aw_term();

        return 0;
    }
}

void send_heartbeat() {
    // Heartbeat function - sends clear command to chat to keep from timing out.
    aw_say("/clear");
}

void handle_avatar_add(void)
{
    int i;
    int rc;

    // Add avatar to the scene
    for (i = 0; i < MAX_AVATARS_IN_SCENE; i++)
    {
        if (avatars[i].session == 0)
        {
            avatars[i].session = aw_int(AW_AVATAR_SESSION);
            strcpy(avatars[i].name, aw_string(AW_AVATAR_NAME));
            break;
        }
    }
    aw_address(aw_int(AW_AVATAR_SESSION));


    // Say Hello (remove slashes from the following lines to enable greeting message) //
  
  //  char message[100];
  //  static char avatar_name[AW_MAX_ATTRIBUTE];
  //  strcpy(avatar_name, aw_string(AW_AVATAR_NAME));
  //  sprintf(message, "Ahoy there %s!", avatar_name);
  //  aw_say(message);
}

void handle_avatar_delete(void)
{
    int i;

    // Remove avatar from the scene
    for (i = 0; i < MAX_AVATARS_IN_SCENE; i++)
    {
        if (avatars[i].session == aw_int(AW_CHAT_SESSION))
        {
            avatars[i].session = 0; // Mark struct as unused
            strcpy(avatars[i].name, "");
            break;
        }
    }


    // Say Bye (remove slashes from the following lines to enable farewell message) //
   
   // char message[100];
   // static char avatar_name[AW_MAX_ATTRIBUTE];
   // strcpy(avatar_name, aw_string(AW_AVATAR_NAME));
   // sprintf(message, "Bye, %s!", avatar_name);
   // aw_say(message);
}

void handle_address(int rc)
{
    /* Keep in mind that AW_AVATAR_NAME is not defined within the context of this callback */

    int i;
    char hud_message[100];
    char name[256];
    char msg[256];

    strcpy(name, "<UNKNOWN>");

    /* Find name of the avatar */
    for (i = 0; i < MAX_AVATARS_IN_SCENE; i++)
    {
        if (avatars[i].session == aw_int(AW_AVATAR_SESSION))
        {
            strcpy(name, avatars[i].name);
            break;
        }
    }

    if (rc != RC_SUCCESS)
    {
        sprintf(msg, "%s, I cannot determine your IP address (reason %d)", name, rc);
    }
    else
    {
        int           address;
        unsigned char* p = (unsigned char*)&address;

        address = aw_int(AW_AVATAR_ADDRESS);

        /* The address is in network byte order which means that the most significant byte comes first in memory */
        sprintf(hud_message, "%s [%u.%u.%u.%u] enters", name, p[0], p[1], p[2], p[3]);

        /* log the event to the console */
        printf("[%u.%u.%u.%u] %s entered chat.\n", p[0], p[1], p[2], p[3], name);

        // Shift up old messages etc
        for (i = 0; i < MAX_HUD_LINES - 1; i++)
        {
            hud_lines[i].id = hud_lines[i + 1].id;
            hud_lines[i].num_lines = hud_lines[i + 1].num_lines;
            for (int j = 0; j < hud_lines[i].num_lines; j++)
            {
                strcpy(hud_lines[i].lines[j], hud_lines[i + 1].lines[j]);
            }
        }
        hud_lines[MAX_HUD_LINES - 1].id = 0; // We don't need the session ID for this message
        wrap_line(hud_message, &hud_lines[MAX_HUD_LINES - 1], MAX_LINE_LENGTH);

        // Update HUD messages
        update_hud_messages();
    }
}


void handle_chat(void)
{
    char message[301];
    static char avatar_name[AW_MAX_ATTRIBUTE];
    strcpy(avatar_name, aw_string(AW_AVATAR_NAME));

    // Check for the "/clear" command
    if (strcmp(aw_string(AW_CHAT_MESSAGE), "/clear") == 0)
    {
        // Clear HUD
        for (int i = 0; i < MAX_HUD_LINES; i++)
        {
            hud_lines[i].id = 0;
            hud_lines[i].num_lines = 0;
        }

        // Display "Chat cleared" message
        wrap_line("Chat cleared", &hud_lines[MAX_HUD_LINES - 1], MAX_LINE_LENGTH);
    }
    else
    {
        // Handle normal chat messages
        snprintf(message, 300, "%s: %s", avatar_name, aw_string(AW_CHAT_MESSAGE));

        // Shift up old messages
        for (int i = 0; i < MAX_HUD_LINES - 1; i++)
        {
            hud_lines[i].id = hud_lines[i + 1].id;
            hud_lines[i].num_lines = hud_lines[i + 1].num_lines;
            for (int j = 0; j < hud_lines[i].num_lines; j++)
            {
                strcpy(hud_lines[i].lines[j], hud_lines[i + 1].lines[j]);
            }
        }

        // Check if the chat message starts with "/me" and remove for action
        if (strncmp(aw_string(AW_CHAT_MESSAGE), "/me", 3) == 0) {
            snprintf(message, 300, "%s %s", avatar_name, aw_string(AW_CHAT_MESSAGE) + 4); // +4 to remove the "/me " from the message
        }
        hud_lines[MAX_HUD_LINES - 1].id = aw_int(AW_CHAT_SESSION);
        wrap_line(message, &hud_lines[MAX_HUD_LINES - 1], MAX_LINE_LENGTH);
    }

    // Update HUD messages
    update_hud_messages();
}


void wrap_line(const char* line, struct HUD_LINE* hud_line, int max_line_length)
{
    const char* line_end = line + strlen(line);
    const char* line_start = line;
    hud_line->num_lines = 0;

    while (line_start < line_end && hud_line->num_lines < MAX_HUD_LINE_LINES)
    {
        const char* line_break = line_start + max_line_length;
        if (line_break > line_end)
        {
            line_break = line_end;
        }
        else
        {
            while (line_break > line_start && *line_break != ' ')
            {
                line_break--;
            }
            if (line_break == line_start)
            {
                line_break = line_start + max_line_length;
            }
        }

        strncpy(hud_line->lines[hud_line->num_lines], line_start, line_break - line_start);
        hud_line->lines[hud_line->num_lines][line_break - line_start] = '\0';
        hud_line->num_lines++;

        line_start = line_break;
        while (*line_start == ' ')
        {
            line_start++;
        }
    }
}



void update_hud_messages(void)
{
    int rc;

    // Destroy old HUD elements
    for (int i = 0; i < MAX_HUD_LINES; i++)
    {
        for (int j = 0; j < MAX_HUD_LINE_LINES; j++)
        {
            aw_hud_destroy(0, i * MAX_HUD_LINE_LINES + j + 1);
        }
    }

    // Create new HUD elements
    int y_offset = 0;
    for (int i = 0; i < MAX_HUD_LINES; i++)
    {
        for (int j = 0; j < hud_lines[i].num_lines; j++)
        {
            // create the HUD element
            aw_int_set(AW_HUD_ELEMENT_TYPE, AW_HUD_TYPE_TEXT);
            aw_string_set(AW_HUD_ELEMENT_TEXT, hud_lines[i].lines[j]);
            aw_int_set(AW_HUD_ELEMENT_ID, y_offset + 1);
            aw_int_set(AW_HUD_ELEMENT_SESSION, 0);
            aw_int_set(AW_HUD_ELEMENT_ORIGIN, AW_HUD_ORIGIN_TOP_LEFT);
            aw_float_set(AW_HUD_ELEMENT_OPACITY, 1.0f);
            aw_int_set(AW_HUD_ELEMENT_X, -64);
            aw_int_set(AW_HUD_ELEMENT_Y, 50 + y_offset * 28); // Adjust the spacing between lines
            aw_int_set(AW_HUD_ELEMENT_Z, 1);
            aw_int_set(AW_HUD_ELEMENT_FLAGS, AW_HUD_ELEMENT_FLAG_CLICKS);
            aw_int_set(AW_HUD_ELEMENT_SIZE_X, 800);
            aw_int_set(AW_HUD_ELEMENT_SIZE_Y, 30); // Increase the text size
            aw_int_set(AW_HUD_ELEMENT_FLAGS, AW_HUD_ELEMENT_FLAG_TRANSITION | true);

            // Set the color to green for the IP address and name announcement message
            if (strstr(hud_lines[i].lines[j], "enters") != NULL && strstr(hud_lines[i].lines[j], "[") != NULL && strstr(hud_lines[i].lines[j], "]") != NULL) {
                aw_int_set(AW_HUD_ELEMENT_COLOR, 0x00FF00); // Green color
            }
            else {
                aw_int_set(AW_HUD_ELEMENT_COLOR, 0xFFFFFF); // White color
            }

            rc = aw_hud_create();
            if (rc != RC_SUCCESS)
            {
                printf("Unable to create HUD element (reason %d)\n", rc);
            }

            y_offset++;
        }
    }
}

 

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...