#include <stdlib.h>
#include <stdio.h>
#include <stdbool.h>
-#include <string.h>
#include <Xm/Text.h>
#include <curl/curl.h>
struct MemoryStruct {
- char *memory;
- size_t size;
+ char *memory;
+ size_t size;
};
+int
+memfail(void)
+{
+ printf("ERROR: Out of memory\n");
+ exit(4);
+}
+
+
static size_t
memback(void *contents, size_t size, size_t nmemb, void *userp)
{
- size_t realsize = size * nmemb;
- struct MemoryStruct *mem = (struct MemoryStruct *)userp;
-
- char *ptr = realloc(mem->memory, mem->size + realsize + 1);
- if(!ptr) {
- /* out of memory! */
- printf("not enough memory (realloc returned NULL)\n");
- return 0;
- }
-
- mem->memory = ptr;
- memcpy(&(mem->memory[mem->size]), contents, realsize);
- mem->size += realsize;
- mem->memory[mem->size] = 0;
-
- return realsize;
+ size_t realsize = size * nmemb;
+ struct MemoryStruct *mem = (struct MemoryStruct *)userp;
+
+ char *ptr = realloc(mem->memory, mem->size + realsize + 1);
+ if (!ptr) memfail();
+
+ mem->memory = ptr;
+ memcpy(&(mem->memory[mem->size]), contents, realsize);
+ mem->size += realsize;
+ mem->memory[mem->size] = 0;
+
+ return realsize;
}
int
main(int argc, char *argv[])
{
- // Initialize motif
- Widget toplevel;
- XtAppContext app;
- Widget text_w;
- Arg args[2];
-
- XtSetLanguageProc (NULL, NULL, NULL);
- toplevel = XtVaOpenApplication (&app, "Castle Menu", NULL, 0, &argc, argv,
- NULL, sessionShellWidgetClass, NULL);
-
// Get webpage
CURL *curl = curl_easy_init();
CURLcode res;
exit(1);
}
- struct MemoryStruct chunk;
- chunk.memory = malloc(1); /* will be grown as needed by the realloc above */
- chunk.size = 0; /* no data at this point */
+ struct MemoryStruct chunk;
+ chunk.memory = malloc(1); // Grown as needed by the realloc in memback()
+ chunk.size = 0; // No data yet
curl_easy_setopt(curl, CURLOPT_URL,
"https://nobilis.nobles.edu/skyworld/castlemenu.php");
- curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, memback);
- curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0);
- curl_easy_setopt(curl, CURLOPT_WRITEDATA, (void *)&chunk);
+ curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, memback);
+ curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0);
+ curl_easy_setopt(curl, CURLOPT_WRITEDATA, (void *)&chunk);
printf("INFO: Fetching wepage\n");
res = curl_easy_perform(curl);
}
curl_easy_cleanup(curl);
-
+
// Parse HTML
printf("INFO: Parsing HTML\n");
bool intag = false;
- char *outp = (char *) malloc(strlen(chunk.memory) + 1); // Realloc?
- strcpy(outp, "");
+ char *outp = (char *) calloc(1, sizeof(char));
+ if (!outp) memfail();
+
+ // Extract text from between HTML tags
+ int j = 1;
for (int i = 345; i < strlen(chunk.memory); i++) {
char c = chunk.memory[i];
if (c == '<') intag = true;
- if (!intag) strncat(outp, &c, 1);
+ if (!intag) {
+ j++;
+ outp = (char *) realloc(outp, j);
+ if (!outp) memfail();
+ strncat(outp, &c, 1);
+ }
if (c == '>') intag = false;
}
- strncat(outp, "\0", 1);
-
- char *nl = outp;
- strcpy(nl, "");
- int old = 0;
- /* for (int i = 0; i < 255; i++) { */
- /* if (old != 0 && i > 0) { */
- /* for (int j = old; j <= i; j++) { */
- /* strncat(nl, outp, i - old); */
- /* } */
- /* } */
- /* if (outp[i] == '\n') */
- /* old = i; */
- /* } */
-
- // Display
+
+ // Strip empty newlines
+ char *nl = (char *) calloc(1, sizeof(char));
+ if (!nl) memfail();
+
+ for (int i = 0; i < strlen(outp) - 1; i++) {
+ if (outp[i] == '\n' && outp[i+1] == '\n') i+=4;
+ nl = (char *) realloc(nl, i);
+ if (!nl) memfail();
+ strncat(nl, &outp[i], 1);
+ }
+
+ // Initialize motif
+ Widget toplevel;
+ XtAppContext app;
+ Widget text_w;
+ Arg args[4];
+
+ XtSetLanguageProc(NULL, NULL, NULL);
+ toplevel = XtVaOpenApplication (&app, "Castle Menu", NULL, 0, &argc, argv,
+ NULL, sessionShellWidgetClass, NULL);
+
+ // Set textbox settings
int n = 0;
- XtSetArg(args[0], XmNvalue, outp); n++;
- XtSetArg(args[1], XmNeditable, False); n++;
- text_w = XmCreateText(toplevel, "text", args, n);
+ XtSetArg(args[n], XmNvalue, nl); n++;
+ XtSetArg(args[n], XmNeditable, False); n++;
+ XtSetArg(args[n], XmNcolumns, 80); n++;
+ XtSetArg(args[n], XmNcursorPositionVisible, False); n++;
+ text_w = XmCreateScrolledText(toplevel, "text", args, n);
free(outp);
+ free(nl);
+ // Display everything
XtManageChild(text_w);
XtRealizeWidget(toplevel);
XtAppMainLoop(app);