summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIan McIntosh <ian_mcintosh@linuxadvocate.org>2005-10-26 00:04:53 +0000
committerIan McIntosh <ian_mcintosh@linuxadvocate.org>2005-10-26 00:04:53 +0000
commite122d63d303f3fc298b4083c3bd437c768d48285 (patch)
treebf0797ebbbcd7eb4afb7c8bc0848d4b2404fe153
parent1c7863052b7db8619e30c393802a6bd3db766ad1 (diff)
Moved list of road suffixes to data file.
-rw-r--r--ChangeLog6
-rw-r--r--data/road-suffix-list.txt41
-rw-r--r--src/main.c4
-rw-r--r--src/road.c57
-rw-r--r--src/road.h6
-rw-r--r--src/scenemanager.c2
-rw-r--r--src/util.c89
-rw-r--r--src/util.h3
8 files changed, 191 insertions, 17 deletions
diff --git a/ChangeLog b/ChangeLog
index 9ea6cf2..561da4a 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+2005-10-26 Ian McIntosh <ian_mcintosh@linuxadvocate.org>
+
+ * src/road.c:
+ * src/util.c:
+ * data/road-suffix-list.txt: Moved list of road suffixes to data file.
+
2005-10-25 Ian McIntosh <ian_mcintosh@linuxadvocate.org>
* src/map.c: Switch from gfreelist to g_new and g_free for the list of selected POI (currently not really used).
diff --git a/data/road-suffix-list.txt b/data/road-suffix-list.txt
new file mode 100644
index 0000000..c49f496
--- /dev/null
+++ b/data/road-suffix-list.txt
@@ -0,0 +1,41 @@
+# format is: tab separated list with 'Proper Name' then 'Short Name' then alternatives (used only during import)
+# lines are numbered starting at 1, with 0 being "no suffix". lines starting with # are ignored.
+Road Rd
+Street St
+Drive Dr
+Boulevard Blv Blvd
+Avenue Ave Av
+Circle Crl Cir
+Square Sq
+Path Pth
+Way Wy
+Plaza Plz
+Trail Trl
+Lane Ln
+Crossing Xing
+Place Pl
+Court Ct
+Turnpike Tpke
+Terrace Ter
+Row Row
+Parkway Pky
+Bridge Brg
+Highway Hwy
+Run Run
+Pass Pass
+Freeway Fwy
+Alley Aly
+Crescent Cres
+Tunnel Tunl
+Walk Walk
+Terrace Trce
+Branch Br
+Cove Cv
+Bypass Byp
+Loop Loop
+Spur Spur
+Ramp Ramp
+Pike Pike
+Grade Grd
+Route Rte
+Arc Arc
diff --git a/src/main.c b/src/main.c
index b412af8..406aed8 100644
--- a/src/main.c
+++ b/src/main.c
@@ -32,6 +32,7 @@
#include <gtk/gtk.h>
#include "main.h"
#include "gui.h"
+#include "road.h"
#include "db.h"
#include "map.h"
#include "map_style.h"
@@ -141,6 +142,9 @@ gboolean main_init(void)
g_free(pszApplicationDir);
#endif
+ g_print("initializing road\n");
+ road_init();
+
g_print("initializing map styles\n");
map_style_init();
g_print("initializing map\n");
diff --git a/src/road.c b/src/road.c
index 5d5c5a0..48a8d12 100644
--- a/src/road.c
+++ b/src/road.c
@@ -23,6 +23,31 @@
#include <gtk/gtk.h>
#include "road.h"
+#include "util.h"
+
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif
+
+#define ROAD_SUFFIX_LIST_FILE_NAME ("road-suffix-list.txt")
+#define ROAD_SUFFIX_LIST_MIN_WORDS (2)
+
+struct {
+ GArray* pRoadNameSuffixArray; // an array of null-terminated vectors (an array of gchar* with the last being NULL)
+} g_Road = {0};
+
+void road_init()
+{
+ gchar* pszPath = g_strdup_printf(PACKAGE_SOURCE_DIR"/data/%s", ROAD_SUFFIX_LIST_FILE_NAME);
+ if(util_load_array_of_string_vectors(pszPath, &(g_Road.pRoadNameSuffixArray), ROAD_SUFFIX_LIST_MIN_WORDS) == FALSE) {
+ g_free(pszPath);
+ pszPath = g_strdup_printf(PACKAGE_DATA_DIR"/data/%s", ROAD_SUFFIX_LIST_FILE_NAME);
+ if(util_load_array_of_string_vectors(pszPath, &(g_Road.pRoadNameSuffixArray), ROAD_SUFFIX_LIST_MIN_WORDS) == FALSE) {
+ g_error("Unable to load %s", ROAD_SUFFIX_LIST_FILE_NAME);
+ }
+ }
+ g_free(pszPath);
+}
struct {
gchar* pszLong;
@@ -158,8 +183,7 @@ struct {
{"Tunl", ROAD_SUFFIX_TUNNEL},
{"Walk", ROAD_SUFFIX_WALK},
- {"Walk", ROAD_SUFFIX_WALK},
-
+
{"Branch", ROAD_SUFFIX_BRANCE},
{"Br", ROAD_SUFFIX_BRANCE},
@@ -193,24 +217,29 @@ struct {
const gchar* road_suffix_itoa(gint nSuffixID, ESuffixLength eSuffixLength)
{
- if(nSuffixID >= ROAD_SUFFIX_FIRST && nSuffixID <= ROAD_SUFFIX_LAST) {
- if(eSuffixLength == ROAD_SUFFIX_LENGTH_SHORT) {
- return g_RoadNameSuffix[nSuffixID].pszShort;
- }
- else {
- return g_RoadNameSuffix[nSuffixID].pszLong;
- }
+ if(nSuffixID < g_Road.pRoadNameSuffixArray->len) {
+ //g_debug("looking up suffixID %d", nSuffixID);
+ gchar** apszWords = g_array_index(g_Road.pRoadNameSuffixArray, gchar**, nSuffixID);
+ g_assert(eSuffixLength == 0 || eSuffixLength == 1); // we know there are at least 2 words in the array (see call to util_load_name_list)
+ return apszWords[eSuffixLength];
+ }
+ else {
+ return "";
}
- if(nSuffixID != ROAD_SUFFIX_NONE) return "???";
- return "";
}
gboolean road_suffix_atoi(const gchar* pszSuffix, gint* pReturnSuffixID)
{
+ g_assert(pszSuffix != NULL);
+ g_assert(pReturnSuffixID != NULL);
+
gint i;
- for(i=0 ; i<G_N_ELEMENTS(g_RoadNameSuffixLookup) ; i++) {
- if(g_ascii_strcasecmp(pszSuffix, g_RoadNameSuffixLookup[i].pszName) == 0) {
- *pReturnSuffixID = g_RoadNameSuffixLookup[i].nID;
+ for(i=0 ; i<g_Road.pRoadNameSuffixArray->len ; i++) {
+ gchar** apszWords = g_array_index(g_Road.pRoadNameSuffixArray, gchar**, i);
+
+ // Does this list of words contain the string?
+ if(util_find_string_in_string_vector(pszSuffix, apszWords, NULL)) {
+ *pReturnSuffixID = i;
return TRUE;
}
}
diff --git a/src/road.h b/src/road.h
index 861012e..db8c514 100644
--- a/src/road.h
+++ b/src/road.h
@@ -26,6 +26,8 @@
#include "map.h"
+void road_init();
+
typedef struct {
GArray* pMapPointsArray;
@@ -40,8 +42,8 @@ typedef struct {
// ESuffixLength
typedef enum {
- ROAD_SUFFIX_LENGTH_SHORT,
- ROAD_SUFFIX_LENGTH_LONG
+ ROAD_SUFFIX_LENGTH_LONG,
+ ROAD_SUFFIX_LENGTH_SHORT
} ESuffixLength;
enum ERoadNameSuffix { // these can't change once stored in DB
diff --git a/src/scenemanager.c b/src/scenemanager.c
index 9c91650..33140b9 100644
--- a/src/scenemanager.c
+++ b/src/scenemanager.c
@@ -22,7 +22,7 @@
*/
/*
-Goals:
+Purpose of scenemanager.c:
- Keep text labels and other screen objects from overlapping
- Prevent the same text from showing up too often (currently not more than once)
*/
diff --git a/src/util.c b/src/util.c
index c7a03bd..e7cc59e 100644
--- a/src/util.c
+++ b/src/util.c
@@ -21,6 +21,8 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
+#include <gnome-vfs-2.0/libgnomevfs/gnome-vfs.h>
+
#include "main.h"
#include "util.h"
@@ -615,3 +617,90 @@ EDirection util_match_border(gint nX, gint nY, gint nWidth, gint nHeight, gint n
}
return eDirection;
}
+
+// Load a \n separated list of \t separated names as a GArray of gchar* vectors... :)
+gboolean util_load_array_of_string_vectors(const gchar* pszPath, GArray** ppReturnArray, gint nMinVectorLength)
+{
+ g_assert(pszPath != NULL);
+ g_assert(ppReturnArray != NULL);
+ g_assert(*ppReturnArray == NULL); // require pointer to NULL pointer
+
+ //
+ // 1. Load entire file into memory. XXX: Better to load one line at a time?
+ //
+ gchar* pszFileContent = NULL;
+ if(gnome_vfs_read_entire_file(pszPath, NULL, &pszFileContent) != GNOME_VFS_OK) {
+ return FALSE;
+ }
+
+ //
+ // 2. Split into lines.
+ //
+ gchar** apszLines = g_strsplit(pszFileContent, "\n", -1); // -1 = no maximum
+ gint nNumLines = g_strv_length(apszLines);
+
+ //
+ // 3. Create array and add 0 element
+ //
+ GArray* pNewArray = g_array_sized_new(FALSE, FALSE, sizeof(gchar**), nNumLines);
+
+ {
+ // Make the first nMinVectorLength indexes point to "" and the last NULL
+ gchar** apszFirst = g_malloc(sizeof(gchar*) * (nMinVectorLength+1));
+ gint iVector;
+ for(iVector=0 ; iVector<nMinVectorLength ; iVector++) {
+ apszFirst[iVector] = g_strdup(""); // Just so we don't mix allocated and static strings
+ }
+ apszFirst[nMinVectorLength] = NULL;
+ g_array_append_val(pNewArray, apszFirst);
+ }
+
+ //
+ // 4. Add one NULL-terminated char* vector per row
+ //
+ gint i;
+ for(i=0 ; i<nNumLines ; i++) {
+ if(apszLines[i][0] == '\0') {
+ g_debug("skipping blank line");
+ continue;
+ }
+ if(apszLines[i][0] == '#') {
+ g_debug("skipping comment line");
+ continue;
+ }
+
+ gchar** apszWords = g_strsplit(apszLines[i], "\t", -1);
+ if(g_strv_length(apszWords) < nMinVectorLength) {
+ g_error("line %d contains fewer than %d words", i+1, nMinVectorLength);
+ }
+ g_array_append_val(pNewArray, apszWords);
+ }
+
+ //
+ // 5. Cleanup and return.
+ //
+ g_strfreev(apszLines);
+ g_free(pszFileContent);
+
+ *ppReturnArray = pNewArray;
+ return TRUE;
+}
+
+gboolean util_find_string_in_string_vector(const gchar* pszSearch, const gchar** apszVector, gint* pnReturnIndex)
+{
+ g_assert(pszSearch != NULL);
+ g_assert(apszVector != NULL);
+
+ gint i=0;
+ while(apszVector[i] != NULL) {
+ if(g_ascii_strcasecmp(pszSearch, apszVector[i]) == 0) {
+ if(pnReturnIndex != NULL) {
+ g_assert(*pnReturnIndex == -1); // require either NULL or pointer to (gint)-1
+ *pnReturnIndex = i;
+ }
+ return TRUE;
+ }
+ i++;
+ }
+ return FALSE;
+}
diff --git a/src/util.h b/src/util.h
index ef83fbd..bc3b058 100644
--- a/src/util.h
+++ b/src/util.h
@@ -68,6 +68,9 @@ gboolean util_gtk_window_set_fullscreen(GtkWindow* pWindow, gboolean bFullscreen
gboolean util_gtk_range_instant_set_on_value_changing_callback(GtkRange *range, GtkScrollType scroll, gdouble value, gpointer user_data);
const gchar* util_gtk_menu_item_get_label_text(GtkMenuItem* pMenuItem);
+gboolean util_load_array_of_string_vectors(const gchar* pszPath, GArray** ppReturnArray, gint nMinNamesPerRow);
+gboolean util_find_string_in_string_vector(const gchar* pszSearch, const gchar** apszVector, gint* pnReturnIndex);
+
// if glib < 2.6
#if(!GLIB_CHECK_VERSION(2,6,0))
gint g_strv_length(const gchar** a);