summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorBehdad Esfahbod <behdad@behdad.org>2009-02-13 16:33:58 -0800
committerBehdad Esfahbod <behdad@behdad.org>2009-02-15 14:13:38 -0800
commit9d58d01c5c061c1fcfb3cca3a3a4622f9bbec727 (patch)
treecd7f99162f84bc2ed5b45b5d7c9a9b26da6ee180 /src
parentd62b85af21777582ad720efd9c319fde97b67d82 (diff)
[fcformat] Enumerate langsets like we do arrays of values
If one asks for a format like '%{[]elt{expr}}' and the first value for elt is a langset, we enumerate the langset languages in expr.
Diffstat (limited to 'src')
-rw-r--r--src/fcformat.c59
1 files changed, 47 insertions, 12 deletions
diff --git a/src/fcformat.c b/src/fcformat.c
index 5aa1977b..77c502d5 100644
--- a/src/fcformat.c
+++ b/src/fcformat.c
@@ -31,7 +31,6 @@
/*
* Some ideas for future syntax extensions:
*
- * - langset enumeration using same syntax as array enumeration
* - allow indexing subexprs using '%{[idx]elt1,elt2{subexpr}}'
* - conditional/filtering/deletion on binding (using '(w)'/'(s)'/'(=)' notation)
*/
@@ -540,6 +539,7 @@ interpret_array (FcFormatContext *c,
const FcChar8 *format_save;
int idx;
FcBool ret, done;
+ FcStrList *lang_strs;
if (!expect_char (c, '[') ||
!expect_char (c, ']'))
@@ -562,6 +562,22 @@ interpret_array (FcFormatContext *c,
}
while (consume_char (c, ','));
+ /* If we have one element and it's of type FcLangSet, we want
+ * to enumerate the languages in it. */
+ lang_strs = NULL;
+ if (os->nobject == 1)
+ {
+ FcLangSet *langset;
+ if (FcResultMatch ==
+ FcPatternGetLangSet (pat, os->objects[0], idx, &langset))
+ {
+ FcStrSet *ss;
+ if (!(ss = FcLangSetGetLangs (langset)) ||
+ !(lang_strs = FcStrListCreate (ss)))
+ goto bail0;
+ }
+ }
+
subpat = FcPatternDuplicate (pat);
if (!subpat)
goto bail0;
@@ -574,22 +590,36 @@ interpret_array (FcFormatContext *c,
done = FcTrue;
- for (i = 0; i < os->nobject; i++)
+ if (lang_strs)
{
- FcValue v;
-
- /* XXX this can be optimized by accessing valuelist linked lists
- * directly and remembering where we were. Most (all) value lists
- * in normal uses are pretty short though (language tags are
- * stored as a LangSet, not separate values.). */
- FcPatternDel (subpat, os->objects[i]);
- if (FcResultMatch ==
- FcPatternGet (pat, os->objects[i], idx, &v))
+ FcChar8 *lang;
+
+ FcPatternDel (subpat, os->objects[0]);
+ if ((lang = FcStrListNext (lang_strs)))
{
- FcPatternAdd (subpat, os->objects[i], v, FcFalse);
+ FcPatternAddString (subpat, os->objects[0], lang);
done = FcFalse;
}
}
+ else
+ {
+ for (i = 0; i < os->nobject; i++)
+ {
+ FcValue v;
+
+ /* XXX this can be optimized by accessing valuelist linked lists
+ * directly and remembering where we were. Most (all) value lists
+ * in normal uses are pretty short though (language tags are
+ * stored as a LangSet, not separate values.). */
+ FcPatternDel (subpat, os->objects[i]);
+ if (FcResultMatch ==
+ FcPatternGet (pat, os->objects[i], idx, &v))
+ {
+ FcPatternAdd (subpat, os->objects[i], v, FcFalse);
+ done = FcFalse;
+ }
+ }
+ }
if (!done)
{
@@ -602,9 +632,14 @@ interpret_array (FcFormatContext *c,
idx++;
} while (!done);
+ if (c->format == format_save)
+ skip_subexpr (c);
+
bail:
FcPatternDestroy (subpat);
bail0:
+ if (lang_strs)
+ FcStrListDone (lang_strs);
FcObjectSetDestroy (os);
return ret;