summary refs log tree commit diff
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--Makefile2
-rw-r--r--freecell.c31
-rw-r--r--path.h57
-rw-r--r--sol.c31
4 files changed, 72 insertions, 49 deletions
diff --git a/Makefile b/Makefile
index c2457d3..cf107f6 100644
--- a/Makefile
+++ b/Makefile
@@ -13,7 +13,7 @@ $(BINS): cards.o
 
 cards.o dump.o freecell.o sol.o: cards.h
 
-freecell.o sol.o: layout.h stack.h
+freecell.o sol.o: layout.h path.h stack.h
 
 clean:
 	rm -f $(BINS) *.o *.bmp
diff --git a/freecell.c b/freecell.c
index e8b41f6..f480bda 100644
--- a/freecell.c
+++ b/freecell.c
@@ -22,6 +22,7 @@
 
 #include "cards.h"
 #include "layout.h"
+#include "path.h"
 #include "stack.h"
 
 #define ARRAY_LEN(a) (sizeof(a) / sizeof((a)[0]))
@@ -274,7 +275,6 @@ static bool mouseButtonUp(SDL_MouseButtonEvent button) {
 	return false;
 }
 
-static SDL_Window *window;
 static SDL_Renderer *render;
 
 static void renderOutlines(void) {
@@ -309,7 +309,7 @@ static void renderList(SDL_Texture **textures, const struct List *list) {
 
 static void err(const char *title) {
 	int error = SDL_ShowSimpleMessageBox(
-		SDL_MESSAGEBOX_ERROR, title, SDL_GetError(), window
+		SDL_MESSAGEBOX_ERROR, title, SDL_GetError(), NULL
 	);
 	if (error) fprintf(stderr, "%s\n", SDL_GetError());
 	exit(EXIT_FAILURE);
@@ -319,32 +319,14 @@ int main(void) {
 	if (SDL_Init(SDL_INIT_VIDEO) < 0) err("SDL_Init");
 	atexit(SDL_Quit);
 
-	char *prefPath = SDL_GetPrefPath("Causal Agency", "Cards");
-	if (!prefPath) err("SDL_GetPrefPath");
-
 	char *basePath = SDL_GetBasePath();
 	if (!basePath) err("SDL_GetBasePath");
 
-	const char *paths[] = { prefPath, basePath, "" };
-	const char *names[] = { "CARDS.DLL", "SOL.EXE", "cards.dll" };
+	char *prefPath = SDL_GetPrefPath("Causal Agency", "Cards");
+	if (!prefPath) err("SDL_GetPrefPath");
 
-	SDL_RWops *rw = NULL;
-	for (uint i = 0; !rw && i < ARRAY_LEN(paths); ++i) {
-		for (uint j = 0; !rw && j < ARRAY_LEN(names); ++j) {
-			char path[1024];
-			snprintf(path, sizeof(path), "%s%s", paths[i], names[j]);
-			rw = SDL_RWFromFile(path, "rb");
-		}
-	}
-	if (!rw) {
-		char msg[4096];
-		snprintf(
-			msg, sizeof(msg), "CARDS.DLL or SOL.EXE not found in:\n%s\n%s",
-			prefPath, basePath
-		);
-		SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Cards", msg, NULL);
-		return EXIT_FAILURE;
-	}
+	SDL_RWops *rw = pathCards(basePath, prefPath);
+	if (!rw) return EXIT_FAILURE;
 
 	SDL_Surface *surfaces[Cards_Empty];
 	int error = Cards_LoadCards(
@@ -354,6 +336,7 @@ int main(void) {
 	if (error) err("Cards_LoadCards");
 	SDL_RWclose(rw);
 
+	SDL_Window *window;
 	error = SDL_CreateWindowAndRenderer(
 		WindowWidth, WindowHeight, SDL_WINDOW_ALLOW_HIGHDPI,
 		&window, &render
diff --git a/path.h b/path.h
new file mode 100644
index 0000000..05caa62
--- /dev/null
+++ b/path.h
@@ -0,0 +1,57 @@
+/* Copyright (C) 2019  C. McEnroe <june@causal.agency>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef PATH_H
+#define PATH_H
+
+#include <SDL_filesystem.h>
+#include <SDL_rwops.h>
+#include <stddef.h>
+#include <stdio.h>
+
+static inline SDL_RWops *
+pathSearch(const char *base, const char *pref, const char **names, size_t len) {
+	const char *paths[3] = { pref, base, "" };
+	for (size_t i = 0; i < 3; ++i) {
+		for (size_t j = 0; j < len; ++j) {
+			char path[1024];
+			snprintf(path, sizeof(path), "%s%s", paths[i], names[j]);
+			SDL_RWops *rw = SDL_RWFromFile(path, "rb");
+			if (rw) return rw;
+		}
+	}
+	return NULL;
+}
+
+static inline SDL_RWops *
+pathFind(const char *base, const char *pref, const char *name) {
+	return pathSearch(base, pref, &name, 1);
+}
+
+static inline SDL_RWops *pathCards(const char *base, const char *pref) {
+	const char *names[3] = { "CARDS.DLL", "SOL.EXE", "cards.dll" };
+	SDL_RWops *rw = pathSearch(base, pref, names, 3);
+	if (rw) return rw;
+	char msg[4096];
+	snprintf(
+		msg, sizeof(msg), "%s or %s not found in:\n%s\n%s",
+		names[0], names[1], pref, base
+	);
+	SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Cards", msg, NULL);
+	return NULL;
+}
+
+#endif
diff --git a/sol.c b/sol.c
index a2bd7c3..f02e4a1 100644
--- a/sol.c
+++ b/sol.c
@@ -22,6 +22,7 @@
 
 #include "cards.h"
 #include "layout.h"
+#include "path.h"
 #include "stack.h"
 
 #define ARRAY_LEN(a) (sizeof(a) / sizeof((a)[0]))
@@ -301,7 +302,6 @@ static bool mouseMotion(SDL_MouseMotionEvent motion) {
 	return true;
 }
 
-static SDL_Window *window;
 static SDL_Renderer *render;
 static SDL_Texture *textures[Cards_CardCount];
 
@@ -315,7 +315,7 @@ static void renderList(const struct List *list) {
 
 static void err(const char *title) {
 	int error = SDL_ShowSimpleMessageBox(
-		SDL_MESSAGEBOX_ERROR, title, SDL_GetError(), window
+		SDL_MESSAGEBOX_ERROR, title, SDL_GetError(), NULL
 	);
 	if (error) fprintf(stderr, "%s\n", SDL_GetError());
 	exit(EXIT_FAILURE);
@@ -325,32 +325,14 @@ int main(void) {
 	if (SDL_Init(SDL_INIT_VIDEO) < 0) err("SDL_Init");
 	atexit(SDL_Quit);
 
-	char *prefPath = SDL_GetPrefPath("Causal Agency", "Cards");
-	if (!prefPath) err("SDL_GetPrefPath");
-
 	char *basePath = SDL_GetBasePath();
 	if (!basePath) err("SDL_GetBasePath");
 
-	const char *paths[] = { prefPath, basePath, "" };
-	const char *names[] = { "CARDS.DLL", "SOL.EXE", "cards.dll" };
+	char *prefPath = SDL_GetPrefPath("Causal Agency", "Cards");
+	if (!prefPath) err("SDL_GetPrefPath");
 
-	SDL_RWops *rw = NULL;
-	for (uint i = 0; !rw && i < ARRAY_LEN(paths); ++i) {
-		for (uint j = 0; !rw && j < ARRAY_LEN(names); ++j) {
-			char path[1024];
-			snprintf(path, sizeof(path), "%s%s", paths[i], names[j]);
-			rw = SDL_RWFromFile(path, "rb");
-		}
-	}
-	if (!rw) {
-		char msg[4096];
-		snprintf(
-			msg, sizeof(msg), "CARDS.DLL or SOL.EXE not found in:\n%s\n%s",
-			prefPath, basePath
-		);
-		SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Cards", msg, NULL);
-		return EXIT_FAILURE;
-	}
+	SDL_RWops *rw = pathCards(basePath, prefPath);
+	if (!rw) return EXIT_FAILURE;
 
 	SDL_Surface *surfaces[Cards_CardCount];
 	int error = Cards_LoadCards(
@@ -360,6 +342,7 @@ int main(void) {
 	if (error) err("Cards_LoadCards");
 	SDL_RWclose(rw);
 
+	SDL_Window *window;
 	error = SDL_CreateWindowAndRenderer(
 		WindowWidth, WindowHeight, SDL_WINDOW_ALLOW_HIGHDPI,
 		&window, &render