[GRASS-dev] iconv a required dependency for using Freetype?
Paul Kelly
paul-grass at stjohnspoint.co.uk
Sat May 5 17:59:21 EDT 2007
On Sat, 5 May 2007, Glynn Clements wrote:
> You just need a hard-coded conversion to UCS-2 for the case where
> iconv() is unavailable. ISO-8859-1 -> UCS-2 (used by d.text.freetype)
> is trivial; a built-in UTF-8 -> UCS-2 converter wouldn't be a lot of
> work.
Thanks for the hint - that seems to have worked out fine and I've already
committed the fix.
I've attached a diff of a few more changes I'm considering making, mostly
relating to path and filename handling for Windows compatibility in
loading fonts. Here's what I've changed so far:
lib/driver/Font.c, COM_Font_get():
* Cross-platform check for absolute path (new gislib function added)
* Check for pathname matching the GRASS stroke fonts made more robust by
(a) First converting all directory separator characters to '/'
(b) Doing a case-insensitive comparison
lib/driver/font2.c, read_fontmap():
* Warning message when unable to open font made clearer by specifying
the exact path it was trying to open and giving the system error message.
font_init():
* Convert directory separator characters to '/' so that the way the
directory name is stripped off works
* Strip off the ".hmp" extension if it was there. It strikes me as very
weird that I needed to do this, because without that I reall can't see how
passing the full path to one of the GRASS stroke fronts would have worked.
The full filename has to be given in the GRASS_FONT variable, otherwise
the font_exists() check in COM_Font_get() will fail, but the .hmp is never
stripped off and then it is added again in read_fontmap(), resulting in it
trying to open a file ending in ".hmp.hmp".
I haven't committed the changes yet as they're not complete. Apart from
being unsure about stripping off the .hmp extension, specifying a
font in GRASS_FONT from the freetypecap file doesn't work. I'm just
testing this from the command line on Windows, i.e. using direct
rendering as drivers don't work, and I can't see where/if the freetypecap
file is actually being read. Specifying the full path to a Freetype font
works fine, but is the freetypecap file only read when a driver process
is initialised?
-------------- next part --------------
Index: include/gisdefs.h
===================================================================
RCS file: /home/grass/grassrepository/grass6/include/gisdefs.h,v
retrieving revision 1.99
diff -u -r1.99 gisdefs.h
--- include/gisdefs.h 2 May 2007 06:00:33 -0000 1.99
+++ include/gisdefs.h 5 May 2007 21:43:58 -0000
@@ -865,6 +865,7 @@
/* paths.c */
int G_mkdir(const char *);
int G_is_dirsep(char);
+int G_is_absolute_path(const char *);
char *G_convert_dirseps_to_host(char *);
char *G_convert_dirseps_from_host(char *);
struct stat;
/* timestamp.c */
Index: lib/gis/paths.c
===================================================================
RCS file: /home/grass/grassrepository/grass6/lib/gis/paths.c,v
retrieving revision 2.3
diff -u -r2.3 paths.c
--- lib/gis/paths.c 4 Apr 2007 04:07:01 -0000 2.3
+++ lib/gis/paths.c 5 May 2007 21:43:58 -0000
@@ -41,6 +41,27 @@
}
/**
+ * \brief Checks if a specified path looks like an absolute
+ * path on the host system
+ *
+ * \param path String containing path to check
+ *
+ * \return 1 if path looks like an absolute path, 0 if not
+ **/
+
+int G_is_absolute_path(const char *path)
+{
+ if ( G_is_dirsep(path[0])
+#ifdef __MINGW32__
+ || ((path[1] == ':') && G_is_dirsep(path[2]))
+#endif
+ )
+ return 1;
+ else
+ return 0;
+}
+
+/**
* \brief Converts directory separator characters in a string to the
* native host separator character (/ on Unix, \ on Windows)
*
Index: lib/driver/Font.c
===================================================================
RCS file: /home/grass/grassrepository/grass6/lib/driver/Font.c,v
retrieving revision 1.8
diff -u -r1.8 Font.c
--- lib/driver/Font.c 3 May 2007 04:32:03 -0000 1.8
+++ lib/driver/Font.c 5 May 2007 21:43:58 -0000
@@ -24,17 +24,25 @@
void COM_Font_get(const char *name)
{
- if (name[0] == '/')
+ if (G_is_absolute_path(name))
{
static char prefix[4096];
+ char name_copy[4096];
if (!font_exists(name))
return;
if (!*prefix)
+ {
sprintf(prefix, "%s/fonts/", G_gisbase());
-
- if (strncmp(name, prefix, strlen(prefix)) == 0)
+ G_convert_dirseps_from_host(prefix);
+ }
+
+ /* Case-insensitive comparison with all '/' dirsep chars */
+ strncpy(name_copy, name, strlen(prefix));
+ name_copy[strlen(prefix)] = '\0';
+ G_convert_dirseps_from_host(name_copy);
+ if (G_strcasecmp(name_copy, prefix) == 0)
stroke_set(name);
else
freetype_set(name);
Index: lib/driver/font2.c
===================================================================
RCS file: /home/grass/grassrepository/grass6/lib/driver/font2.c,v
retrieving revision 1.2
diff -u -r1.2 font2.c
--- lib/driver/font2.c 5 Mar 2007 06:20:00 -0000 1.2
+++ lib/driver/font2.c 5 May 2007 21:43:58 -0000
@@ -2,6 +2,7 @@
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
+#include <errno.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
@@ -152,7 +153,8 @@
fp = fopen(buf, "r");
if (!fp)
{
- G_warning("unable to open font map '%s'", name);
+ G_warning("unable to open font map '%s': %s", buf,
+ strerror(errno));
return;
}
@@ -185,13 +187,23 @@
int font_init(const char *name)
{
- if (strchr(name, '/'))
- name = strrchr(name, '/') + 1;
+ char name_copy[4096];
+ char *name_ptr;
- if (strcmp(name, current_font) == 0)
+ strcpy(name_copy, name);
+ G_convert_dirseps_from_host(name_copy);
+
+ if (strchr(name_copy, GRASS_DIRSEP))
+ name_ptr = strrchr(name_copy, GRASS_DIRSEP) + 1;
+ else
+ name_ptr = name_copy;
+
+ G_basename(name_ptr, "hmp");
+
+ if (strcmp(name_ptr, current_font) == 0)
return 0;
- strcpy(current_font, name);
+ strcpy(current_font, name_ptr);
font_loaded = 0;
return 0;
More information about the grass-dev
mailing list