Annotation of libwww/Library/src/HTIcons.c, revision 2.30
2.6 frystyk 1: /* HTIcon.c
2: ** ICON MANAGEMENT
3: **
2.10 frystyk 4: ** (c) COPYRIGHT MIT 1995.
2.6 frystyk 5: ** Please first read the full copyright statement in the file COPYRIGH.
2.30 ! kahan 6: ** @(#) $Id: HTIcons.c,v 2.29 1999/02/22 22:10:11 frystyk Exp $
2.1 frystyk 7: **
8: ** This module contains the functions for initializing, adding
9: ** and selecting the icon for local directory listings, FTP and Gopher.
10: **
11: ** History:
2.13 frystyk 12: ** Mar 94 Written by Ari Luotonen, luotonen@dxcern.cern.ch
2.27 frystyk 13: ** Henrik Frystyk, frystyk@w3.org
2.1 frystyk 14: **
15: */
16:
17: /* Library include files */
2.28 frystyk 18: #include "wwwsys.h"
2.27 frystyk 19: #include "WWWUtil.h"
20: #include "WWWCore.h"
2.1 frystyk 21: #include "HTIcons.h" /* Implemented here */
2.5 duns 22:
2.27 frystyk 23: struct _HTIconNode {
24: char * icon_url;
25: char * icon_alt;
26: char * type_templ;
27: };
28:
2.1 frystyk 29: /* Globals */
2.15 frystyk 30: PRIVATE HTIconNode * icon_unknown = NULL; /* Unknown file type */
31: PRIVATE HTIconNode * icon_blank = NULL; /* Blank icon in heading */
32: PRIVATE HTIconNode * icon_parent = NULL; /* Parent directory icon */
33: PRIVATE HTIconNode * icon_dir = NULL; /* Directory icon */
2.1 frystyk 34:
35: /* Type definitions and global variables etc. local to this module */
36: PRIVATE HTList * icons = NULL;
37: PRIVATE int alt_len = 0; /* Longest ALT text */
38:
39: /* ------------------------------------------------------------------------- */
40:
2.18 frystyk 41: PRIVATE void alt_resize (char * alt)
2.1 frystyk 42: {
43: if (alt) {
44: int len = strlen(alt);
45: if (len > alt_len) alt_len = len;
46: }
47: }
48:
2.27 frystyk 49: PRIVATE BOOL match (char * templ,
50: const char * actual)
51: {
52: static char * c1 = NULL;
53: static char * c2 = NULL;
54: char * slash1;
55: char * slash2;
56:
57: StrAllocCopy(c1,templ);
58: StrAllocCopy(c2,actual);
59:
60: slash1 = strchr(c1,'/');
61: slash2 = strchr(c2,'/');
62:
63: if (slash1 && slash2) {
64: *slash1++ = 0;
65: *slash2++ = 0;
66: return HTStrMatch(c1,c2) && HTStrMatch(slash1,slash2);
67: }
68: else if (!slash1 && !slash2)
69: return HTStrMatch(c1,c2) ? YES : NO;
70: else
71: return NO;
72: }
73:
2.1 frystyk 74:
2.27 frystyk 75: PRIVATE char * prefixed (const char * name, const char * prefix)
2.1 frystyk 76: {
2.27 frystyk 77: char * ret = NULL;
78: if (name) {
79: int len = prefix ? strlen(prefix) : 0;
80: if ((ret = (char *) HT_MALLOC(len + strlen(name) + 2)) == NULL)
81: HT_OUTOFMEM("prefixed");
82: if (prefix) {
83: strcpy(ret, prefix);
84: if (*prefix && prefix[len-1] != '/') strcat(ret, "/");
85: strcat(ret, name);
86: } else
87: strcpy(ret, name);
88: }
89: return ret;
90: }
91:
92: PUBLIC char * HTIcon_url (HTIconNode * node)
93: {
94: return node ? node->icon_url : NULL;
95: }
2.1 frystyk 96:
2.27 frystyk 97: /*
98: ** Returned string must be freed by caller
99: */
100: PUBLIC char * HTIcon_alternative (HTIconNode * node, BOOL brackets)
101: {
102: char * ret = NULL;
103: if (node) {
104: char * p = NULL;
105: int len = node->icon_alt ? strlen(node->icon_alt) : 0;
106: if ((p = ret = (char *) HT_MALLOC(alt_len + 3)) == NULL)
107: HT_OUTOFMEM("HTIcon_alt_string");
2.1 frystyk 108: *p++ = brackets ? '[' : ' ';
2.27 frystyk 109: if (node->icon_alt) strcpy(p, node->icon_alt);
110: p += len;
111: while (len++ < alt_len) *p++=' ';
2.1 frystyk 112: *p++ = brackets ? ']' : ' ';
2.27 frystyk 113: *p = 0;
114: }
2.1 frystyk 115: return ret;
116: }
117:
118: /*
119: ** HTAddIcon(url, alt, type_templ) adds icon:
120: **
121: ** <IMG SRC="url" ALT="[alt]">
122: **
123: ** for files for which content-type or content-encoding matches
124: ** type_templ. If type_templ contains a slash, it is taken to be
125: ** a content-type template. Otherwise, it is a content-encoding
126: ** template.
127: */
2.27 frystyk 128: PUBLIC BOOL HTIcon_add (const char * url, const char * prefix,
129: char * alt, char * type_templ)
2.1 frystyk 130: {
2.27 frystyk 131: if (url && type_templ) {
132: HTIconNode * node;
133: if ((node = (HTIconNode *) HT_CALLOC(1,sizeof(HTIconNode))) == NULL)
134: HT_OUTOFMEM("HTAddIcon");
135: if (url) node->icon_url = prefixed(url, prefix);
136: if (alt) StrAllocCopy(node->icon_alt, alt);
137: if (type_templ) StrAllocCopy(node->type_templ, type_templ);
138: if (!icons) icons = HTList_new();
139: HTList_addObject(icons, (void *) node);
140: alt_resize(alt);
2.29 frystyk 141: HTTRACE(PROT_TRACE, "AddIcon..... %s => SRC=\"%s\" ALT=\"%s\"\n" _
142: type_templ _ url _ alt ? alt : "");
2.27 frystyk 143: return YES;
144: }
145: return NO;
2.1 frystyk 146: }
147:
148: /*
2.27 frystyk 149: ** Add the icon used for files for which
2.1 frystyk 150: ** no other icon seems appropriate (unknown type).
151: */
2.27 frystyk 152: PUBLIC BOOL HTIcon_addUnknown (const char * url, const char * prefix,
153: char * alt)
2.1 frystyk 154: {
2.27 frystyk 155: if ((icon_unknown = (HTIconNode *) HT_CALLOC(1,sizeof(HTIconNode)))==NULL)
2.21 frystyk 156: HT_OUTOFMEM("HTAddUnknownIcon");
2.27 frystyk 157: if (url) icon_unknown->icon_url = prefixed(url, prefix);
2.1 frystyk 158: if (alt) StrAllocCopy(icon_unknown->icon_alt, alt);
159: alt_resize(alt);
2.29 frystyk 160: HTTRACE(PROT_TRACE, "Icon add.... UNKNOWN => SRC=\"%s\" ALT=\"%s\"\n" _ url _
2.8 frystyk 161: alt ? alt : "");
2.27 frystyk 162: return YES;
2.1 frystyk 163: }
164:
165:
166: /*
2.27 frystyk 167: ** Add the blank icon used in the heading of the listing.
2.1 frystyk 168: */
2.27 frystyk 169: PUBLIC BOOL HTIcon_addBlank (const char * url, const char * prefix, char * alt)
2.1 frystyk 170: {
2.21 frystyk 171: if ((icon_blank = (HTIconNode *) HT_CALLOC(1,sizeof(HTIconNode))) == NULL)
172: HT_OUTOFMEM("HTAddBlankIcon");
2.27 frystyk 173: if (url) icon_blank->icon_url = prefixed(url, prefix);
2.1 frystyk 174: if (alt) StrAllocCopy(icon_blank->icon_alt, alt);
175: alt_resize(alt);
2.29 frystyk 176: HTTRACE(PROT_TRACE, "Icon add.... BLANK => SRC=\"%s\" ALT=\"%s\"\n" _ url _
2.8 frystyk 177: alt ? alt : "");
2.27 frystyk 178: return YES;
2.1 frystyk 179: }
180:
181:
182: /*
2.27 frystyk 183: ** Add the parent directory icon.
2.1 frystyk 184: */
2.27 frystyk 185: PUBLIC BOOL HTIcon_addParent (const char * url, const char * prefix, char * alt)
2.1 frystyk 186: {
2.21 frystyk 187: if ((icon_parent = (HTIconNode *) HT_CALLOC(1,sizeof(HTIconNode))) == NULL)
188: HT_OUTOFMEM("HTAddBlankIcon");
2.27 frystyk 189: if (url) icon_parent->icon_url = prefixed(url, prefix);
2.1 frystyk 190: if (alt) StrAllocCopy(icon_parent->icon_alt, alt);
191: alt_resize(alt);
2.29 frystyk 192: HTTRACE(PROT_TRACE, "Icon add.... PARENT => SRC=\"%s\" ALT=\"%s\"\n" _ url _
2.8 frystyk 193: alt ? alt : "");
2.27 frystyk 194: return YES;
2.1 frystyk 195: }
196:
197:
198: /*
2.27 frystyk 199: ** Add the directory icon.
2.1 frystyk 200: */
2.27 frystyk 201: PUBLIC BOOL HTIcon_addDir (const char * url, const char * prefix, char * alt)
2.1 frystyk 202: {
2.21 frystyk 203: if ((icon_dir = (HTIconNode *) HT_CALLOC(1,sizeof(HTIconNode))) == NULL)
204: HT_OUTOFMEM("HTAddBlankIcon");
2.27 frystyk 205: if (url) icon_dir->icon_url = prefixed(url, prefix);
2.1 frystyk 206: if (alt) StrAllocCopy(icon_dir->icon_alt, alt);
207: alt_resize(alt);
2.29 frystyk 208: HTTRACE(PROT_TRACE, "Icon add.... DIRECTORY => SRC=\"%s\" ALT=\"%s\"\n" _ url _
2.8 frystyk 209: alt ? alt : "");
2.27 frystyk 210: return YES;
2.1 frystyk 211: }
212:
2.27 frystyk 213: /*
214: ** Returns the icon corresponding to content_type or content_encoding.
215: ** If no match is found then use "unknown icon"
2.1 frystyk 216: */
2.27 frystyk 217: PUBLIC HTIconNode * HTIcon_find (HTFileMode mode,
218: HTFormat content_type,
219: HTEncoding content_encoding)
2.1 frystyk 220: {
221: if (!icon_unknown) icon_unknown = icon_blank;
2.15 frystyk 222: if (mode == HT_IS_FILE) {
2.26 eric 223: const char * ct = content_type ? HTAtom_name(content_type) : NULL;
224: const char * ce = content_encoding ? HTAtom_name(content_encoding) : NULL;
2.1 frystyk 225: HTList * cur = icons;
226: HTIconNode * node;
227:
228: while ((node = (HTIconNode*)HTList_nextObject(cur))) {
229: char * slash = strchr(node->type_templ,'/');
230: if ((ct && slash && match(node->type_templ,ct)) ||
2.20 frystyk 231: (ce && !slash && HTStrMatch(node->type_templ,ce))) {
2.1 frystyk 232: return node;
233: }
234: }
2.15 frystyk 235: } else if (mode == HT_IS_DIR) {
2.1 frystyk 236: return icon_dir ? icon_dir : icon_unknown;
2.15 frystyk 237: } else if (mode == HT_IS_BLANK) {
238: return icon_blank ? icon_blank : icon_unknown;
239: } else if (mode == HT_IS_PARENT) {
240: return icon_parent ? icon_parent : icon_unknown;
2.1 frystyk 241: }
242: return icon_unknown;
2.30 ! kahan 243: }
! 244:
! 245: PRIVATE void HTIconNode_delete (HTIconNode* pNode)
! 246: {
! 247: if (pNode) {
! 248: HT_FREE(pNode->icon_url);
! 249: HT_FREE(pNode->icon_alt);
! 250: HT_FREE(pNode->type_templ);
! 251: HT_FREE(pNode);
! 252: }
! 253: }
! 254: /*
! 255: ** cleans up all memory used by icons. Should be called by
! 256: ** HTLibTerminate() (but it isn't)
! 257: **
! 258: */
! 259: PUBLIC void HTIcon_deleteAll (void)
! 260: {
! 261: if(icons != NULL) {
! 262: HTList * iconList = icons;
! 263: HTIconNode * node;
! 264: while((node = (HTIconNode*)HTList_removeLastObject(iconList))) {
! 265: HTIconNode_delete(node);
! 266: }
! 267: /* delete the list as well */
! 268: HTList_delete(icons);
! 269: icons = NULL;
! 270: }
! 271: HTIconNode_delete(icon_unknown);
! 272: icon_unknown = NULL;
! 273: HTIconNode_delete(icon_blank);
! 274: icon_blank = NULL;
! 275: HTIconNode_delete(icon_parent);
! 276: icon_parent = NULL;
! 277: HTIconNode_delete(icon_dir);
! 278: icon_dir = NULL;
2.2 luotonen 279: }
Webmaster