denemo-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Denemo-devel] Patch to read mudela (lilypond) files


From: Roy Rankin
Subject: [Denemo-devel] Patch to read mudela (lilypond) files
Date: Wed, 31 Jan 2007 20:23:14 +1100

I have the reading of mudela files working for many of the features
supported by denemo. I am sure there are still plenty of issues. I am
interested in any mudela files generated by denemo which are not read in
correctly.

Regards,
Roy Rankin

diff -urN -X xdiff ../denemo/ChangeLog ./ChangeLog
--- ../denemo/ChangeLog 2007-01-30 15:13:57.000000000 +1100
+++ ./ChangeLog 2007-01-31 19:44:13.000000000 +1100
@@ -1,3 +1,16 @@
+2007-01-31 <address@hidden>
+       * denemo_types.h: DenemoObjType PARTIAL added
+       * frogparser.y lyparser.y: PARTIAL renamed to avoid conflict
+       * calculatepositions.c: fix floating point exception
+       * scoreprops.c: allow edit of header properties for lily files
+       * exportmudela.c: allow export of lilyfiles, remove commented out code
+       * exportmudela.c: output \partial,  \lyricsto in staff block
+       * exportmudela.c: do not output \skip in lyrics
+       * file.c: allow I/O of mudela files
+       * lylexer.l lyparserfuncs.c lyparserfuncs.h lyparser.y: fixes to the
+         parsing of mudela files
+       * Makefile.am: add lylexer.l, lyparser.y to build
+
 2007-01-23 <address@hidden>
         * configure.in: indentation
         * configure.in: added HAVE_FILE_LOCKS macro
diff -urN -X
xdiff ../denemo/include/denemo/denemo_types.h ./include/denemo/denemo_types.h
--- ../denemo/include/denemo/denemo_types.h     2006-12-22
23:53:31.000000000 +1100
+++ ./include/denemo/denemo_types.h     2007-01-29 15:58:18.000000000 +1100
@@ -66,7 +66,8 @@
   GRACE_END,
   LYRIC,
   FIGURE,
-  FAKECHORD
+  FAKECHORD,
+  PARTIAL
 }DenemoObjType;
 
 /**
diff -urN -X
xdiff ../denemo/src/calculatepositions.c ./src/calculatepositions.c
--- ../denemo/src/calculatepositions.c  2007-01-22 08:49:16.000000000
+1100
+++ ./src/calculatepositions.c  2007-01-29 08:26:41.000000000 +1100
@@ -224,7 +224,7 @@
                {
                  curobj->x = *base_x + extra_advance
                    + ((starts_at_tick - *base_tick) * block_width
-                      / ticks_in_block);
+                      / (ticks_in_block ? ticks_in_block : 1));
                  non_chord_pixels = 0;
                }
              starts_at_tick = curobj->starttickofnextnote;
Binary files ../denemo/src/denemo and ./src/denemo differ
diff -urN -X xdiff ../denemo/src/exportmudela.c ./src/exportmudela.c
--- ../denemo/src/exportmudela.c        2007-01-30 15:14:10.000000000 +1100
+++ ./src/exportmudela.c        2007-01-31 19:38:23.000000000 +1100
@@ -598,34 +598,9 @@
 void
 exportmudela (gchar * thefilename, DenemoScore * si, gint dummy1, gint
dummy2)
 {
-  FILE *fp;
   GString *filename = g_string_new (thefilename);
-  if (si->lily_file == NULL)
-    {
-      g_string_free (filename, TRUE);
-      old_exportmudela (thefilename, si, dummy1, dummy2);
-    }
-  /* Append .ly onto the filename if necessary
-     if (strcmp (filename->str + filename->len - 3, ".ly"))
-     g_string_append (filename, ".ly");
-
-     Now open the file 
-     fp = fopen (filename->str, "w");
-     if (fp)
-     {
-     lily_write_out (fp, si->lily_file, TO_FILE);
-     #if 0
-
-     why ? ? ? fprintf (fp, "\n");
-     #endif
-
-     fclose (fp);
-     }
-     else
-     g_error ("Could not open file %s\n", filename->str);
-
-     g_string_free (filename, TRUE);
-   */
+  g_string_free (filename, TRUE);
+  old_exportmudela (thefilename, si, dummy1, dummy2);
 }
 
 
@@ -727,6 +702,7 @@
          else
            lyrics = g_string_append (lyrics, "__ ");
        }
+#if 0  // no skip in lyrics RRR
       else if (lyrics)
        {
 
@@ -738,6 +714,7 @@
            g_string_append_printf (lyrics, ".");
          lyrics = g_string_append (lyrics, " ");
        }
+#endif
       /* figured bass stuff */
       if (si && si->has_figures)
        output_figured_bass (si, &figures, pchord);
@@ -1072,6 +1049,19 @@
     case LYRIC:
     case FIGURE:
       break;
+
+    case PARTIAL:
+      empty_measure = FALSE;
+      pchord = (chord *) curobj->object;
+      duration = internaltomuduration (pchord->baseduration);
+      numdots = pchord->numdots;
+      ret = g_string_append (ret, "\\partial ");
+      g_string_append_printf (ret, "%d", duration);
+      for (j = 0; j < numdots; j++)
+        ret = g_string_append (ret, ".");
+      ret = g_string_append (ret, " ");
+      break;
+
     default:
       break;
     }
@@ -1198,7 +1188,8 @@
   objnode *curobjnode;
   DenemoObject *curobj;
   gint curmeasurenum;
-  gint i, last = 0, p;
+  gint i; 
+  gint last = 0;
 
   prevduration = 0;
   prevnumdots = -1;
@@ -1440,21 +1431,23 @@
        fprintf (fp, "\t\t\\FakeChordLine\n");
   
       if (curstaffstruct->voicenumber != 2)
-       fprintf (fp, "\t\t\\%s\n", curstaffstruct->lily_name->str);
-      else if (curstaffstruct->voicenumber ==
-              2 /*&& curstaffstruct->context == DENEMO_NONE */ )
-       fprintf (fp, "\t\t\\%s\n", curstaffstruct->lily_name->str);
-
-    }
-  if (lyricsstaffs)
-    {
-      GList *tmp;
-      for (tmp = lyricsstaffs; tmp; tmp = tmp->next)
        {
-         fprintf (fp, "\n\t\t \\lyricsto %s \\new Lyrics "
-                  "\\%sLyrics\n", (gchar *) tmp->data, (gchar *) tmp->data,
-                  (gchar *) tmp->data);
+         fprintf (fp, "\t\t\\%s\n", curstaffstruct->lily_name->str);
+         if (lyricsstaffs)
+           {
+               GList *tmp;
+               for (tmp = lyricsstaffs; tmp; tmp = tmp->next)
+                 {
+                   if (! strcmp (curstaffstruct->lily_name->str, (gchar *)
tmp->data))
+                   fprintf (fp, "\n\t\t \\lyricsto %s \\new Lyrics \\%sLyrics
\n", 
+                       (gchar *) tmp->data, (gchar *) tmp->data);
+                 }
+            }
        }
+      else if (curstaffstruct->voicenumber == 2
+               /*&& curstaffstruct->context == DENEMO_NONE */ )
+       fprintf (fp, "\t\t\\%s\n", curstaffstruct->lily_name->str);
+
     }
 
   if (si->has_figures)
@@ -1554,9 +1547,8 @@
          GList *tmp;
          for (tmp = lyricsstaffs; tmp; tmp = tmp->next)
            {
-             fprintf (fp, "\n\t\t \\lyricsto %s \\new Lyrics "
-                      "\\%sLyrics\n", (gchar *) tmp->data,
-                      (gchar *) tmp->data, (gchar *) tmp->data);
+             fprintf (fp, "\n\t\t \\lyricsto %s \\new Lyrics \\%sLyrics\n", 
+               (gchar *) tmp->data, (gchar *) tmp->data);
            }
 
        }
diff -urN -X xdiff ../denemo/src/file.c ./src/file.c
--- ../denemo/src/file.c        2007-01-30 15:14:12.000000000 +1100
+++ ./src/file.c        2007-01-30 15:14:27.000000000 +1100
@@ -65,7 +65,7 @@
 static struct FileFormatData supported_import_file_formats[] = {
   {"*.denemo", N_("Denemo XML format (*.denemo)"), ".denemo"},
   {"*.dnm", N_("Denemo XML format (*.dnm)"), ".dnm"},
-  //     {"*.ly", N_("Lilypond (formerly Mudela) (*.ly)"), ".ly"},
+  {"*.ly", N_("Lilypond (formerly Mudela) (*.ly)"), ".ly"},
   {"*.mid", N_("Midi (*.mid)"), ".mid"},
   {"*.midi", N_("Midi (*.midi)"), ".midi"}
 };
@@ -234,8 +234,8 @@
     result = importXML (filename, gui->si);
   else if (strcmp (filename + strlen (filename) - 4, ".dnm") == 0)
     result = importXML (filename, gui->si);
-//  else if (strcmp (filename + strlen (filename) - 3, ".ly") == 0)
-//    result = lyinput (filename, si);
+  else if (strcmp (filename + strlen (filename) - 3, ".ly") == 0)
+    result = lyinput (filename, gui);
   else if (strcmp (filename + strlen (filename) - 4, ".mid") == 0 ||
           strcmp (filename + strlen (filename) - 5, ".midi") == 0)
     result = importMidi (filename, gui);
@@ -676,15 +676,6 @@
                                 renderer, "text", COLUMN_NAME);
   gtk_box_pack_start (GTK_BOX (hbox), combobox, TRUE, TRUE, 0);
 
-  if (gui->si->lily_file)
-    {
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
-                         COLUMN_NAME, _(FORMAT_DESCRIPTION (MUDELA_FORMAT)),
-                         COLUMN_ID, MUDELA_FORMAT, -1);
-    }
-  else
-    {
       int i;
       for (i = 0; i < (int) G_N_ELEMENTS
(supported_export_file_formats); i++)
        {
@@ -694,7 +685,6 @@
                              supported_export_file_formats[i].description,
                              COLUMN_ID, i, -1);
        }
-    }
 
   gtk_tree_model_get_iter_first (GTK_TREE_MODEL (list_store), &iter);
   gtk_combo_box_set_active_iter (GTK_COMBO_BOX (combobox), &iter);
diff -urN -X xdiff ../denemo/src/frogparser.y ./src/frogparser.y
--- ../denemo/src/frogparser.y  2007-01-08 08:43:49.000000000 +1100
+++ ./src/frogparser.y  2007-01-13 21:42:29.000000000 +1100
@@ -95,7 +95,7 @@
 %token < string > CLEFTYPE
 %token < string > ORNAMENT
 %token < string > FULL
-%token < string > PARTIAL
+%token < string > PARTIAL_
 %token < string > MODE
 %token < string > BARTYPE
 %token < string > TEMPOTERM
@@ -648,7 +648,7 @@
 
 ;
 
-secondary:PARTIAL
+secondary:PARTIAL_
 {
 
 }
diff -urN -X xdiff ../denemo/src/lylexer.l ./src/lylexer.l
--- ../denemo/src/lylexer.l     2006-03-01 01:14:51.000000000 +1100
+++ ./src/lylexer.l     2007-01-30 08:53:33.000000000 +1100
@@ -41,6 +41,8 @@
 }
 #define RETURN(token) {lylval.generic.type = token;return token;}
 #define UNDO_YY_USER_ACTION  {input_text = lylval.generic.user_string;}
+#define YY_NO_UNPUT 1
+#define YY_NO_TOP_STATE 1
 
 /* discard the str stored in input_text by YY_USER_ACTION */
 static void remove_from_input (gchar *str);
@@ -53,7 +55,7 @@
 
 
 
-#define escaped_char(a) (a) /* FIXME */
+static char  escaped_char(char a);
 static void 
 scan_fraction (gchar *str, struct twoints *pt);
 
@@ -86,8 +88,6 @@
 
 static gboolean main_input_b_;
 
-static gboolean
-valid_version_b (char * s);
 
 #define start_quote()  \
        yy_push_state (quote);\
@@ -109,7 +109,6 @@
 
 %}
 
-
 %option yylineno
 %option noyywrap
 %option nodefault
@@ -151,13 +150,12 @@
 WHITE          [ \n\t\f\r]
 HORIZONTALWHITE                [ \t]
 BLACK          [^ \n\t\f\r]
-RESTNAME       [rs]
 NOTECOMMAND    \\{A}+
 LYRICS         ({AA}|{TEX})[^0-9 \t\n\f]*
 ESCAPED                [nt\\'"]
 EXTENDER       __
 HYPHEN         --
-IGNORE_BLOCK   "\\header"|"\\paper"|"\\midi"|"\\layout"
+IGNORE_BLOCK   "\\paper"|"\\layout"
 %%
 
 
@@ -188,21 +186,6 @@
   }
 }
 
-<INITIAL,chords,lyrics,notes,figures>\\version{WHITE}* {
-        /* treat version number as comment for now */
-       UNDO_YY_USER_ACTION;
-       yy_push_state (version);
-}
-<version>\"[^"]*\"     { /* got the version number */
-        /* treat version number as comment for now */
-       UNDO_YY_USER_ACTION;
-       pop_state ();
-}
-<version>.     {
-       pop_state ();
-       g_error ("No quoted string found after \\version");
-
-}
 <longcomment>{
        [^\%]*          |
        \%*[^}%]*       {
@@ -283,9 +266,12 @@
 <incl>\"[^"]*   { // backup rule
        parser_error ("Missing end quote", lylineno);
 }
-<chords,notes,figures>{RESTNAME}       {
+<chords,notes,figures>r        {
        RETURN (RESTNAME);
 }
+<chords,notes,figures>s        {
+       RETURN (SKIPNAME);
+}
 <chords,notes,figures>R                {
        RETURN (MULTI_MEASURE_REST);
 }
@@ -330,6 +316,14 @@
          }
 }
 
+<INITIAL,notes,lyrics>{
+        \<\<   {
+                return DOUBLE_ANGLE_OPEN;
+        }
+        \>\>   {
+                return DOUBLE_ANGLE_CLOSE;
+        }
+}
 
 <figures>{
        _       {
@@ -375,7 +369,7 @@
 }
 <quote>{
        \\{ESCAPED}     {
-               g_string_append_c (quoted_string, *escaped_char (yytext+1));
+               g_string_append_c (quoted_string, escaped_char (*(yytext+1)));
        }
        [^\\"]+ {
                g_string_append (quoted_string, yytext);
@@ -493,7 +487,7 @@
 }
 
 <INITIAL,lyrics,notes,figures>\\. {
-    char c= *yytext;
+    char c= *(yytext+1);
 
     switch (c) {
     case '>':
@@ -526,7 +520,7 @@
 
 %%
 void
-push_notes_state ()
+push_note_state ()
 {
   yy_push_state (notes);
 }
@@ -559,16 +553,16 @@
 int
 scan_escaped_word (gchar * str)
 {
-  nodeglist *sid;              /* a definition of an identifier already turned 
into
a 
-                                                               typed glist by 
the parser encountering an assignment */
+  nodeglist *sid;      /* a definition of an identifier already turned into
a 
+                       typed glist by the parser encountering an assignment */
   nodegstr *scm_str;
   int look = lookup_keyword (str);
   if (look != -1)
     {
-      RETURN (look);           /* this is many of the tokens eg /times and so 
on
*/
+      RETURN (look);   /* this is many of the tokens eg /times and so on
*/
     }
-  sid = lookup_identifier (str);       /* there follows all the things that
can have
-                                                                               
                been defined using the = syntax */
+  sid = lookup_identifier (str); /* there follows all the things that
can have
+                                       been defined using the = syntax */
   if (sid)
     {
       lylval.id.id  = sid->branch;
@@ -580,15 +574,15 @@
     {
       lylval.gstr.type = scm_str->type;
       lylval.gstr.gstr = g_string_new (scm_str->gstr->str);
-      return SCM_IDENTIFIER;
+      return scm_str->type;
     }
 
   if ((YYSTATE != notes) && (YYSTATE != chords))
     {
 #ifdef LATER
       /*      SCM pitch = scm_hashq_get_handle (pitchname_tab_, str); 
-                                 some sort of lookup of pitchnames to yield a 
pitch object to be 
-                                 stored in lylval */
+         some sort of lookup of pitchnames to yield a pitch object to be 
+         stored in lylval */
 
       if (gh_pair_p (pitch))
        {
@@ -606,11 +600,13 @@
 }
 
 /* scan_bare_word takes a string and if in chords or notes it tries to 
-       interpret the word as a notename of one sort or another eg
NOTENAME_PITCH 
-       etc. It uses tables for notes pitchname_tab_ and  chordmodifier_tab_
which I
-       will need to create similar things for (ultimately they can be changed
by 
-       the include file). My lylval should have a field for the str and
another for
-       the pitchname in some binary form ready to be attached to a
mudelaobject...
+       interpret the word as a notename of one sort or another eg 
+       NOTENAME_PITCH etc. It uses tables for notes pitchname_tab_ 
+       and  chordmodifier_tab_ which I will need to create similar 
+       things for (ultimately they can be changed by the include file). 
+       My lylval should have a field for the str and another for
+       the pitchname in some binary form ready to be attached to a 
+       mudelaobject...
        Otherwise it returns a STRING_ token. */
 int
 scan_bare_word (gchar * str)
@@ -622,7 +618,7 @@
        {
          lylval.t.t.a = *str - 'a';
          lylval.t.t.b = lookup_enshift (str + 1);
-         RETURN ((YYSTATE == notes) ? NOTENAME_PITCH : TONICNAME_PITCH);
+         RETURN ((YYSTATE != chords) ? NOTENAME_PITCH : TONICNAME_PITCH);
        }
     }
 #ifdef LATER
@@ -676,28 +672,6 @@
 Lilypond_version oldest_version ("1.3.146");
  */
 
-static gboolean
-valid_version_b (char *s)
-{
-#ifdef LATER
-  Lilypond_version current (MAJOR_VERSION "." MINOR_VERSION "."
PATCH_LEVEL);
-  Lilypond_version ver (s);
-  if (!((ver >= oldest_version) && (ver <= current)))
-    {
-      non_fatal_error (_f
-                      ("Incorrect lilypond version: %s (%s, %s)",
-                       ver.string (), oldest_version.string (),
-                       current.string ()));
-      non_fatal_error (_
-                      ("Consider updating the input with the convert-ly 
script"));
-      return FALSE;
-    }
-#endif
-  return TRUE;
-}
-
-
-
 
 
 static void
@@ -751,3 +725,22 @@
     return 2;
   return BAD_ENSHIFT;
 }
+
+static char
+escaped_char (char c)
+{
+  switch (c)
+    {
+    case 'n':
+      return '\n';
+    case 't':
+      return '\t';
+    case '\'':
+    case '\"':
+    case '\\':
+      return c;
+    }
+  return 0;
+}
+
+
diff -urN -X xdiff ../denemo/src/lyparserfuncs.c ./src/lyparserfuncs.c
--- ../denemo/src/lyparserfuncs.c       2006-08-07 04:11:09.000000000 +1000
+++ ./src/lyparserfuncs.c       2007-01-31 19:17:02.000000000 +1100
@@ -4,7 +4,7 @@
 
 /* For Denemo, a gtk+ frontend to GNU Lilypond
  * (c) 2000-2005 Matthew Hiller */
-/*#define DEBUG 1*/
+//#define DEBUG 1
 #include "chordops.h"
 #include <denemo/denemo.h>
 #include "lyparserfuncs.h"
@@ -12,7 +12,7 @@
 #include "processstaffname.h"
 #include "utils.h"
 #include <string.h>
-/*#include "lyparser.h"*/
+#include "lyparser.h"
 #include "contexts.h"
 #include "staffops.h"
 #include "calculatepositions.h"
@@ -21,12 +21,14 @@
 #include "commandfuncs.h"
 #include "articulations.h"
 
+ crescendo_state cresc_state;
+
 gboolean g_string_equal (const GString * v, const GString * v2);
 
 /* RECURSIVE return the first object in object list 
    CUROBJ of type thetype before any CHORD type,
    following branches made for references to identifiers 
-*
+*/
 static DenemoObject *
 first_node_context (objnode * curobj, gint thetype)
 {
@@ -47,52 +49,84 @@
   return NULL;
 }
 
-/* return the first object in measure curmeasure of type thetype before
any CHORD type *
+/* delete obj from curmeasure if it occurs before the first chord */
+static void
+delete_context(measurenode * curmeasure, DenemoObject * obj)
+{
+  objnode *curobj = (objnode *) curmeasure->data;
+ while (curobj)
+    {
+      if ((DenemoObject *) curobj->data == obj)
+      {
+        curmeasure->data = g_list_remove_link ((objnode *)
curmeasure->data,
+                                          curobj);
+       freeobject ((DenemoObject *) curobj->data);
+        g_list_free_1 (curobj);
+        return;
+      }
+      if (((DenemoObject *) curobj->data)->type == CHORD)
+        return ;
+      curobj = curobj->next;
+    }
+}
+/* return the first object in measure curmeasure of type thetype before
any CHORD type */
 static DenemoObject *
 first_context (measurenode * curmeasure, gint thetype)
 {
   objnode *curobj = (objnode *) curmeasure->data;
   return first_node_context (curobj, thetype);
 }
-*
+
+/* Denemo holds initial staff properties in the staff structure rather
+   than nodes, so transfer node data to staff structure and delete
+   the nodes. If we do not do this, objects like initial key, clef, and
time
+   signatures are shown twice in denemo */
 static void
 set_initial_staffcontext (DenemoStaff * curstaffstruct, DenemoScore
*si)
 {
   measurenode *firstmeasure = curstaffstruct->measures;
   DenemoObject *obj;
+  curstaffstruct->context = DENEMO_NONE;
   g_assert (firstmeasure);
-  if ((obj = first_context (firstmeasure, CLEF))
-      || (obj = first_context (firstmeasure, INITIAL_CLEF)))
+  if ((obj = first_context (firstmeasure, CLEF)))
     {
-      * DENEMO treats CLEF as clef change, so make the initial clef
-         a different type 
-      obj->type = (DenemoObjType) INITIAL_CLEF;
-      setpixelmin (obj);        different object different width 
       curstaffstruct->sclef = ((clef *) obj->object)->type;
       find_leftmost_staffcontext (curstaffstruct, si);
       fixnoteheights (curstaffstruct);
-        find_xes_in_all_measures (si); core dumps 
+      delete_context (firstmeasure, obj);
     }
-  if ((obj = first_context (firstmeasure, KEYSIG))
-      || (obj = first_context (firstmeasure, INITIAL_KEYSIG)))
+  if ((obj = first_context (firstmeasure, KEYSIG)))
     {
-      obj->type = (DenemoObjType) INITIAL_KEYSIG;
-      setpixelmin (obj);
       curstaffstruct->skey = ((keysig *) obj->object)->number;
       initkeyaccs (curstaffstruct->skeyaccs, curstaffstruct->skey);
+      delete_context (firstmeasure, obj);
     }
-  if ((obj = first_context (firstmeasure, TIMESIG))
-      || (obj = first_context (firstmeasure, INITIAL_TIMESIG)))
+  if ((obj = first_context (firstmeasure, TIMESIG)))
     {
-      obj->type = (DenemoObjType) INITIAL_TIMESIG;
-      setpixelmin (obj);
       curstaffstruct->stime1 = ((timesig *) obj->object)->time1;
       curstaffstruct->stime2 = ((timesig *) obj->object)->time2;
+      delete_context (firstmeasure, obj);
     }
+  if ((obj = first_context (firstmeasure, SET )))
+  {
+       char *pt  = strstr(obj->user_string, "Staff.midiInstrument");
+       if ( pt != NULL)
+       {
+           char tmp[40];
+           int i;
+
+           pt += 20;
+           while(*pt && *pt != '"')pt++;
+           if (*pt) pt++;
+           for(i=0; *pt && *pt != '"' && i < 39; i++)
+               tmp[i] = *pt++;
+           tmp[i] = 0;
+           curstaffstruct->midi_instrument = g_string_new(tmp);
+           delete_context (firstmeasure, obj);
+       }
+  }
 }
-*/
 
-/*
 void
 set_initial_staffcontexts (DenemoScore *si)
 {
@@ -105,7 +139,7 @@
     }
 }
 
-*/
+
 void
 setstaffname (DenemoScore * si, gchar * str)
 {
@@ -263,45 +297,9 @@
 void
 set_tone_option (DenemoObject * curmudelaobj, gchar * option)
 {
-
-  if (!strcmp (option, "fermata"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (FERMATA,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-  else if (!strcmp (option, "trill"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (TRILL,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-
-  else if (!strcmp (option, "turn"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (TURN,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-
-  else if (!strcmp (option, "mordent"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (MORDENT,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-  else if (!strcmp (option, "accent"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (D_ACCENT,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-  else if (!strcmp (option, "staccato"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (STACCATO,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-  else if (!strcmp (option, "staccatissimo"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (STACCATISSIMO,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-  else if (!strcmp (option, "tenuto"))
-    ((chord *) curmudelaobj->object)->ornamentlist =
-      insert_ornament_list (TENUTO,
-                           ((chord *) curmudelaobj->object)->ornamentlist);
-
+  set_articulation (option, curmudelaobj);
 }
 
-/*
 typedef struct Keyword_ent
 {
   gchar *str;
@@ -321,10 +319,11 @@
   {"alternative", ALTERNATIVE},
   {"bar", BAR},
   {"breathe", BREATHE},
+  {"break", BREAK},
   {"char", CHAR_T},
   {"chordmodifiers", CHORDMODIFIERS},
   {"chords", CHORDS},
-  {"clef", CLEF_},              underscore added for denemo name clash 
+  {"clef", CLEF_},             /* underscore added for denemo name clash */
   {"cm", CM_T},
   {"consists", CONSISTS},
   {"consistsend", CONSISTSEND},
@@ -339,12 +338,16 @@
   {"glissando", GLISSANDO},
   {"header", HEADER},
   {"in", IN_T},
-  {"lyrics", LYRICS},
   {"key", KEY},
   {"mark", MARK},
+  {"new", NEWCONTEXT},
   {"pitch", PITCH},
   {"time", TIME_T},
   {"times", TIMES},
+  {"layout", LAYOUT},
+  {"lyricmode", LYRICMODE},
+  {"lyrics", LYRICS},
+  {"lyricsto", LYRICSTO},
   {"midi", MIDI},
   {"mm", MM_T},
   {"name", NAME},
@@ -355,7 +358,7 @@
   {"set", SET},
   {"rest", REST},
   {"revert", REVERT},
-  {"partial", PARTIAL},
+  {"partial", PARTIAL_},
   {"paper", PAPER},
   {"penalty", PENALTY},
   {"property", PROPERTY},
@@ -374,10 +377,18 @@
   {"transpose", TRANSPOSE},
   {"type", TYPE},
   {"unset", UNSET},
-  {"layout", LAYOUT},
+  { "version", LILYVERSION},
   {0, 0}
 };
 
+static Keyword_ent the_par_tab[] = {
+  {"MUSIC_IDENTIFIER", MUSIC_IDENTIFIER},
+  {"voicecontext", voicecontext},
+  {"staffcontext", staffcontext},
+  {"endcontext", endcontext},
+  { NULL, 0}
+};
+
 gint
 lookup_keyword (gchar * str)
 {
@@ -385,15 +396,32 @@
   for (i = 0; the_key_tab[i].str; i++)
     {
       if (!strcmp (the_key_tab[i].str, str))
-       return the_key_tab[i].type;     very inefficient! 
+       return the_key_tab[i].type;     /*very inefficient! */
     }
 
 
 
   return -1;
 }
+gchar *
+lookup_type (gint type)
+{
+  int i;
+  for (i = 0; the_key_tab[i].str; i++)
+    {
+      if (the_key_tab[i].type == type)
+       return the_key_tab[i].str;      /*very inefficient! */
+    }
+  for (i = 0; the_par_tab[i].str; i++)
+    {
+      if (the_par_tab[i].type == type)
+       return the_par_tab[i].str;      /*very inefficient! */
+    }
+
+  return "Unknown";
+}
+
 
-*/
 
 /* sets si->currentstaff to the first staff in si->thescore with
lily_name 
  *  NAME or NULL if none.
@@ -404,35 +432,57 @@
 {
   DenemoStaff *curstaffstruct;
   if (si->thescore)
+  {
     for (si->currentstaff = si->thescore, si->currentstaffnum = 0;
         si->currentstaff;
         si->currentstaff = si->currentstaff->next, si->currentstaffnum++)
       {
        curstaffstruct = (DenemoStaff *) (si->currentstaff->data);
        if (g_string_equal (curstaffstruct->staff_name, name))
+       {
          return;
+       }
       }
+  }
   si->currentstaff = NULL;
   si->currentstaffnum = g_list_length (si->thescore);  /*set to insert
at end */
 }
 
+static GList *staffctx = NULL, *voicectx = NULL, *lyricsctx =
+  NULL, *figuresctx = NULL;
+
+static void
+anewstaff (DenemoScore * si, GString * staffname, GString * voicename);
 /* set si->currentstaff to the insertion point for voice named NAME in
staff 
  * STAFFCTX, return TRUE if voice already exists else FALSE. 
  * sets si->currentstaffnum to correspond 
  */
 static gboolean
-findvoice (GString * name, GList * staffctx, DenemoScore * si)
+findvoice (GString *name, DenemoScore * si)
 {
   DenemoStaff *curstaffstruct;
   DenemoStaff *staffctxstruct;
+  if (!si->thescore || !staffctx)
+  {
+       si->currentstaff = NULL;
+       si->currentstaffnum = g_list_length (si->thescore);     /*set to insert
at end */
+       si->currentstaff = si->thescore;
+       anewstaff (si, g_string_new ("staff"), name);
+       si->currentmeasurenum = 1;
+       staffctx = si->currentstaff = g_list_last (si->thescore);
+       set_denemo_name (name, staffstruct (staffctx)->denemo_name);
+  }
   if (si->thescore)
+  {
     if (staffctx)
-      {
+    {
        staffctxstruct = (DenemoStaff *) (staffctx->data);
        for (si->currentstaff = si->thescore, si->currentstaffnum = 1;
             si->currentstaff && (staffctx != si->currentstaff);
             si->currentstaff = si->currentstaff->next, si->currentstaffnum++)
          /* move to primary voice in current staff */ ;
+    
+
        curstaffstruct = (DenemoStaff *) (si->currentstaff->data);
        if (curstaffstruct->lily_name->len == 0)
          {                     /* no voice here yet */
@@ -453,8 +503,8 @@
        si->currentstaff = si->currentstaff->prev, si->currentstaffnum--;
        /* just come off this staff, go back one */
        return FALSE;
-      }
-  /* FIXME these cases - no staffs or no staff context */
+     }
+  }
   si->currentstaff = NULL;
   si->currentstaffnum = 0;
   return FALSE;
@@ -463,8 +513,7 @@
 static void
 anewstaff (DenemoScore * si, GString * staffname, GString * voicename)
 {
-  DenemoStaff *thestaffstruct =
-    (DenemoStaff *) g_malloc0 (sizeof (DenemoStaff));
+  DenemoStaff *thestaffstruct = (DenemoStaff *) g_malloc0 (sizeof
(DenemoStaff));
 
   thestaffstruct->sclef = DENEMO_TREBLE_CLEF;
   thestaffstruct->stime1 = 4;
@@ -474,6 +523,8 @@
   thestaffstruct->denemo_name = g_string_new ("");
   thestaffstruct->lily_name = voicename;
   thestaffstruct->midi_instrument = g_string_new ("acoustic grand");
+  thestaffstruct->voicenumber = 1;
+  thestaffstruct->nummeasures = 1;
   if (si->thescore)
     {
       si->thescore =
@@ -490,7 +541,7 @@
 }
 
 /* traverse G a GList of object nodes returning the first of type T or
-NULL if none 
+NULL if none */
 GList *
 findtok (GList * g, int t)
 {
@@ -498,21 +549,21 @@
     g = g->next;
   return g;
 }
-*/
+
 /* put separate chords into a tones list of a chord and return that,
  * amalgamating the user_strings 
- *
+ */
 static DenemoObject *
 generate_chord (GList * chordnode)
 {
   GList *g;
   GList *firstchord = findtok (chordnode, CHORD);
 
-  gchar *str;                  * collect up the user strings here *
+  gchar *str;                  /* collect up the user strings here */
   if (firstchord == NULL)
     {
       g_warning ("<> without any notes");
-      return (DenemoObject *) chordnode->data; * FIXME return
everything *
+      return (DenemoObject *) chordnode->data; /* FIXME return
everything */
     }
 
   for (str = NULL, g = chordnode; g; g = g->next)
@@ -534,11 +585,10 @@
                   ((note
                     *) (((chord *) (((DenemoObject *) g->data)->object))->
                         tones->data))->enshift, 0);
-       }                       * FIXME memory leak *
+       }                       /* FIXME memory leak */
     }
   return (DenemoObject *) firstchord->data;
 }
-*/
 
 /* RECURSIVE: generate_chords_and_sequentials()
  * called within a SEQUENTIAL it detects <> and { } music.
@@ -549,667 +599,956 @@
  * Note we don't cope with new contexts being created...
  */
 
-// static int create_score (DenemoScore * si, GList * top);
-// 
-// static void
-// generate_chords_and_sequentials (DenemoScore * si, GList * g)
-// {
-//   GList *chordnode;
-// 
-//   for (chordnode = br (g); chordnode; chordnode = chordnode->next)
-//     {
-//       if (ntype (chordnode) == SIMULTANEOUS)
-//      {
-//        gchar *str = u_str (chordnode);
-//        gchar *str2 = u_post_str (chordnode);
-//        chordnode->data = generate_chord (br (chordnode));
-//        u_str (chordnode) =
-//          g_strconcat (str, u_str (chordnode), str2, NULL);
-//        /* FIXME memory leak */
-//      }
-//       else if (ntype (chordnode) == SEQUENTIAL)
-//      {
-//        /*create a text node for the u_str, one for the u_post_str
and 
-//           in between link in the create_score(br(chordnode) */
-//        GList *temp = br (chordnode);
-//        generate_chords_and_sequentials (si, chordnode);
-//        u_str (temp) = g_strconcat (u_str (chordnode), u_str (temp),
NULL);
-//        (chordnode->prev)->next = NULL;
-//        g_list_concat (chordnode->prev, temp);
-//        temp = g_list_last (temp);
-//        u_str (temp) =
-//          g_strconcat (u_str (temp), u_post_str (chordnode), NULL);
-//        chordnode->prev = NULL;
-//        g_list_concat (temp, chordnode->next);
-//        /* FIXME memory leak of chordnode itself */
-//      }
-//     }
-// }
-// 
-// 
-// 
-// /* RECURSIVE: perform the guts of end_of_first_measure() qv, going
inside
-//    MUSIC_IDENTIFIERS - assume such a thing does not cross a tuplet
or grace */
-// static GList *
-// recursive_end_of_first_measure (GList * theobjs, gint * ptime1, gint
* ptime2,
-//                              gint * pticks_so_far, gint *
ptickspermeasure,
-//                              gint * pnumerator, gint * pdenominator)
-// {
-// 
-//   objnode *curobjnode;
-//   DenemoObject *theobj;
-//   gint basic_ticks_in_tuplet_group = 0;
-//   gint basic_ticks_in_grace_group = 0;
-//   gboolean in_tuplet = FALSE;
-//   gboolean in_grace = FALSE;
-//   for (curobjnode = theobjs; curobjnode; curobjnode =
curobjnode->next)
-//     {
-//       theobj = (DenemoObject *) curobjnode->data;
-//       theobj->starttick =
-//      *pticks_so_far + (basic_ticks_in_tuplet_group * *pnumerator
-//                        / *pdenominator) +
basic_ticks_in_grace_group;
-// 
-//       switch (theobj->type)
-//      {
-//      case PARTIAL:
-//      case CHORD:
-// 
-//        if (in_tuplet)
-//          {
-//            set_tuplefied_numticks (theobj, *pnumerator,
*pdenominator);
-//            basic_ticks_in_tuplet_group += theobj->basic_durinticks;
-//          }
-//        else if (in_grace)
-//          {
-//            set_grace_numticks (theobj, 8);
-//            basic_ticks_in_grace_group += theobj->basic_durinticks;
-//          }
-//        else
-//          {
-//            set_tuplefied_numticks (theobj, 1, 1);
-//            set_grace_numticks (theobj, 1);
-//            if (theobj->type == PARTIAL)
-//              {
-//                theobj->durinticks = *ptickspermeasure -
theobj->durinticks;
-//                /* FIXME need to handle the FRACTION multiplier which
is not 
-//                   being passed through at the moment */
-//              }
-//            *pticks_so_far += theobj->durinticks;
-//          }
-//        break;
-// 
-//      case TUPOPEN:
-// 
-//        in_tuplet = TRUE;
-//        *pnumerator = ((tupopen *) theobj->object)->numerator;
-//        *pdenominator = ((tupopen *) theobj->object)->denominator;
-//        basic_ticks_in_tuplet_group = 0;      /* Probably gratuitous
*/
-//        break;
-//      case TUPCLOSE:
-// 
-//        in_tuplet = FALSE;
-//        *pticks_so_far += ((basic_ticks_in_tuplet_group *
*pnumerator)
-//                           / *pdenominator);
-//        *pnumerator = 1;
-//        *pdenominator = 1;
-//        basic_ticks_in_tuplet_group = 0;
-//        break;
-//      case GRACE_START:
-// 
-//        in_grace = TRUE;
-//        basic_ticks_in_grace_group = 0;
-//        break;
-//      case GRACE_END:
-// 
-//        in_grace = FALSE;
-//        /*      *pticks_so_far += basic_ticks_in_grace_group; */
-//        basic_ticks_in_grace_group = 0;
-//        break;
-//      case INITIAL_TIMESIG:
-//      case TIMESIG:
-//        *ptime1 = ((timesig *) theobj->object)->time1;
-//        *ptime2 = ((timesig *) theobj->object)->time2;
-//        *ptickspermeasure = *ptime1 * WHOLE_NUMTICKS / *ptime2;
-//        break;
-//      case MUSIC_IDENTIFIER:
-//        {
-//          GList *ret =
-//            recursive_end_of_first_measure ((((nodeid *)
(curobjnode)->
-//                                              data)->id), ptime1,
ptime2,
-//                                            pticks_so_far,
ptickspermeasure,
-//                                            pnumerator,
pdenominator);
-//          if (ret)
-//            {
-//              g_warning ("Measure finishes inside a music_identifier
\n");
-//              return ret;
-//                   /** bar finished inside the MUSIC_IDENTIFIER */
-//            }
-//        }
-//        break;
-//      default:
-//        break;
-//      }
-// 
-//       theobj->starttickofnextnote =
-//      *pticks_so_far + (basic_ticks_in_tuplet_group * *pnumerator
-//                        / *pdenominator) +
basic_ticks_in_grace_group;
-//       if (*pticks_so_far >= *ptickspermeasure)
-//      break;
-//     }
-//   return curobjnode;
-// }
-// 
-// /* return the node in g at which one measure is complete in terms
-//    of ticks. On entering, assume timesig of (*ptime1) / (*ptime2),
any
-//    change in the timesig changes these.
-//    If end of measure, or incomplete measure return NULL
-//    This function has been ripped off of settickvalsinmeasure() in
-//    measureops.cpp, it side-effects the ticks fields of the objs in
-//    the list, in the same manner as will that function when called.
-// */
-// static GList *
-// end_of_first_measure (GList * theobjs, gint * ptime1, gint * ptime2)
-// {
-//   gint numerator = 1, denominator = 1;       /* varies if in tuplet
etc */
-//   gint ticks_so_far = 0;
-//   gint tickspermeasure = *ptime1 * WHOLE_NUMTICKS / *ptime2;
-//   return recursive_end_of_first_measure (theobjs, ptime1, ptime2,
-//                                       &ticks_so_far,
&tickspermeasure,
-//                                       &numerator, &denominator);
-// 
-// 
-// }
-// 
-// /*  attach the measures in BRANCH to the MEASURES_LIST, by counting
ticks 
-//  * return the measures list built up */
-// static GList *
-// break_into_measures (GList * branch, GList * measures_list)
-// {
-//   GList *barline;
-//   GList *rest;
-//   gint time1 = 4, time2 = 4; /*default timesig */
-//   barline = end_of_first_measure (branch, &time1, &time2);
-//   if (barline)
-//     {
-//       rest = barline->next;
-//       if (rest)
-//      rest->prev = NULL;
-//       barline->next = NULL;
-//     }
-//   else
-//     rest = NULL;
-//   measures_list = g_list_append (measures_list, branch);
-//   while (rest)
-//     {
-//       barline = end_of_first_measure (rest, &time1, &time2);
-//       if (barline)
-//      {
-//        measures_list = g_list_append (measures_list, rest);
-//        rest = barline->next;
-//        if (rest)
-//          rest->prev = NULL;
-//        barline->next = NULL;
-//      }
-//       else
-//      {
-//        measures_list = g_list_append (measures_list, rest);
-//        rest = NULL;
-// 
-//      }
-//     }
-//   return measures_list;
-// }
-// 
-// static GList *staffctx = NULL, *voicectx = NULL, *lyricsctx =
-//   NULL, *figuresctx = NULL;
-// 
-// /* create_score: Recursively traverse the GList TOP which represents
a 
-//    score block of the input lily file. Create denemo structures to
enable 
-//    it to be edited graphically
-// */
-// static int
-// create_score (DenemoScore * si, GList * top)
-// {
-//   GList *g;
-// 
-//   DenemoStaff *curstaffstruct;
-// #if DEBUG
-//   g_print
-//     ("The parse tree from this node downwards looks"
-//      " like this\n*************************************\n");
-//   for (g = top; g; g = g->next)
-//     {
-//       g_print ("node type = %d string = %s\n",
-//             ((nodegeneric *) g->data)->type,
-//             ((nodegeneric *) g->data)->user_string);
-//     }
-//   g_print ("\n*************************************\n");
-// #endif
-// 
-//   for (g = top; g; (g = g->next))
-//     {
-// #if DEBUG
-//       g_print ("Handling: node type = %d string = %s\n",
-//             ((nodegeneric *) g->data)->type,
-//             ((nodegeneric *) g->data)->user_string);
-// #endif
-//       switch (ntype (g))
-//      {
-//      case NOTES:
-// #if DEBUG
-//        g_print ("Found notes\n");
-// #endif
-//        break;
-//      case figuredbasscontext:
-//      case staffcontext:
-//        findstaff (gstr (g), si);     /*sets si->currentstaffnum */
-//        staffctx = si->currentstaff;
-//        if (!staffctx)
-//          {
-//            si->currentstaff = si->thescore;
-//            anewstaff (si, gstr (g), g_string_new (""));
-//            staffctx = si->currentstaff = g_list_last (si->thescore);
-//            staffstruct (staffctx)->voicenumber = 1;
-//          }
-//        si->currentprimarystaff = staffctx;
-//        if (ntype (g) == figuredbasscontext)
-//          {
-//            staff_info *staffs =
-//              (staff_info *) g_malloc0 (sizeof (staff_info));
-//            if (staffctx->prev == NULL)
-//              {
-//                parser_error ("Figured Bass not preceded by a bass
staff ",
-//                              0);
-//                return -1;
-//              }
-//            staffs->main_staff = (DenemoStaff *)
(staffctx->prev->data);
-//            staffs->related_staff = (DenemoStaff *) (staffctx->data);
-//            si->has_figures = staffs;
-//            ((DenemoStaff *) (staffctx->data))->no_of_lines = 0;
-//          }
-//        break;
-// 
-//      case voicecontext:
-// 
-//        if (!findvoice (gstr (g), staffctx, si))
-//          {
-//            anewstaff (si, staffstruct (staffctx)->staff_name, gstr
(g));
-//            voicectx = si->currentstaff;
-//            set_denemo_name (gstr (g), staffstruct
(voicectx)->denemo_name);
-//            staffstruct (voicectx)->voicenumber = 2;
-//          }
-//        voicectx = si->currentstaff;
-//        break;
-// 
-//      case endcontext:
-//        if (voicectx)
-//          {
-//            voicectx = NULL;
-//          }
-//        else
-//          staffctx = NULL;
-//        break;
-//      case MUSIC_IDENTIFIER:
-// #define id(g) (((nodeid*)(g)->data)->id)
-//        if (create_score (si, id (g)))
-//          return -1;
-//        break;
-//      case SIMULTANEOUS:
-//        if (create_score (si, br (g)))
-//          return -1;
-//        break;
-// 
-//      case SCORE:
-//        parser_error ("Score block inside a score block", 0);
-//        return -1;
-//        break;
-// 
-//      case DENEMO_MEASURES:
-//      case SEQUENTIAL:
-//        /* first find out if we have voice and staff contexts,
-//           if not create use/create
-//           default staff structures */
-//        if (!staffctx)
-//          {                   /* use/create the first staff structure
in si->thescore */
-//            if (si->thescore)
-//              {
-//                /* if we have a named voice context create a staff
context 
-//                   for it otherwise insert it as a voice in the first
staff 
-//                 */
-//                staffctx = voicectx = g_list_last (si->thescore);
-//              }
-//            else
-//              {
-//                anewstaff (si, g_string_new ("dummyname"),
-//                           g_string_new ("dummyname"));
-//                staffctx = voicectx = si->currentstaff;
-//              }
-//          }
-//        else
-//          {                   /* there is a staff context */
-//            if (!voicectx)
-//              voicectx = staffctx;
-//          }
-//        si->currentstaff = voicectx;
-//        curstaffstruct = staffstruct (voicectx);
-//        if (ntype (g) == SEQUENTIAL)
-//          {
-//            generate_chords_and_sequentials (si, g);
-// 
-//            curstaffstruct->measures =
-//              break_into_measures (br (g), curstaffstruct->measures);
-//            br (g) = (GList *) & (curstaffstruct->measures);
-//            /* nasty - we store the address
-//               of the GList* pointer. This is so that if
-//               editing in denemo adds a new bar at the beginning we
-//               will not find ourselves pointing to the second bar.
Or,
-//               worse if the first bar got deleted. We are not yet
tackling 
-//               the case where the staff gets deleted. We should
probably 
-//               store the name and prevent that
-//               being changed uncontrollably */
-//            ntype (g) = DENEMO_MEASURES;
-//          }
-//        else
-//          {                   /* these measures are already in
another staff */
-//            curstaffstruct->measures = *(measurenode **) br (g);
-//            curstaffstruct->is_parasite = (measurenode **) br (g);
-//          }
-//        break;
-// 
-// 
-//      default:
-//        break;
-//      }
-//     }
-//   return 0;
-// 
-// }
-// 
-// int
-// create_score_from_lily (DenemoScore * si, GList * top)
-// {
-//   staffctx = NULL;
-//   voicectx = NULL;
-//   lyricsctx = NULL;
-//   figuresctx = NULL;
-//   return create_score (si, top);
-// }
-// 
-// 
-// /* this function seems to be missing from the glib library, 
-//    although in the headers */
-// gboolean
-// g_string_equal (const GString * v, const GString * v2)
-// {
-//   if ((!v) || (!v2) || (v->len != v2->len))
-//     return FALSE;
-//   return !strcmp (v->str, v2->str);  /* not general case of embedded
0 bytes */
-// }
-// 
-// 
-// 
-// /***************** functions for managing display of lily text
***************/
-// 
-// static void
-// string_edited (GtkTextBuffer * buffer, gpointer data)
-// {
-//   GtkTextIter start, end;
-//   gchar *text;
-//   DenemoScore *si = (DenemoScore *) data;
-//   gtk_text_buffer_get_bounds (buffer, &start, &end);
-//   text = gtk_text_iter_get_text (&start, &end);
-//   if (si->curlilynode == NULL)
-//     {
-//       g_warning ("Attempt to edit nonexistent node - ignored\n");
-//       return;
-//     }
-//   if (u_str (si->curlilynode))
-//     g_free (u_str (si->curlilynode));
-//   /* else big memory leak - check all lilynodes 
-//      xsuser_strings are mallocced strings  */
-//   u_str (si->curlilynode) = text;
-// }
-// 
-// 
-// void
-// lily_text_change (DenemoGUI * gui)
-// {
-//   static gboolean text_is_readonly = FALSE;
-//   g_signal_handler_block (G_OBJECT (gui->textbuffer), gui->sigid);
-//   if (ntype (gui->si->curlilynode) == DENEMO_MEASURES)
-//     {
-//       gtk_widget_hide (gui->textview);
-//       gtk_widget_show (gui->musicdatabutton);
-//       text_is_readonly = TRUE;
-//     }
-//   else
-//     {
-//       if (text_is_readonly)
-//      {
-//        gtk_widget_show (gui->textview);
-//        gtk_widget_hide (gui->musicdatabutton);
-//      }
-//       text_is_readonly = FALSE;
-//       if (ntype (gui->si->curlilynode) == endcontext)
-//      gtk_text_buffer_set_text (gui->textbuffer,
-//                                g_strdup ("<<Music Data End>>"), -1);
-//       if (!u_str (gui->si->curlilynode))
-//      u_str (gui->si->curlilynode) = generate_lily
(gui->si->curlilynode);
-//       gtk_text_buffer_set_text (gui->textbuffer, u_str
(gui->si->curlilynode), -1);
-// 
-//     }
-// 
-//   g_signal_handler_unblock (G_OBJECT (gui->textbuffer), gui->sigid);
-// }
-// 
-// 
-// void
-// set_text_node (GtkWidget * button, DenemoGUI* gui)
-// {
-//   /* FIXME: the next line can coredump when you have multiple score
blocks
-//      and you have destroyed the textwindow and switched scores...
-//      there are a series of fields like these that need to be
file-wide
-//      not score block wide */
-//   if (!gui->textwindow)
-//     create_text_display (gui);
-//   if (gui->si->currentobject)
-//     gui->si->curlilynode = gui->si->currentobject;
-//   lily_text_change (gui);
-// }
-// /*void updatescoreinfo (DenemoScore *si);*/
-// /* this is missing from header */
-// void
-// next_score (GtkWidget * button, DenemoGUI * gui)
-// {
-//   GList *g = gui->si->scoreblocks;
-//   if (g == NULL)
-//     return;
-//   /* copy the si to the last in the list si->next,
-//      then copy the first to si, and then move the first to the last
*/
-//   memcpy (g_list_last (g)->data, gui, sizeof (DenemoGUI));
-//   memcpy (gui, g->data, sizeof (DenemoGUI));
-//   g = g_list_append (g, g->data);    /* put it on the end */
-//   g = g_list_delete_link (g, g);     /* and remove it from the
beginning */
-//   gui->si->scoreblocks = g;
-//   updatescoreinfo (gui->si);
-// }
-// 
-// void
-// toggle_top_node (GtkWidget * button, DenemoGUI * gui)
-// {
-//   if (gui->si->lily_file->next == NULL)
-//     return;                  /* all in one node */
-//   if (GTK_WIDGET_VISIBLE (gui->scorearea))   /* not in toplevel */
-//     {
-//       if (gui->si->lily_file)
-//              gui->si->curlilynode = gui->si->lily_file;
-//       gtk_widget_hide (gui->scorearea);
-//       if (!GTK_WIDGET_IS_SENSITIVE (gui->textview))
-//      {
-//        gtk_widget_set_sensitive (gui->textview, TRUE);
-//        gtk_widget_set_sensitive (gui->scorearea, FALSE);
-//      }
-//     }
-//   else
-//     gtk_widget_show (gui->scorearea);
-//   lily_text_change (gui);
-// }
-// static void
-// node_text_next (GtkWidget * win, gpointer data)
-// {
-//   DenemoGUI *gui = (DenemoGUI *) data;
-//   if (gui->si->curlilynode == gui->si->currentobject)
-//     {
-//       cursorright (gui->si);
-//       gui->si->curlilynode = gui->si->currentobject;
-//       gtk_widget_draw (gui->scorearea, NULL);
-//       /* so cursor is seen to move in score */
-//     }
-//   else if (gui->si->curlilynode->next)
-//     {
-//       gui->si->curlilynode = gui->si->curlilynode->next;
-//     }
-// #if DEBUG
-//   g_print ("next node has node type = %d string = %s\n",
-//         ntype (gui->si->curlilynode), u_str (gui->si->curlilynode));
-// #endif
-//   lily_text_change (gui);
-// }
-// 
-// static void
-// node_text_previous (GtkWidget * win, gpointer data)
-// {
-//   DenemoGUI *gui = (DenemoGUI*) data;
-//   /*  if(si->curlilynode == NULL) si->curlilynode = lily_file; */
-//   if (gui->si->curlilynode == gui->si->currentobject)
-//     {
-//       cursorleft (gui->si);
-//       gui->si->curlilynode = gui->si->currentobject;
-//       gtk_widget_draw (gui->scorearea, NULL);
-//       /* so cursor is seen to move in score */
-//     }
-//   else if (gui->si->curlilynode->prev)
-//     {
-//       gui->si->curlilynode = gui->si->curlilynode->prev;
-//     }
-// 
-// #if DEBUG
-//   g_print ("next node has node type = %d string = %s\n",
-//         ntype (gui->si->curlilynode), u_str (gui->si->curlilynode));
-// #endif
-//   lily_text_change (gui);
-// }
-// 
-// 
-// static void
-// toggle_window (GtkWidget * widget, gpointer data)
-// {
-//   DenemoGUI *gui = (DenemoGUI *) data;
-//   /*  printf("toggling display\n"); */
-//   if (GTK_WIDGET_IS_SENSITIVE (gui->textview))
-//     {
-//       gtk_widget_set_sensitive (gui->textview, FALSE);
-//       gtk_widget_set_sensitive (gui->scorearea, TRUE);
-//     }
-//   else
-//     {
-//       gtk_widget_set_sensitive (gui->textview, TRUE);
-//       gtk_widget_set_sensitive (gui->scorearea, FALSE);
-//     }
-// 
-// }
-// 
-// /* create a textwindow to display the nodes in scoreinfo lily_file
-//     */
-// void
-// create_text_display (DenemoGUI * gui)
-// {
-//   GtkWidget *main_vbox;
-//   static GtkWidget *second_window = NULL;
-//   GtkWidget *hbox;
-//   GtkWidget *sw;
-//   GtkWidget *togglebutton, *topbutton, *prevbutton, *nextbutton,
-//     *reloadbutton;
-// 
-//   main_vbox = gtk_bin_get_child ((GtkBin *) gui->window);
-//   gui->textwindow = gtk_vbox_new (FALSE, 1);
-//   gtk_container_add (GTK_CONTAINER (main_vbox), gui->textwindow);
-//   gtk_widget_show (gui->textwindow);
-//   main_vbox = gui->textwindow;
-//   if (!second_window)
-//     {
-//       second_window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
-//       gtk_window_set_title (GTK_WINDOW (second_window),
-//                          "Lilypond Mode Functions");
-//       gtk_window_set_default_size (GTK_WINDOW (second_window), 100,
75);
-//       gtk_widget_show (second_window);
-// 
-//       hbox = gtk_hbox_new (FALSE, 1);
-//       gtk_container_add (GTK_CONTAINER (second_window), hbox);
-//       gtk_widget_show (hbox);
-//       /* the reload node button */
-//       reloadbutton = gtk_button_new_with_label ("Reload");
-//       g_signal_connect (G_OBJECT (reloadbutton), "clicked",
-//                      (GtkSignalFunc) reload_lily_file, gui);
-//       gtk_box_pack_start (GTK_BOX (hbox), reloadbutton, TRUE, FALSE,
0);
-//       gtk_widget_show (reloadbutton);
-//       /* the edit button */
-//       togglebutton = gtk_button_new_with_label ("Toggle window");
-//       gtk_widget_set_size_request (togglebutton, -1, 20);
-//       g_signal_connect (G_OBJECT (togglebutton), "clicked",
-//                      (GtkSignalFunc) toggle_window, gui);
-//       gtk_box_pack_start (GTK_BOX (hbox), togglebutton, TRUE, FALSE,
0);
-//       gtk_widget_show (togglebutton);
-// 
-//       /* the top node button */
-//       topbutton = gtk_button_new_with_label ("Toplevel <-> Music
Data");
-//       gtk_widget_set_size_request (topbutton, -1, 20);
-//       g_signal_connect (G_OBJECT (topbutton), "clicked",
-//                      (GtkSignalFunc) toggle_top_node, gui);
-//       gtk_box_pack_start (GTK_BOX (hbox), topbutton, TRUE, FALSE,
0);
-//       gtk_widget_show (topbutton);
-// 
-// 
-//       /* the previous node button */
-//       prevbutton = gtk_button_new_with_label ("<-");
-//       gtk_widget_set_size_request (prevbutton, -1, 20);
-//       g_signal_connect (G_OBJECT (prevbutton), "clicked",
-//                      (GtkSignalFunc) node_text_previous, gui);
-//       gtk_box_pack_start (GTK_BOX (hbox), prevbutton, TRUE, FALSE,
0);
-//       gtk_widget_show (prevbutton);
-//       /* the next node button */
-//       nextbutton = gtk_button_new_with_label ("->");
-//       gtk_widget_set_size_request (nextbutton, -1, 20);
-//       g_signal_connect (G_OBJECT (nextbutton), "clicked",
-//                      (GtkSignalFunc) node_text_next, gui);
-//       gtk_box_pack_start (GTK_BOX (hbox), nextbutton, TRUE, FALSE,
0);
-//       gtk_widget_show (nextbutton);
-//       /* the music data button */
-//       gui->musicdatabutton =
-//      gtk_button_new_with_label ("music data - edit graphically");
-//       gtk_widget_set_size_request (gui->musicdatabutton, -1, 20);
-//       /* could have signal here to go to current object? */
-//       gtk_box_pack_start (GTK_BOX (hbox), gui->musicdatabutton,
TRUE,
-//                        FALSE, 0);
-//       gtk_widget_show (gui->musicdatabutton);
-// 
-//     }
-//   /******* the text to edit ***********/
-//   sw = gtk_scrolled_window_new (NULL, NULL);
-//   gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (sw),
-//                                GTK_POLICY_AUTOMATIC,
GTK_POLICY_AUTOMATIC);
-// 
-//   gtk_container_add (GTK_CONTAINER (main_vbox), sw);
-//   gtk_widget_show (sw);
-// 
-// 
-//   gui->textview = gtk_text_view_new ();
-//   gtk_widget_set_sensitive (gui->textview, FALSE);
-//   gtk_container_add (GTK_CONTAINER (sw), gui->textview);
-//   gui->textbuffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW
(gui->textview));
-//   gui->si->curlilynode = gui->si->lily_file;
-//   gtk_text_buffer_set_text (gui->textbuffer, u_str
(gui->si->curlilynode), -1);
-//   gui->sigid = g_signal_connect (G_OBJECT (gui->textbuffer),
"changed",
-//                              (GtkSignalFunc) string_edited, gui);
-//   gtk_widget_show (gui->textview);
-// }
+static int create_score (DenemoScore * si, GList * top);
+
+static void
+generate_chords_and_sequentials (DenemoScore * si, GList * g)
+{
+  GList *chordnode;
+
+  for (chordnode = br (g); chordnode; chordnode = chordnode->next)
+    {
+      if (ntype (chordnode) == SIMULTANEOUS)
+       {
+         gchar *str = u_str (chordnode);
+         gchar *str2 = u_post_str (chordnode);
+         chordnode->data = generate_chord (br (chordnode));
+         u_str (chordnode) =
+           g_strconcat (str, u_str (chordnode), str2, NULL);
+         /* FIXME memory leak */
+       }
+      else if (ntype (chordnode) == SEQUENTIAL)
+       {
+         /*create a text node for the u_str, one for the u_post_str and 
+            in between link in the create_score(br(chordnode) */
+         GList *ret;
+         GList *temp = br (chordnode);
+         generate_chords_and_sequentials (si, chordnode);
+         u_str (temp) = g_strconcat (u_str (chordnode), u_str (temp), NULL);
+         (chordnode->prev)->next = NULL;
+         ret = g_list_concat (chordnode->prev, temp);
+         temp = g_list_last (temp);
+         u_str (temp) =
+           g_strconcat (u_str (temp), u_post_str (chordnode), NULL);
+         chordnode->prev = NULL;
+         ret = g_list_concat (temp, chordnode->next);
+         /* FIXME memory leak of chordnode itself */
+       }
+    }
+}
+
+
+
+/* RECURSIVE: perform the guts of end_of_first_measure() qv, going
inside
+   MUSIC_IDENTIFIERS - assume such a thing does not cross a tuplet or
grace */
+static GList *
+recursive_end_of_first_measure (GList * theobjs, gint * ptime1, gint *
ptime2,
+                               gint * pticks_so_far, gint * ptickspermeasure,
+                               gint * pnumerator, gint * pdenominator)
+{
+
+  objnode *curobjnode;
+  DenemoObject *theobj;
+  gint basic_ticks_in_tuplet_group = 0;
+  gint basic_ticks_in_grace_group = 0;
+  gboolean in_tuplet = FALSE;
+  gboolean in_grace = FALSE;
+  for (curobjnode = theobjs; curobjnode; curobjnode = curobjnode->next)
+    {
+      theobj = (DenemoObject *) curobjnode->data;
+      theobj->starttick =
+       *pticks_so_far + (basic_ticks_in_tuplet_group * *pnumerator
+                         / *pdenominator) + basic_ticks_in_grace_group;
+
+      switch (theobj->type)
+       {
+       case PARTIAL:
+       case CHORD:
+
+         if (in_tuplet)
+           {
+             set_tuplefied_numticks (theobj, *pnumerator, *pdenominator);
+             basic_ticks_in_tuplet_group += theobj->basic_durinticks;
+           }
+         else if (in_grace)
+           {
+             set_grace_numticks (theobj, 8);
+             basic_ticks_in_grace_group += theobj->basic_durinticks;
+           }
+         else
+           {
+             set_tuplefied_numticks (theobj, 1, 1);
+             set_grace_numticks (theobj, 1);
+             if (theobj->type == PARTIAL)
+               {
+                 theobj->durinticks = *ptickspermeasure - theobj->durinticks;
+                 /* FIXME need to handle the FRACTION multiplier which is not 
+                    being passed through at the moment */
+               }
+             *pticks_so_far += theobj->durinticks;
+           }
+         break;
+
+       case TUPOPEN:
+
+         in_tuplet = TRUE;
+         *pnumerator = ((tupopen *) theobj->object)->numerator;
+         *pdenominator = ((tupopen *) theobj->object)->denominator;
+         basic_ticks_in_tuplet_group = 0;      /* Probably gratuitous */
+         break;
+       case TUPCLOSE:
+
+         in_tuplet = FALSE;
+         *pticks_so_far += ((basic_ticks_in_tuplet_group * *pnumerator)
+                            / *pdenominator);
+         *pnumerator = 1;
+         *pdenominator = 1;
+         basic_ticks_in_tuplet_group = 0;
+         break;
+       case GRACE_START:
+
+         in_grace = TRUE;
+         basic_ticks_in_grace_group = 0;
+         break;
+       case GRACE_END:
+
+         in_grace = FALSE;
+         /*      *pticks_so_far += basic_ticks_in_grace_group; */
+         basic_ticks_in_grace_group = 0;
+         break;
+       case TIMESIG:
+         *ptime1 = ((timesig *) theobj->object)->time1;
+         *ptime2 = ((timesig *) theobj->object)->time2;
+         *ptickspermeasure = *ptime1 * WHOLE_NUMTICKS / *ptime2;
+         break;
+       case MUSIC_IDENTIFIER:
+         {
+           GList *ret =
+             recursive_end_of_first_measure ((((nodeid *) (curobjnode)->
+                                               data)->id), ptime1, ptime2,
+                                             pticks_so_far, ptickspermeasure,
+                                             pnumerator, pdenominator);
+           if (ret)
+             {
+               g_warning ("Measure finishes inside a music_identifier\n");
+               return ret;
+                    /** bar finished inside the MUSIC_IDENTIFIER */
+             }
+         }
+         break;
+
+       case SKIPNAME:  // FIXME memory leak and
+                       // This assumes skip is for entire bar which is not
+                       // generally true. The issue is duration, dot(s) used
+                       // by denemo cannot describe full measure skip 
+                       // durations in some time signatures such as 5/4. 
+         return curobjnode;
+         break;
+
+       default:
+         break;
+       }
+
+      theobj->starttickofnextnote =
+       *pticks_so_far + (basic_ticks_in_tuplet_group * *pnumerator
+                         / *pdenominator) + basic_ticks_in_grace_group;
+      if (*pticks_so_far >= *ptickspermeasure)
+       break;
+    }
+
+  return curobjnode;
+}
+
+/* return the node in g at which one measure is complete in terms
+   of ticks. On entering, assume timesig of (*ptime1) / (*ptime2), any
+   change in the timesig changes these.
+   If end of measure, or incomplete measure return NULL
+   This function has been ripped off of settickvalsinmeasure() in
+   measureops.cpp, it side-effects the ticks fields of the objs in
+   the list, in the same manner as will that function when called.
+*/
+static GList *
+end_of_first_measure (GList * theobjs, gint * ptime1, gint * ptime2)
+{
+  gint numerator = 1, denominator = 1; /* varies if in tuplet etc */
+  gint ticks_so_far = 0;
+  gint tickspermeasure = *ptime1 * WHOLE_NUMTICKS / *ptime2;
+  return recursive_end_of_first_measure (theobjs, ptime1, ptime2,
+                                        &ticks_so_far, &tickspermeasure,
+                                        &numerator, &denominator);
+
+
+}
+
+/*  attach the measures in BRANCH to the MEASURES_LIST, by counting
ticks 
+ * return the measures list built up */
+static GList *
+break_into_measures (GList * branch, DenemoStaff * staff)
+{
+  GList * measures_list = staff->measures;
+  GList *barline;
+  GList *rest;
+  gint time1 = staff->stime1; 
+  gint time2 = staff->stime2;
+  barline = end_of_first_measure (branch, &time1, &time2);
+  if (barline)
+    {
+      rest = barline->next;
+      if (rest)
+       rest->prev = NULL;
+      barline->next = NULL;
+    }
+  else
+    rest = NULL;
+  measures_list = g_list_append (measures_list, branch);
+  while (rest && ntype(rest) != BAR)
+    {
+      barline = end_of_first_measure (rest, &time1, &time2);
+      if (barline)
+       {
+         measures_list = g_list_append (measures_list, rest);
+         staff->nummeasures++;
+         rest = barline->next;
+         if (rest)
+           rest->prev = NULL;
+         barline->next = NULL;
+       }
+      else
+       {
+         measures_list = g_list_append (measures_list, rest);
+         staff->nummeasures++;
+         rest = NULL;
+
+       }
+    }
+  return measures_list;
+}
+
+/*
+       is_tied is TRUE after either a slur or tie becomes active
+       calling is_tied with an argument of NULL resets it's state
+*/
+static gboolean
+is_tied ( chord * chord_pt)
+{
+    static gboolean active_tie;
+    static gboolean active_slur;
+    gboolean ret = active_tie || active_slur;
+
+    if (chord_pt == NULL)
+      {
+       active_tie = FALSE;
+       active_slur = FALSE;
+       return FALSE;
+      }
+
+    if (chord_pt->is_tied)
+       active_tie = TRUE;
+    else
+       active_tie = FALSE;
+
+    if (chord_pt->slur_end_p)
+       active_slur = FALSE;
+
+    if (chord_pt->slur_begin_p)
+       active_slur = TRUE;
+
+    return ret;
+}
+/*
+       recursively scan lyrucsto object lyparser tree for lyrics
+       and attach lyrics to chord structure
+
+       Note: Denemo does not support multiple lines of lyrics.
+*/ 
+static gboolean
+get_lyric (GList * glyric, measurenode **meas, objnode *curobjnode)
+{
+      DenemoObject *curobj;
+
+      if (glyric == NULL)
+         return (FALSE);
+
+      switch (ntype (glyric))
+      {
+       case MUSIC_IDENTIFIER:
+         get_lyric (((nodeid*)(glyric)->data)->id, meas, curobjnode);
+         glyric = glyric->next;
+         break;
+
+       case SIMULTANEOUS:
+         get_lyric (br (glyric), meas, curobjnode);
+         if ((br (glyric))->next)
+               g_warning("Lyricsto: Denemo does not support more than one line 
of
lyrics");
+         glyric = glyric->next;
+         break;
+
+       case SEQUENTIAL:
+         get_lyric (br (glyric), meas, curobjnode);
+         glyric = glyric->next;
+         break;
+
+       case OVERRIDE:
+       case LYRICMODE:
+       case lyricscontext:
+       case endcontext:
+         glyric = glyric->next;
+         break;
+
+       case LYRICS:
+       case SKIP:
+         do
+           {
+               if (curobjnode == NULL)
+                 {
+                   if (*meas == NULL)
+                       return FALSE;
+                   curobjnode = (objnode *) (*meas)->data;
+                   *meas = (*meas)->next;
+                 }
+                curobj = (DenemoObject *) curobjnode->data;
+               if (curobj->type == CHORD 
+                   && ( (chord *) curobj->object)->numtones
+                   && ! is_tied ((chord *) curobj->object))
+                 {
+                   if (ntype (glyric) == LYRICS)
+                       ( (chord *) curobj->object)->lyric = 
+                               ((chord *) gobj (glyric))->lyric;
+                   glyric = glyric->next;
+                 }
+               curobjnode = curobjnode->next;
+           }
+         while (glyric && (ntype (glyric) == LYRICS || ntype (glyric) ==
SKIP));
+         break;
+
+       default:
+         g_warning("get_lyric unexpected lyric type %d", ntype (glyric));
+         return FALSE;
+         break;
+
+      }
+      return (get_lyric (glyric, meas, curobjnode));
+
+}
+/*
+       process the lyricsto list generated by the lyparser
+*/
+static void
+process_lyricsto (DenemoScore * si, GList * top)
+{
+       staffnode *staff;
+        measurenode *meas;
+
+
+    for (staff = si->thescore; staff; staff = staff->next)
+      {
+       if (!strcmp (( (DenemoStaff *) (staff->data))->lily_name->str, 
+               u_str (top)))
+       {
+         break;
+       }
+      }
+      if (!staff)
+      {
+       g_warning("Lyricsto staff %s not found\n", u_str (top));
+       return;
+      }
+
+
+      meas = (measurenode *) (((DenemoStaff *)
(staff->data))->measures);
+      get_lyric (br (top), &meas, NULL);
+}
+
+/* create_score: Recursively traverse the GList TOP which represents a 
+   score block of the input lily file. Create denemo structures to
enable 
+   it to be edited graphically
+*/
+static int
+create_score (DenemoScore * si, GList * top)
+{
+  GList *g;
+
+  DenemoStaff *curstaffstruct;
+#if DEBUG
+
+  char *name;
+  g_print
+    ("The parse tree from this node downwards looks"
+     " like this\n*************************************\n");
+  for (g = top; g; g = g->next)
+    {
+      g_print ("node type = %s(%d) string = %s\n",
+              lookup_type(((nodegeneric *) g->data)->type),
+              ((nodegeneric *) g->data)->type,
+              ((nodegeneric *) g->data)->user_string);
+    }
+  g_print ("\n*************************************\n");
+#endif
+
+  for (g = top; g; (g = g->next))
+    {
+#if DEBUG
+      g_print ("Handling: node type = %d string = %s\t",
+              ((nodegeneric *) g->data)->type,
+              ((nodegeneric *) g->data)->user_string);
+#endif
+      switch (ntype (g))
+       {
+       case figuredbasscontext:
+       case staffcontext:
+         ; // for GString 
+         GString *staffname = gstr (g) ? gstr (g) : g_string_new ("");
+         findstaff (staffname, si);    /*sets si->currentstaffnum */
+         staffctx = si->currentstaff;
+         if (!staffctx)
+           {
+             si->currentstaff = si->thescore;
+             anewstaff (si, staffname, g_string_new (""));
+             staffctx = si->currentstaff = g_list_last (si->thescore);
+             set_denemo_name (staffname, staffstruct
(staffctx)->denemo_name);
+             staffstruct (staffctx)->voicenumber = 1;
+           }
+         si->currentprimarystaff = staffctx;
+         if (ntype (g) == figuredbasscontext)
+           {
+             staff_info *staffs =
+               (staff_info *) g_malloc0 (sizeof (staff_info));
+             if (staffctx->prev == NULL)
+               {
+                 parser_error ("Figured Bass not preceded by a bass staff ",
+                               0);
+                 return -1;
+               }
+             staffs->main_staff = (DenemoStaff *) (staffctx->prev->data);
+             staffs->related_staff = (DenemoStaff *) (staffctx->data);
+             si->has_figures = staffs;
+             ((DenemoStaff *) (staffctx->data))->no_of_lines = 0;
+           }
+         break;
+
+       case voicecontext:
+         ; // for GString
+          GString *name = gstr(g) ? gstr (g) : g_string_new ("");
+
+
+         if (!findvoice (name, si))
+           {
+             anewstaff (si, staffstruct (staffctx)->staff_name, name);
+             si->currentmeasurenum = 1;
+             voicectx = si->currentstaff;
+             set_denemo_name (name, staffstruct (voicectx)->denemo_name);
+             //staffstruct (voicectx)->voicenumber = 2;
+             staffstruct (voicectx)->voicenumber = 1;
+           }
+         voicectx = si->currentstaff;
+         break;
+
+       case endcontext:
+         if (voicectx)
+           {
+             voicectx = NULL;
+           }
+         else
+           staffctx = NULL;
+         break;
+       case MUSIC_IDENTIFIER:
+#define id(g) (((nodeid*)(g)->data)->id)
+         if (create_score (si, id (g)))
+           return -1;
+         break;
+       case SIMULTANEOUS:
+         if (create_score (si, br (g)))
+           return -1;
+         break;
+
+       case SCORE:
+         parser_error ("Score block inside a score block", 0);
+         return -1;
+         break;
+
+       case DENEMO_MEASURES:
+       case SEQUENTIAL:
+         /* first find out if we have voice and staff contexts,
+            if not create use/create
+            default staff structures */
+         if (!staffctx)
+           {                   /* use/create the first staff structure in 
si->thescore */
+             if (si->thescore)
+               {
+                 /* if we have a named voice context create a staff context 
+                    for it otherwise insert it as a voice in the first staff 
+                  */
+                 staffctx = voicectx = g_list_last (si->thescore);
+               }
+             else
+               {
+                 anewstaff (si, g_string_new ("dummyname"),
+                            g_string_new ("dummyname"));
+                 staffctx = voicectx = si->currentstaff;
+               }
+           }
+         else
+           {                   /* there is a staff context */
+             if (!voicectx)
+               voicectx = staffctx;
+           }
+         si->currentstaff = voicectx;
+         curstaffstruct = staffstruct (voicectx);
+         if (ntype (g) == SEQUENTIAL)
+           {
+             generate_chords_and_sequentials (si, g);
+
+             curstaffstruct->measures =
+               break_into_measures (br (g), curstaffstruct);
+             br (g) = (GList *) & (curstaffstruct->measures);
+             /* nasty - we store the address
+                of the GList* pointer. This is so that if
+                editing in denemo adds a new bar at the beginning we
+                will not find ourselves pointing to the second bar. Or,
+                worse if the first bar got deleted. We are not yet tackling 
+                the case where the staff gets deleted. We should probably 
+                store the name and prevent that
+                being changed uncontrollably */
+             ntype (g) = DENEMO_MEASURES;
+           }
+         else
+           {                   /* these measures are already in another staff 
*/
+             curstaffstruct->measures = *(measurenode **) br (g);
+             curstaffstruct->is_parasite = (measurenode **) br (g);
+           }
+         break;
+
+       case LYRICSTO: {
+               process_lyricsto (si, g);
+           }
+         break;
+
+       default:
+         break;
+               }
+    }
+  return 0;
+
+}
+
+int
+create_score_from_lily (DenemoScore * si, GList * top)
+{
+  staffctx = NULL;
+  voicectx = NULL;
+  lyricsctx = NULL;
+  figuresctx = NULL;
+  return create_score (si, top);
+}
+
+
+/* this function seems to be missing from the glib library, 
+   although in the headers */
+gboolean
+g_string_equal (const GString * v, const GString * v2)
+{
+  if ((!v) || (!v2) || (v->len != v2->len))
+    return FALSE;
+  return !strcmp (v->str, v2->str);    /* not general case of embedded 0
bytes */
+}
+void
+init_crescendo_state ()
+{
+       cresc_state.active_cres = FALSE;
+       cresc_state.active_decres = FALSE;
+}
+/*
+       terminate crescendo or decrescendo if active
+*/
+static void
+terminate_crescendo_state (chord *cd)
+{
+       if (cresc_state.active_cres)
+       {
+           cd->crescendo_end_p = TRUE;
+           cresc_state.active_cres = FALSE;
+       }
+       if (cresc_state.active_decres)
+       {
+           cd->diminuendo_end_p = TRUE;
+           cresc_state.active_decres = FALSE;
+       }
+}
+
+void
+set_post_events (DenemoObject *mud, gchar *usr_str, GList *g)
+{
+    DenemoObject *obj = mud;
+    chord * chordpt;
+
+    if (!g)
+       return;
+
+    if (obj->type == SIMULTANEOUS)
+    {
+       obj = (((nodeglist*)obj)->branch)->data;
+    }
+
+    if (obj->type != CHORD)
+    {
+
+       g_assert (obj->type == CHORD);
+    }
+    chordpt = (chord *) (obj->object);
+       while (g)
+       {
+               usr_str = g_strconcat (usr_str , u_str (g), NULL);
+               switch (ntype (g)) {
+               case '(':
+                       chordpt->slur_begin_p = TRUE;
+                       break;
+
+               case ')':
+                       chordpt->slur_end_p = TRUE;
+                       break;  
+
+               case '~':
+                       chordpt->is_tied = TRUE;
+                       break;  
+
+               case E_SMALLER:
+                       terminate_crescendo_state (chordpt);
+                       chordpt->crescendo_begin_p = TRUE;
+                       cresc_state.active_cres = TRUE;
+                       break;
+
+               case E_BIGGER:
+                       terminate_crescendo_state (chordpt);
+                       chordpt->diminuendo_begin_p = TRUE;
+                       cresc_state.active_decres = TRUE;
+                       break;
+
+               case E_EXCLAMATION:
+                       terminate_crescendo_state (chordpt);
+                       break;
+
+               case TONEOPTION:
+                       set_articulation (gstr (g)->str, obj);
+                       break;
+
+               case DYNAMICMARK:
+                   {
+
+                       /*
+                          A dynamic mark terminates crescendo or decrescendo
+                       */
+                       terminate_crescendo_state (chordpt);
+
+                       /*
+                               \cr alternate \<
+                               \decr alternate \>
+                               \rc & \rced (\!) backward compatibility Denemo 
+                       */
+                       if (!strcmp ( gstr (g)->str, "cr"))
+                       {
+                           chordpt->crescendo_begin_p = TRUE;
+                           cresc_state.active_cres = TRUE;
+                       }
+                       else if (!strcmp ( gstr (g)->str, "decr"))
+                       {
+                           chordpt->diminuendo_begin_p = TRUE;
+                           cresc_state.active_decres = TRUE;
+                       }
+                       else if (!strcmp ( gstr (g)->str, "rced")
+                                || !strcmp ( gstr (g)->str, "rc"))
+                       {
+                               /* we have already terminated hairpin
+                                  this is so Denemo does not show these
+                                  strings as dynamics */
+                       }
+                       else
+                       
+                           chordpt->dynamics = 
+                               g_list_append ( chordpt->dynamics, gstr (g));
+                   }
+                       break;
+
+
+               default: g_warning ("type %d not processed in set_post_events", 
+                               ntype (g));
+                       break;
+               }
+           g = g->next;
+       }
+}
+
+#ifdef LILYEDIT
+/***************** functions for managing display of lily text
***************/
+
+static void
+string_edited (GtkTextBuffer * buffer, gpointer data)
+{
+  GtkTextIter start, end;
+  gchar *text;
+  DenemoScore *si = (DenemoScore *) data;
+  gtk_text_buffer_get_bounds (buffer, &start, &end);
+  text = gtk_text_iter_get_text (&start, &end);
+  if (si->curlilynode == NULL)
+    {
+      g_warning ("Attempt to edit nonexistent node - ignored\n");
+      return;
+    }
+  if (u_str (si->curlilynode))
+    g_free (u_str (si->curlilynode));
+  /* else big memory leak - check all lilynodes 
+     xsuser_strings are mallocced strings  */
+  u_str (si->curlilynode) = text;
+}
+
+
+void
+lily_text_change (DenemoScore * si)
+{
+  static gboolean text_is_readonly = FALSE;
+  g_signal_handler_block (G_OBJECT (si->textbuffer), si->sigid);
+  if (ntype (si->curlilynode) == DENEMO_MEASURES)
+    {
+      gtk_widget_hide (si->textview);
+      gtk_widget_show (si->musicdatabutton);
+      text_is_readonly = TRUE;
+    }
+  else
+    {
+      if (text_is_readonly)
+       {
+         gtk_widget_show (si->textview);
+         gtk_widget_hide (si->musicdatabutton);
+       }
+      text_is_readonly = FALSE;
+      if (ntype (si->curlilynode) == endcontext)
+       gtk_text_buffer_set_text (si->textbuffer,
+                                 g_strdup ("<<Music Data End>>"), -1);
+      if (!u_str (si->curlilynode))
+       u_str (si->curlilynode) = generate_lily (si->curlilynode);
+      gtk_text_buffer_set_text (si->textbuffer, u_str
(si->curlilynode), -1);
+
+    }
+
+  g_signal_handler_unblock (G_OBJECT (si->textbuffer), si->sigid);
+}
+
+
+void
+set_text_node (GtkWidget * button, DenemoScore * si)
+{
+  /* FIXME: the next line can coredump when you have multiple score
blocks
+     and you have destroyed the textwindow and switched scores...
+     there are a series of fields like these that need to be file-wide
+     not score block wide */
+  if (!si->textwindow)
+    create_text_display (si);
+  if (si->currentobject)
+    si->curlilynode = si->currentobject;
+  lily_text_change (si);
+}
+
+void
+toggle_top_node (GtkWidget * button, DenemoScore * si)
+{
+  if (si->lily_file->next == NULL)
+    return;                    /* all in one node */
+  if (GTK_WIDGET_VISIBLE (si->scorearea))      /* not in toplevel */
+    {
+      if (si->lily_file)
+       si->curlilynode = si->lily_file;
+      gtk_widget_hide (si->scorearea);
+      if (!GTK_WIDGET_IS_SENSITIVE (si->textview))
+       {
+         gtk_widget_set_sensitive (si->textview, TRUE);
+         gtk_widget_set_sensitive (si->scorearea, FALSE);
+       }
+    }
+  else
+    gtk_widget_show (si->scorearea);
+  lily_text_change (si);
+}
+static void
+node_text_next (GtkWidget * win, gpointer data)
+{
+  DenemoScore *si = (DenemoScore *) data;
+  if (si->curlilynode == si->currentobject)
+    {
+      cursorright (si);
+      si->curlilynode = si->currentobject;
+      gtk_widget_draw (si->scorearea, NULL);
+      /* so cursor is seen to move in score */
+    }
+  else if (si->curlilynode->next)
+    {
+      si->curlilynode = si->curlilynode->next;
+    }
+#if DEBUG
+  g_print ("next node has node type = %d string = %s\n",
+          ntype (si->curlilynode), u_str (si->curlilynode));
+#endif
+  lily_text_change (si);
+}
+
+static void
+node_text_previous (GtkWidget * win, gpointer data)
+{
+  DenemoScore *si = (DenemoScore *) data;
+  /*  if(si->curlilynode == NULL) si->curlilynode = lily_file; */
+  if (si->curlilynode == si->currentobject)
+    {
+      cursorleft (si);
+      si->curlilynode = si->currentobject;
+      gtk_widget_draw (si->scorearea, NULL);
+      /* so cursor is seen to move in score */
+    }
+  else if (si->curlilynode->prev)
+    {
+      si->curlilynode = si->curlilynode->prev;
+    }
+
+#if DEBUG
+  g_print ("next node has node type = %d string = %s\n",
+          ntype (si->curlilynode), u_str (si->curlilynode));
+#endif
+  lily_text_change (si);
+}
+
+
+static void
+toggle_window (GtkWidget * widget, gpointer data)
+{
+  DenemoScore *si = (DenemoScore *) data;
+  /*  printf("toggling display\n"); */
+  if (GTK_WIDGET_IS_SENSITIVE (si->textview))
+    {
+      gtk_widget_set_sensitive (si->textview, FALSE);
+      gtk_widget_set_sensitive (si->scorearea, TRUE);
+    }
+  else
+    {
+      gtk_widget_set_sensitive (si->textview, TRUE);
+      gtk_widget_set_sensitive (si->scorearea, FALSE);
+    }
+
+}
+
+/* create a textwindow to display the nodes in DenemoScore lily_file
+    */
+void
+create_text_display (DenemoScore * si)
+{
+  GtkWidget *main_vbox;
+  static GtkWidget *second_window = NULL;
+  GtkWidget *hbox;
+  GtkWidget *sw;
+  GtkWidget *togglebutton, *topbutton, *prevbutton, *nextbutton,
+    *reloadbutton;
+
+  main_vbox = gtk_bin_get_child ((GtkBin *) si->window);
+  si->textwindow = gtk_vbox_new (FALSE, 1);
+  gtk_container_add (GTK_CONTAINER (main_vbox), si->textwindow);
+  gtk_widget_show (si->textwindow);
+  main_vbox = si->textwindow;
+  if (!second_window)
+    {
+      second_window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
+      gtk_window_set_title (GTK_WINDOW (second_window),
+                           "Lilypond Mode Functions");
+      gtk_window_set_default_size (GTK_WINDOW (second_window), 100,
75);
+      gtk_widget_show (second_window);
+
+      hbox = gtk_hbox_new (FALSE, 1);
+      gtk_container_add (GTK_CONTAINER (second_window), hbox);
+      gtk_widget_show (hbox);
+      /* the reload node button */
+      reloadbutton = gtk_button_new_with_label ("Reload");
+      g_signal_connect (G_OBJECT (reloadbutton), "clicked",
+                       (GtkSignalFunc) reload_lily_file, si);
+      gtk_box_pack_start (GTK_BOX (hbox), reloadbutton, TRUE, FALSE,
0);
+      gtk_widget_show (reloadbutton);
+      /* the edit button */
+      togglebutton = gtk_button_new_with_label ("Toggle window");
+      gtk_widget_set_size_request (togglebutton, -1, 20);
+      g_signal_connect (G_OBJECT (togglebutton), "clicked",
+                       (GtkSignalFunc) toggle_window, si);
+      gtk_box_pack_start (GTK_BOX (hbox), togglebutton, TRUE, FALSE,
0);
+      gtk_widget_show (togglebutton);
+
+      /* the top node button */
+      topbutton = gtk_button_new_with_label ("Toplevel <-> Music
Data");
+      gtk_widget_set_size_request (topbutton, -1, 20);
+      g_signal_connect (G_OBJECT (topbutton), "clicked",
+                       (GtkSignalFunc) toggle_top_node, si);
+      gtk_box_pack_start (GTK_BOX (hbox), topbutton, TRUE, FALSE, 0);
+      gtk_widget_show (topbutton);
+
+
+      /* the previous node button */
+      prevbutton = gtk_button_new_with_label ("<-");
+      gtk_widget_set_size_request (prevbutton, -1, 20);
+      g_signal_connect (G_OBJECT (prevbutton), "clicked",
+                       (GtkSignalFunc) node_text_previous, si);
+      gtk_box_pack_start (GTK_BOX (hbox), prevbutton, TRUE, FALSE, 0);
+      gtk_widget_show (prevbutton);
+      /* the next node button */
+      nextbutton = gtk_button_new_with_label ("->");
+      gtk_widget_set_size_request (nextbutton, -1, 20);
+      g_signal_connect (G_OBJECT (nextbutton), "clicked",
+                       (GtkSignalFunc) node_text_next, si);
+      gtk_box_pack_start (GTK_BOX (hbox), nextbutton, TRUE, FALSE, 0);
+      gtk_widget_show (nextbutton);
+      /* the music data button */
+      si->musicdatabutton =
+       gtk_button_new_with_label ("music data - edit graphically");
+      gtk_widget_set_size_request (si->musicdatabutton, -1, 20);
+      /* could have signal here to go to current object? */
+      gtk_box_pack_start (GTK_BOX (hbox), si->musicdatabutton, TRUE,
+                         FALSE, 0);
+      gtk_widget_show (si->musicdatabutton);
+
+    }
+  /******* the text to edit ***********/
+  sw = gtk_scrolled_window_new (NULL, NULL);
+  gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (sw),
+                                 GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
+
+  gtk_container_add (GTK_CONTAINER (main_vbox), sw);
+  gtk_widget_show (sw);
+
+
+  si->textview = gtk_text_view_new ();
+  gtk_widget_set_sensitive (si->textview, FALSE);
+  gtk_container_add (GTK_CONTAINER (sw), si->textview);
+  si->textbuffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW
(si->textview));
+  si->curlilynode = si->lily_file;
+  gtk_text_buffer_set_text (si->textbuffer, u_str (si->curlilynode),
-1);
+  si->sigid = g_signal_connect (G_OBJECT (si->textbuffer), "changed",
+                               (GtkSignalFunc) string_edited, si);
+  gtk_widget_show (si->textview);
+}
+#else /* GTK version 1 */
+void
+toggle_top_node (GtkWidget * button, DenemoGUI *gui)
+{
+  return;
+}
+
+void
+set_text_node (GtkWidget * button, DenemoGUI *gui)
+{
+  return;
+}
+
+void
+lily_text_change (DenemoGUI *gui)
+{
+  return;
+}
+
+void
+create_text_display (DenemoGUI *gui)
+{
+  updatescoreinfo (gui->si); // RRR
+  return;
+}
+#endif
diff -urN -X xdiff ../denemo/src/lyparserfuncs.h ./src/lyparserfuncs.h
--- ../denemo/src/lyparserfuncs.h       2006-05-15 05:04:01.000000000 +1000
+++ ./src/lyparserfuncs.h       2007-01-17 21:27:02.000000000 +1100
@@ -36,164 +36,175 @@
 void set_tone_option (DenemoObject * curmudelaobj, gchar * option);
 
 gint pitchtomid_c_offset (gchar name, gint octave);
-// /* reset the lexer's initial state (after failed lex/parse) */
-// void reset_initial_lexer_state (void);
-// /* sets the current lily node to the current node and displays the
user_string of that
-//    node for editing */
-// void set_text_node (GtkWidget * button, DenemoGUI * si);
-// 
-// gint lookup_keyword (gchar *);
-// /* node types returned by the lily lexer */
-// /* nodegeneric is large enough to overlay all the other node types
*/
-// typedef struct 
-//   {
-//     int type;
-//     gchar *user_string;
-//     union
-//       {
-//         char c;
-//         int i;
-//         gboolean b;
-//         GList *branch;
-//         double r;
-//         GString *gstr;
-//         DenemoObject m;             /*cheating - too big really */
-//       }
-//     u;
-//     char *post_user_string;
-//   }
-// nodegeneric;
-// 
-// typedef struct nodec
-//   {
-//     int type;
-//     gchar *user_string;
-//     char c;
-//   }
-// nodec;
-// typedef struct nodei
-//   {
-//     int type;
-//     gchar *user_string;
-//     int i;
-//   }
-// nodei;
-// typedef struct node2i
-//   {
-//     int type;
-//     gchar *user_string;
-//     struct twoints t;
-//   }
-// node2i;
-// typedef struct node4i
-//   {
-//     int type;
-//     gchar *user_string;
-//     struct twoints t1;
-//     struct twoints t2;
-//   }
-// node4i;
-// typedef struct nodeb
-//   {
-//     int type;
-//     gchar *user_string;
-//     gboolean boolean;
-//   }
-// nodeb;
-// typedef struct nodeglist
-//   {
-//     int type;
-//     gchar *user_string;
-//     GList *branch;
-//     char *post_user_string;
-//   }
-// nodeglist;
-// typedef struct nodeid
-//   {
-//     int type;
-//     gchar *user_string;
-//     GList *id;
-//   }
-// nodeid;
-// typedef struct nodemus
-//   {
-//     int type;
-//     gchar *user_string;
-//     GList *music;
-//   }
-// nodemus;
-// typedef struct noder
-//   {
-//     int type;
-//     gchar *user_string;
-//     double r;
-//   }
-// noder;
-// typedef struct nodegstr
-//   {
-//     int type;
-//     gchar *user_string;
-//     GString *gstr;
-//   }
-// nodegstr;
-// 
-// /* only in non-terminals */
-// typedef struct noden
-//   {
-//     int type;
-//     gchar *user_string;
-//     note n;
-//   }
-// noden;
-// 
-// typedef struct nodemin
-//   {
-//     int type;
-//     gchar *user_string;
-//   }
-// nodemin;
-// 
-// /* a set of convenience macros for accessing objects held in GLists
*/
-// #define ntype(g) (((nodemin*)(g)->data)->type)
-// #define u_str(g) (((nodemin*)(g)->data)->user_string)
-// #define u_post_str(g) (((nodeglist*)(g)->data)->post_user_string)
-// #define br(g) (((nodeglist*)(g)->data)->branch)
-// #define gstr(g) (((nodegstr*)(g)->data)->gstr)
-// 
-// 
-// #define staffstruct(g) ((DenemoStaff*)(g->data))
-// 
-// 
-// #define BAD_ENSHIFT (0xFFFF)        /* not an enshift */
-// 
-// 
-// /* these lexer states are manipulated by the parser  */
-// void push_notes_state (void);
-// void push_figuredbass_state (void);
-// void push_chord_state (void);
-// void push_lyric_state (void);
-// void pop_state (void);
-// /* inform parser about whitespace after last rule but before EOF */
-// void set_trailing_white_space (gchar *trailing);
-// 
-// 
-// /* creates a denemo scoreinfo from the lily parse tree TOP */
-// int create_score_from_lily (DenemoScore * si, GList * top);
-// /* sets parser state to error, creates a dialog with text and offers
to exit
-//  * if the user doesn't exit the parser takes the whole file for
editing */
-// void parser_error (gchar * text, int linenum);
-// /* sets up a text display for the lily text */
-// void create_text_display (DenemoGUI * gui);
-// /* toggles the display to show the topmost lily node in si
-//    and enable text editing or switch back to scorearea editing */
-// void toggle_top_node (GtkWidget * button,DenemoGUI *gui);
-// /* show text associated with curlilynode of si */
-// void lily_text_change (DenemoGUI *gui);
-// * traverse G a GList of object nodes returning the first of type T
or
-// NULL if none 
-// GList *findtok (GList * g, int t);
-// * move to the next score in the list of scores 
-// void next_score (GtkWidget * button, DenemoGUI* gui);
-// */
+ /* reset the lexer's initial state (after failed lex/parse) */
+ void reset_initial_lexer_state (void);
+ /* sets the current lily node to the current node and displays the
user_string of that
+    node for editing */
+ void set_text_node (GtkWidget * button, DenemoGUI * si);
+ 
+ gint lookup_keyword (gchar *);
+
+typedef struct crescendo_state
+{
+       gboolean active_cres;
+       gboolean active_decres;
+} crescendo_state;
+
+void init_crescendo_state();
+
+ /* node types returned by the lily lexer */
+ /* nodegeneric is large enough to overlay all the other node types */
+ typedef struct 
+   {
+     int type;
+     gchar *user_string;
+     union
+       {
+         char c;
+         int i;
+         gboolean b;
+         GList *branch;
+         double r;
+         GString *gstr;
+         DenemoObject m;               /*cheating - too big really */
+       }
+     u;
+     char *post_user_string;
+   }
+ nodegeneric;
+ 
+ typedef struct nodec
+   {
+     int type;
+     gchar *user_string;
+     char c;
+   }
+ nodec;
+ typedef struct nodei
+   {
+     int type;
+     gchar *user_string;
+     int i;
+   }
+ nodei;
+ typedef struct node2i
+   {
+     int type;
+     gchar *user_string;
+     struct twoints t;
+   }
+ node2i;
+ typedef struct node4i
+   {
+     int type;
+     gchar *user_string;
+     struct twoints t1;
+     struct twoints t2;
+   }
+ node4i;
+ typedef struct nodeb
+   {
+     int type;
+     gchar *user_string;
+     gboolean boolean;
+   }
+ nodeb;
+ typedef struct nodeglist
+   {
+     int type;
+     gchar *user_string;
+     GList *branch;
+     char *post_user_string;
+   }
+ nodeglist;
+ typedef struct nodeid
+   {
+     int type;
+     gchar *user_string;
+     GList *id;
+   }
+ nodeid;
+ typedef struct nodemus
+   {
+     int type;
+     gchar *user_string;
+     GList *music;
+   }
+ nodemus;
+ typedef struct noder
+   {
+     int type;
+     gchar *user_string;
+     double r;
+   }
+ noder;
+ typedef struct nodegstr
+   {
+     int type;
+     gchar *user_string;
+     GString *gstr;
+   }
+ nodegstr;
+ 
+ /* only in non-terminals */
+ typedef struct noden
+   {
+     int type;
+     gchar *user_string;
+     note n;
+   }
+ noden;
+ 
+ typedef struct nodemin
+   {
+     int type;
+     gchar *user_string;
+   }
+ nodemin;
+ 
+ /* a set of convenience macros for accessing objects held in GLists */
+ #define ntype(g) (((nodemin*)(g)->data)->type)
+ #define u_str(g) (((nodemin*)(g)->data)->user_string)
+ #define u_post_str(g) (((nodeglist*)(g)->data)->post_user_string)
+ #define br(g) (((nodeglist*)(g)->data)->branch)
+ #define gstr(g) (((nodegstr*)(g)->data)->gstr)
+ #define gi(g) (((nodei*)(g)->data)->i)
+ #define gobj(g) (((DenemoObject *)(g)->data)->object)
+ 
+ 
+ #define staffstruct(g) ((DenemoStaff*)(g->data))
+ 
+ 
+ #define BAD_ENSHIFT (0xFFFF)  /* not an enshift */
+ 
+void set_post_events (DenemoObject *mud, gchar *usr_str, GList *g);
+ 
+ /* these lexer states are manipulated by the parser  */
+ void push_notes_state (void);
+ void push_figuredbass_state (void);
+ void push_chord_state (void);
+ void push_lyric_state (void);
+ void pop_state (void);
+ /* inform parser about whitespace after last rule but before EOF */
+ void set_trailing_white_space (gchar *trailing);
+ 
+ 
+ /* creates a denemo scoreinfo from the lily parse tree TOP */
+ int create_score_from_lily (DenemoScore * si, GList * top);
+ /* sets parser state to error, creates a dialog with text and offers
to exit
+  * if the user doesn't exit the parser takes the whole file for
editing */
+ void parser_error (gchar * text, int linenum);
+ /* sets up a text display for the lily text */
+ void create_text_display (DenemoGUI * gui);
+ /* toggles the display to show the topmost lily node in si
+    and enable text editing or switch back to scorearea editing */
+ void toggle_top_node (GtkWidget * button, DenemoGUI *gui);
+ /* show text associated with curlilynode of si */
+ void lily_text_change (DenemoGUI *gui);
+ /* traverse G a GList of object nodes returning the first of type T or
+    NULL if none */
+    GList *findtok (GList * g, int t);
+   /* move to the next score in the list of scores */
+   void next_score (GtkWidget * button, DenemoGUI* gui);
 
 #endif /*LYPARSERFUNCSH */
diff -urN -X xdiff ../denemo/src/lyparser.y ./src/lyparser.y
--- ../denemo/src/lyparser.y    2006-08-24 05:48:39.000000000 +1000
+++ ./src/lyparser.y    2007-01-30 21:26:30.000000000 +1100
@@ -27,29 +27,25 @@
 the list into measures which are linked into the staff->measures list.
 After editing graphically denemo stype the whole list is traversed
writing 
 out the user_string fields or (where they are NULL) re-creating them
from 
-the data in the mudelaobject concerned.
+the data in the DenemoObject concerned.
 Note that the structure node is arranged to have the same first fields
as
-mudelaobject so that either type can appear in the parse tree.
+DenemoObject so that either type can appear in the parse tree.
 
 */
-/*#define YYDEBUG 1*/
-/*#define DEBUG 1*/
+#define YYDEBUG 1
+#define YYPRINT fprintf
+//#define DEBUG 1
+#define YYTOKEN_TABLE 1
 #include <string.h> /*for memcpy */
 #include <stdlib.h> /* for system() */
 #include <sys/signal.h> /* for SIGINT and friends */
 #include <denemo/denemo.h>
 #include "view.h" /* this includes many others - many are not 
                     protected against double inclusion */
-/*#include "scoreops.h"*/
-/*#include "staffops.h"*/
 #include "chordops.h"
-/*#include "utils.h"*/
-/*#include "contexts.h"*/
 #include "objops.h"
 #include "twoints.h"
 #include "processstaffname.h"
-/*#include "exportmudela.h"*/
-/*#include "file.h"*/
 #include "tupletops.h"
 #include "graceops.h"
 
@@ -74,7 +70,7 @@
 static GtkWidget *parser_error_dialog;
 static int error_level_;
 /* lexer states FIXME */
-void push_notes_state(void);
+void push_note_state(void);
 void push_figuredbass_state(void);
 void push_chord_state(void);
 void push_lyric_state(void);
@@ -119,7 +115,8 @@
     name_value_pairs = g_hash_table_new (g_str_hash, g_str_equal);
   g_hash_table_insert (name_value_pairs, (gpointer)name,
(gpointer)value);
 #if DEBUG
-g_warning("Set identifier %s to value %p\n",name, value);
+//g_warning("Set identifier %s to value %p\n",name, value);
+g_print("Set identifier %s to value %s\n",name,  u_str(value->branch));
 #endif 
 }
 
@@ -130,6 +127,9 @@
        return nodeg;
 }
 
+#ifdef YYPRINT
+static gchar * type_name(gint type);
+#endif
 
 gboolean
 regular_identifier_b (char *s)
@@ -225,17 +225,16 @@
 %token DENEMO_MEASURES
 /* make a distinction for initial and other clef changes etc for
denemo 
    which would otherwise issue a change of clef etc at the start of
each staff */
-%token INITIAL_CLEF INITIAL_KEYSIG INITIAL_TIMESIG
 %token <generic> TEXT
 %token <gstr> staffcontext voicecontext lyricscontext
figuredbasscontext
 %token endcontext
 
 
-%token MUSICMODE
-%token TONEOPTION
+%token<gstr> MUSICMODE
+%token<gstr> TONEOPTION
 
 
-%token DYNAMICMARK
+%token<gstr> DYNAMICMARK
 
 
 
@@ -251,6 +250,7 @@
 %token <generic> ACCEPTS
 %token <generic> ALTERNATIVE
 %token <generic> BAR
+%token <generic> BREAK
 %token <generic> BREATHE
 %token <generic> CHORDMODIFIERS
 %token <generic> CHORDS
@@ -276,6 +276,7 @@
 %token <generic> KEY
 %token <generic> LYRICS
 %token <generic> MARK
+%token <generic> MARKUP
 %token <generic> MULTI_MEASURE_REST
 %token <generic> MIDI
 %token <generic> MM_T
@@ -285,7 +286,7 @@
 %token <generic> PITCHNAMES
 %token <generic> NOTES
 %token <generic> PAPER
-%token <generic> PARTIAL
+%token <generic> PARTIAL_
 %token <generic> PENALTY
 %token <generic> PROPERTY
 %token <generic> OVERRIDE SET REVERT 
@@ -295,7 +296,6 @@
 %token <generic> REPEAT
 %token <generic> ADDLYRICS
 %token <generic> PARTCOMBINE
-%token          SCM_T
 %token <generic> SCORE
 %token <generic> SCRIPT
 %token <generic> SKIP
@@ -312,17 +312,27 @@
 %token <generic> UNSET
 %token <minimal> CONTEXT
 %token <generic> LAYOUT
+%token <generic> LYRICSTO
+%token <generic> LYRICMODE
+%token <generic> NEWCONTEXT
+%token <generic> LILYVERSION
+%token <generic> DRUM_PITCH
+%token <generic> MUSIC_FUNCTION
 %token <i> REST
 
+%token DOUBLE_ANGLE_CLOSE ">>"
+%token DOUBLE_ANGLE_OPEN "<<"
+
+
 /* escaped */
-%token E_CHAR E_EXCLAMATION E_SMALLER E_BIGGER E_OPEN E_CLOSE
+%token <generic> E_CHAR E_EXCLAMATION E_SMALLER E_BIGGER E_OPEN E_CLOSE
 %token E_LEFTSQUARE E_RIGHTSQUARE E_TILDE
 %token E_BACKSLASH
 %token CHORD_BASS CHORD_COLON CHORD_MINUS CHORD_CARET
 %token <generic> FIGURE_SPACE
 
 
-%type <i>      exclamations questions dots optional_rest
+%type <i>      exclamations questions dots optional_rest 
 %type <i>      bass_number bass_mod
 %type <generic>        br_bass_figure bass_figure figure_list figure_spec
 
@@ -368,6 +378,7 @@
 %token <id>    STRING_IDENTIFIER 
 %token <gstr>      SCM_IDENTIFIER 
 %token <generic>       RESTNAME
+%token <generic>       SKIPNAME
 %token <gstr>  STRING_   
 %token <generic>       SCM_T
 %token <i>     UNSIGNED
@@ -375,15 +386,19 @@
 
 %type <scm> output_def
 %type <scm>    lilypond_header lilypond_header_body toplevel_expression
assignment score_block 
-%type <scm>    open_request_parens close_request_parens open_request
close_request
-%type <scm> request_with_dir request_that_take_dir verbose_request
+%type <scm>    direction_less_char  direction_less_event
direction_reqd_event
 %type <i>      sub_quotes sup_quotes
-%type <scm>    simple_element  request_chord command_element Simple_music
Composite_music 
+%type <scm>    simple_element  event_chord command_element Simple_music
Composite_music 
+%type <scm>    chord_body
+%type <scm>    chord_body_element
+%type <scm>    music_function_chord_body
+%type <scm>    chord_body_elements
 %type <scm>    Repeated_music
 %type <scm>     Alternative_music
 %type <i>      tremolo_type
 %type <i>      bare_int  bare_unsigned
 %type <i>      script_dir
+%type <i>      octave_check
 
 %type <branch> identifier_init 
 
@@ -391,8 +406,10 @@
 %type <f>      optional_notemode_duration multiplied_duration
 %type <f>       verbose_duration
        
-%type <scm>  pre_requests post_requests
+%type <scm>  post_events
+%type <scm>  note_chord_element
 %type <scm> gen_text_def
+%type <scm> full_markup
 %type <n>   steno_pitch pitch absolute_pitch
 %type <n>   explicit_pitch steno_tonic_pitch
 
@@ -409,17 +426,17 @@
 %type <scm> Music_list
 %type <scm>  music_output_def_body
 %type <scm> shorthand_command_req
-%type <scm>    post_request 
+%type <scm>    post_event
 %type <scm> command_req verbose_command_req
 %type <scm>    extender_req
 %type <scm> hyphen_req
-%type <gstr>   string
+%type <gstr>   string 
 %type <scm>    bare_number number_expression number_term number_factor 
 
 %type <scm>    score_body
 
 %type <scm>    translator_spec_block translator_spec_body
-%type <scm>    tempo_request
+%type <scm>    tempo_event tempo_optional
 %type <scm> notenames_body notenames_block chordmodifiers_block
 %type <scm>    script_abbreviation
 
@@ -437,14 +454,16 @@
 lilypond:      /* empty */
        | lilypond toplevel_expression { 
                if(lily_file)  {
-                       g_list_concat(lily_file, $2);
+                       GList *ret;
+                       ret = g_list_concat (lily_file, $2);
                } else {
                lily_file = $2;
                }
        }
        | lilypond assignment { 
                if(lily_file)  {
-                       g_list_concat(lily_file, $2);
+                       GList *ret;
+                       ret = g_list_concat(lily_file, $2);
                } else {
                lily_file = $2;
                }
@@ -494,6 +513,7 @@
        }
        | SCM_IDENTIFIER {
        MALLOC_NODE(n, $1);
+       ((nodegstr*)n)->gstr = $1.gstr;
        $$ = g_list_append(NULL, n);
        }
        ;
@@ -537,6 +557,15 @@
        $$ = g_list_concat($$,$3);
        $$ = g_list_append($$, n4);     
        }
+       |
+       LILYVERSION STRING_
+       {
+               MALLOC_NODE(n,$1);
+           g_free(n->user_string);
+           n->user_string = $2.gstr->str;
+       set_identifier("lilyversion", typed_glist (g_list_append(NULL,n),
STRING_IDENTIFIER));
+       $$ = NULL;
+       }
        ;
 
 
@@ -554,8 +583,12 @@
                                " only please"));
                }
 #if DEBUG
-               g_print("got to assignment with %s %s ...\n",$1.gstr->str, 
+               g_print("got to assignment with %s %s ",$1.gstr->str, 
                        $2.user_string);
+               if ($3->type == STRING_IDENTIFIER)
+                       g_print("%s\n", u_str($3->branch));
+               else
+                       g_print("type %d\n", $3->type);
 #endif
                /* $3 because mid rule action deleted */
                set_identifier ($1.gstr->str, $3);
@@ -587,7 +620,7 @@
        | Music  {
                $$ = typed_glist ($1, MUSIC_IDENTIFIER);
        }
-       | post_request {
+       | post_event {
                $$ = typed_glist ($1, REQUEST_IDENTIFIER);
        }
        | verbose_duration {
@@ -598,12 +631,16 @@
                $$ = typed_glist ($1, STRING_IDENTIFIER);
        }
        | string {
-               MALLOC_NODE(n,$1);
+               nodegeneric x;
+               x.type = STRING_IDENTIFIER;
+               x.user_string = strdup($1.gstr->str);
+               MALLOC_NODE(n,x);
                $$ = typed_glist (g_list_append(NULL,n), STRING_IDENTIFIER);
        }
        | embedded_scm  {
                $$ = typed_glist ($1, SCM_IDENTIFIER);
        }
+
        ;
 
 translator_spec_block:
@@ -624,9 +661,9 @@
 score_block:
        SCORE '{' score_body '}'        {
                MALLOC_NODE(n,$1);
-               n->user_string = g_strconcat($1.user_string, $2.user_string, 
NULL);
+               n->user_string = g_strconcat($1.user_string, "{" , NULL);
                /*FIXME memory leak of $1,2 */
-               ((nodeglist*)n)->post_user_string = $4.user_string;
+               ((nodeglist*)n)->post_user_string = "}";
                ((nodeglist*)n)->branch = $3;
                $$ = g_list_append(NULL, n);
        }
@@ -645,7 +682,7 @@
                /*intercept this at lexical level*/     
        }
        | score_body output_def {
-       g_error ("parser should have caught this");
+       //g_error ("parser should have caught this");
                /*intercept this at lexical level*/
        }
        | score_body error {
@@ -666,28 +703,39 @@
        }
        ;
 
+
 music_output_def_body:
-       PAPER '{'       {
+       MIDI '{' tempo_optional {
+               set_identifier("midi_tempo", typed_glist ($3, 
STRING_IDENTIFIER));
+               $$ = $3;
+       }
+       | PAPER '{'     {
                /* caught by lexer - does not occur*/
                g_error ("parser should have caught this");
        }
-       | music_output_def_body error {
-               lyerror("music_output_def_body error");
-               }
        | LAYOUT '{' {
                /* caught by lexer - does not occur*/
                g_error ("parser should have caught this");
        }
+       | music_output_def_body error {
+               lyerror("music_output_def_body error");
+               }
+       ;
+
+tempo_optional:
+       /* empty */ {
+               $$ = NULL;
+       }
+       | tempo_event {
+               $$ = $1;
+       }
        ;
 
-tempo_request:
+tempo_event:
        TEMPO steno_duration '=' bare_unsigned  {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               $$ = new Tempo_req;
-               $$->set_mus_property ("duration", $2);
-               $$->set_mus_property ("metronome-count", gh_int2scm ( $4));
-#endif
+       MALLOC_NODE(n, $4);
+       ((nodei*)n)->i = $4.i;
+       $$ = g_list_append(NULL, n);
        }
        ;
 
@@ -702,15 +750,21 @@
                $$ = NULL;
        }
        | Music_list Music {
-               if($1) {
+               if($1) 
+               {
 #if DEBUG
 g_print("building up a music list now from %s to %s\n", u_str($1),
u_str($2));
 #endif
                        $$ = g_list_concat($1, $2);
-                       }
+               }
                else 
                        $$ = $2;
-               }
+       }
+/*
+        | Music_list embedded_scm {
+
+        }
+*/
        | Music_list error {
        }
        ;
@@ -764,15 +818,16 @@
 Sequential_music:
        SEQUENTIAL '{' Music_list '}'           {
                MALLOC_NODE(n1, $1);
-               n1->user_string = g_strconcat($1.user_string, $2.user_string, 
NULL);
+               n1->user_string = g_strconcat($1.user_string, "{", NULL);
                /*FIXME memory leak $1,2 and $4*/
-               ((nodeglist*)n1)->post_user_string = $4.user_string;
+               ((nodeglist*)n1)->post_user_string = "}" ;
                ((nodeglist*)n1)->branch = $3;
                $$ = g_list_prepend(NULL, n1);
        }
        | '{' Music_list '}'            {
                MALLOC_NODE(n1, $1);
-               ((nodeglist*)n1)->post_user_string = $3.user_string;
+               n1->user_string = "{";  
+               ((nodeglist*)n1)->post_user_string = "}";
                /* FIXME memory leak of $3 */
                ((nodeglist*)n1)->type = SEQUENTIAL;
                ((nodeglist*)n1)->branch = $2;
@@ -790,11 +845,14 @@
                $$->set_spot(THIS->here_input());
 #endif
        }
-       |  '<' Music_list '>'   {
-       /* we don't try to disambiguate chords on one stave from notes one to
a staff here
+       |  simul_open  Music_list simul_close   {
+       /* we don't try to disambiguate chords on one stave from 
+          notes one to a staff here
           that is done in generate_chords() called by create_score() */
-               MALLOC_NODE(n1, $1);
-               ((nodeglist*)n1)->post_user_string = $3.user_string;
+// RRR         MALLOC_NODE(n1, $2);
+               nodegeneric*n1 = (nodegeneric*)g_malloc0(sizeof(nodegeneric));
+               n1->user_string = "<<";
+               ((nodeglist*)n1)->post_user_string = ">>";
                /* FIXME memory leak of $3 */
                ((nodeglist*)n1)->type = SIMULTANEOUS;
                ((nodeglist*)n1)->branch = $2;
@@ -803,7 +861,7 @@
        ;
 
 Simple_music:
-       request_chord           { $$ = $1; }
+       event_chord             { $$ = $1; }
        | OUTPUTPROPERTY embedded_scm embedded_scm '=' embedded_scm     {
 LATER_MESSAGE(@$.first_line);
 #ifdef LATER
@@ -831,7 +889,7 @@
 #endif
        }
        | MUSIC_IDENTIFIER { /* this may be ok now ... */
-               /* has to be big enough for mudelaobject access 
+               /* has to be big enough for DenemoObject access 
                   eg when writing start_ticks in break into measures... */
                nodeid *n = (nodeid*)g_malloc0(sizeof(nodegeneric));
                n->type = $1.type;
@@ -848,10 +906,10 @@
           amalgamate the strings into a TEXT node */
                
 
-}
+       }
        | translator_change {
        LATER_MESSAGE(@$.first_line);
-}
+       }
        ;
 
 
@@ -859,13 +917,13 @@
        CONTEXT STRING_ Music   {
                MALLOC_NODE (n1, $1);
                if(!strcmp("Staff",$2.gstr->str)) 
-                 $1.type = staffcontext;
+                 n1->type = staffcontext;
                else if(!strcmp("Voice",$2.gstr->str)) 
-                 $1.type = voicecontext;
+                 n1->type = voicecontext;
                else if(!strcmp("Lyrics",$2.gstr->str)) 
-                 $1.type = lyricscontext;
+                 n1->type = lyricscontext;
                else if(!strcmp("FiguredBass",$2.gstr->str)) 
-                 $1.type = figuredbasscontext;
+                 n1->type = figuredbasscontext;
                else 
                  n1->type = TEXT;/*ignore other contexts at present */
                n1->user_string = g_strconcat($1.user_string, $2.user_string, 
@@ -876,18 +934,6 @@
                        $$ = g_list_append(g_list_prepend($3, n1), 
                                           &endcontextnode);      
                /* FIXME memory leak of $2 */
-#if 0
-
-               Context_specced_music *csm =  
-                       new Context_specced_music (SCM_EOL);
-               csm->set_mus_property ("element", $3);
-               scm_gc_unprotect_object ($3);
-
-               csm->set_mus_property ("context-type",$2);
-               csm->set_mus_property ("context-id", scm_makfrom0str (""));
-
-               $$ = csm;
-#endif
        }
        | AUTOCHANGE STRING_ Music      {
 LATER_MESSAGE(@$.first_line);
@@ -906,7 +952,7 @@
 #endif
        }
        | GRACE Music {
-       mudelaobject *start, *end;
+       DenemoObject *start, *end;
        start = newgracestart();
        end =  newgraceend();
        start->user_string = $1.user_string;
@@ -930,7 +976,7 @@
                else 
                   n1->type = TEXT;/*ignore other contexts at present */
                n1->user_string = g_strconcat($1.user_string, $2.user_string, 
-                                             $3.user_string, $4.user_string, 
+                                             "=", $4.user_string, 
                                              NULL);    
                if (n1->type == TEXT)
                        $$ = g_list_prepend($5, n1);
@@ -939,9 +985,31 @@
                                           &endcontextnode);      
                /* FIXME memory leak $2 $3 $4 */
        }
+       | NEWCONTEXT STRING_ Music      {
+               MALLOC_NODE (n1, $1);
+               if(!strcmp("Staff",$2.gstr->str)) 
+                 n1->type = staffcontext;
+               else if(!strcmp("Voice",$2.gstr->str)) 
+                 n1->type = voicecontext;
+               else if(!strcmp("Lyrics",$2.gstr->str)) 
+               {
+                 n1->type = lyricscontext;
+               }
+               else if(!strcmp("FiguredBass",$2.gstr->str)) 
+                 n1->type = figuredbasscontext;
+               else 
+                 n1->type = TEXT;/*ignore other contexts at present */
+               n1->user_string = g_strconcat($1.user_string, $2.user_string, 
+                                             NULL);    
+               if (n1->type == TEXT)
+                       $$ = g_list_prepend($3, n1);
+               else
+                       $$ = g_list_append(g_list_prepend($3, n1), 
+                                          &endcontextnode);      
+       }
        | TIMES fraction Music  
 
-       {mudelaobject *tupopen, *tupclose;
+       {DenemoObject *tupopen, *tupclose;
                tupopen = newtupopen ($2.t.a, $2.t.b);
                tupclose = newtupclose ();
                g_assert(ntype($3)==SEQUENTIAL);
@@ -952,9 +1020,15 @@
                tupclose->user_string = u_post_str($3);
                $$ = g_list_append(g_list_prepend (br($3), tupopen), tupclose);
        }
-       | Repeated_music                { $$ = $1; }
-       | Simultaneous_music            { $$ = $1; }
-       | Sequential_music              { $$ = $1; }
+       | Repeated_music { 
+               $$ = $1; 
+       }
+       | Simultaneous_music    { 
+               $$ = $1; 
+       }
+       | Sequential_music      { 
+               $$ = $1; 
+       }
        | TRANSPOSE pitch Music {
 
                /* could we try to display transposed?? later FIXME */
@@ -985,7 +1059,7 @@
                $$ = g_list_concat($2, $3);
        }
        | NOTES
-               { push_notes_state (); }
+               { push_note_state (); }
                /* cont */
        Music
                { 
@@ -1025,9 +1099,23 @@
                $$ = g_list_prepend($3, n);
                pop_state();
        }
-       | relative_music        { $$ = $1; }
-       | re_rhythmed_music     { $$ = $1; } 
-       | part_combined_music   { $$ = $1; } 
+       | LYRICMODE 
+               { push_lyric_state (); }
+       Music
+               {
+               MALLOC_NODE(n, $1)
+               $$ = g_list_prepend($3, n);
+               pop_state();
+       }
+       | relative_music        { 
+               $$ = $1; 
+       }
+       | re_rhythmed_music     { 
+               $$ = $1; 
+       } 
+       | part_combined_music   { 
+               $$ = $1; 
+       } 
        ;
 
 relative_music:
@@ -1051,6 +1139,27 @@
                ((nodeglist*)n)->branch = g_list_append(g_list_append(NULL,
g_list_append(NULL, $2)), g_list_append(NULL, $3)); /* ADDLYRICS is a
branch containing two GLists */
                $$ = g_list_append(NULL, n);
        }
+       | LYRICSTO STRING_  Music {
+               GList *g;
+               MALLOC_NODE(n, $1);
+               g_free(n->user_string);
+               if (*$2.gstr->str == '\"')
+               {
+                   GString * name = g_string_erase ($2.gstr, 0, 1);
+                   name = g_string_truncate(name, name->len - 1);
+                   n->user_string = name->str;
+               }
+               else
+                   n->user_string = $2.gstr->str;
+               if (ntype ($3) == NEWCONTEXT)
+               {
+                   g = $3;
+                   $3 = g_list_remove_link ( $3, g);
+                   g_list_free(g);
+               }
+               ((nodeglist*)n)->branch = $3;
+               $$ = g_list_append(NULL, n);
+       }
        ;
 
 part_combined_music:
@@ -1092,8 +1201,8 @@
        PROPERTY STRING_ '.' STRING_ '='  scalar {
        MALLOC_NODE(n, $1)
         n->user_string = g_strconcat($1.user_string, $2.user_string, 
-                                     $3.user_string, $4.user_string, 
-                                     $5.user_string, u_str($6), NULL);
+                                     ".", $4.user_string, 
+                                     "=", u_str($6), NULL);
        $$ = g_list_append(NULL, n); /* FIXME memory leak*/
        }
        | PROPERTY STRING_ '.' STRING_ UNSET {
@@ -1107,7 +1216,13 @@
        MALLOC_NODE(n, $1)
        n->user_string = g_strconcat($1.user_string, $2.user_string, 
                                     $3.user_string, $4.user_string, 
$5.user_string, u_str($6),
NULL);
-       g_print ("%s\n", n->user_string);
+       $$ = g_list_append(NULL, n);
+       }
+       | SET STRING_ '.' STRING_ '=' STRING_ {
+       MALLOC_NODE(n, $1)
+       n->user_string = g_strconcat($1.user_string, $2.user_string, 
+                                    $3.user_string, $4.user_string, 
+                               $5.user_string, $6.user_string, NULL);
        $$ = g_list_append(NULL, n);
        }
        | OVERRIDE STRING_ '.' STRING_ '=' embedded_scm {
@@ -1117,12 +1232,26 @@
                                     $5.user_string, u_str($6), NULL);
        $$ = g_list_append(NULL, n);
        }
+        | OVERRIDE STRING_ embedded_scm '=' embedded_scm {
+       MALLOC_NODE(n, $1);
+       n->user_string = g_strconcat($1.user_string, $2.user_string, 
+                                    u_str ($3), $4.user_string, 
+                                    u_str ($5), NULL);
+       $$ = g_list_append (NULL, n);
+        }
+        | REVERT STRING_ embedded_scm {
+       MALLOC_NODE(n, $1);
+       n->user_string = g_strconcat($1.user_string, $2.user_string, 
+                                    u_str ($3), NULL);
+       $$ = g_list_append (NULL, n);
+        }
+
        | PROPERTY STRING_ '.' STRING_ REVERT embedded_scm {
        MALLOC_NODE(n, $1);
        n->user_string = g_strconcat($1.user_string, $2.user_string, 
                                     $3.user_string, $4.user_string, 
-                                    $5.user_string, u_str($6), NULL);
-       $$ = g_list_append(NULL, n);
+                                    $5.user_string, u_str ($6), NULL);
+       $$ = g_list_append (NULL, n);
        }
        ;
 
@@ -1135,60 +1264,122 @@
         | embedded_scm  { $$ = $1; }
         ;
 
+pre_events: /* empty */
+       ;
 
-request_chord:
-       pre_requests simple_element post_requests       {
+event_chord:
+       pre_events simple_element post_events   {
 /* things like start cresc, simple_element end cresc */
-       GList *g;
-       for (g = $1;g;g=g->next) {
-               mudelaobject *mud = (mudelaobject *)($2->data);
-               u_str($2) = g_strconcat(u_str(g), u_str($2), NULL);
-               switch (ntype(g)) {     
-               case ')':
-                       g_assert(mud->type == CHORD);
-                       ((chord *)(mud->object))->slur_end_p = TRUE;
-               break;  
-               default: g_warning("type %d not presented graphically\nsee 
lyparser.h
for types", 
-                               ntype(g));
-               break;
-               }
-       }
-
-       for (g = $3;g;g=g->next) {
-               mudelaobject *mud = (mudelaobject *)($2->data);
-               u_str($2) = g_strconcat(u_str($2), u_str(g), NULL);
-               switch (ntype(g)) {
-               case '(':
-                       g_assert(mud->type == CHORD);
-                       ((chord *)(mud->object))->slur_begin_p = TRUE;
-               break;
-               case TONEOPTION:
-                       g_assert(mud->type == CHORD);
-                       set_tone_option(mud, gstr(g)->str);
-                       break;
-               case DYNAMICMARK:
-                       {
-                       g_assert(mud->type == CHORD);
-                       ((chord *)(mud->object))->dynamics = 
-                               g_list_append(((chord 
*)(mud->object))->dynamics, gstr(g));
-                       }
-               break;
-
-
-               default: g_warning("type %d not presented graphically\nsee 
lyparser.h
for types", 
-                               ntype(g));
-               break;
-               }
-       }
 
+       set_post_events ((DenemoObject *) ($2->data), u_str ($2), $3);
                        
        $$ = $2;/* FIXME memory leak */
        }
        | command_element {
        $$ = $1;
        }
+       | note_chord_element {
+               $$ = $1;
+       }
+       ;
+
+note_chord_element:
+       chord_body optional_notemode_duration post_events
+       {
+           GList *firstchord = br ($1);
+           if (firstchord && firstchord->data)
+               changedur ((DenemoObject *)(firstchord->data), $2.t1.a, 
$2.t1.b);
+           set_post_events ((DenemoObject *) ($1->data), u_str ($1), $3);
+           $$ = $1;
+       }
+       ;
+
+
+chord_open: '<'
+       ;
+
+chord_close: '>'
+       ;
+
+chord_body:
+       chord_open chord_body_elements chord_close
+       {
+           nodegeneric*n1 = (nodegeneric*)g_malloc0(sizeof(nodegeneric));
+           n1->user_string = "<";      
+           ((nodeglist*)n1)->post_user_string = ">";
+           ((nodeglist*)n1)->type = SIMULTANEOUS;
+           ((nodeglist*)n1)->branch = $2;
+           $$ = g_list_prepend(NULL, n1);
+       }
+       ;
+
+chord_body_elements:
+       /* empty */          { $$ = NULL; }
+       | chord_body_elements chord_body_element {
+               $$ = g_list_concat ($1, $2);
+       }
+       ;
+
+music_function_chord_body:
+        MUSIC_FUNCTION {
+LATER_MESSAGE(@$.first_line);
+#ifdef LATER
+                $$ = scm_list_2 ($1, make_input (@$));
+#endif
+        }
+
        ;
 
+chord_body_element:
+       pitch exclamations questions  octave_check post_events {
+               DenemoObject *mud = newchord ( 0, 0, 0);
+
+               if (!note_state_b ())
+                       g_error (_ ("Have to be in Note mode for notes"));
+
+               addtone ( mud, $1.n.mid_c_offset, $1.n.enshift, 0);/*FIXME 
should be
+                                                       using $1.n directly */
+
+#define no ((note*)((((chord *)mud->object)->tones)->data))
+               if ($3.i % 2) 
+               {
+                       no->showaccidental = TRUE;
+                       ( (chord *)mud->object)->hasanacc = TRUE;
+               }
+               if ($2.i % 2 ) {
+                       no->showaccidental = TRUE;
+                       ( (chord *)mud->object)->hasanacc = TRUE;
+               }
+#undef no
+
+               mud->user_string = $1.user_string;
+               if ($2.i) stradd ( (*mud),$2);
+               if ($3.i) stradd ( (*mud),$3);
+               //stradd ( (*mud),$4);
+
+               set_post_events (mud, mud->user_string, $5);
+               $$ = g_list_append (NULL,mud);
+        }
+        | DRUM_PITCH post_events {
+LATER_MESSAGE(@$.first_line);
+#ifdef LATER
+                Music *n = MY_MAKE_MUSIC ("NoteEvent");
+                n->set_property ("duration", $2);
+                n->set_property ("drum-type", $1);
+                n->set_spot (@$);
+
+                if (scm_is_pair ($2)) {
+                        SCM arts = scm_reverse_x ($2, SCM_EOL);
+                        n->set_property ("articulations", arts);
+                }
+                $$ = n;
+#endif // LATER
+        }
+        | music_function_chord_body {
+LATER_MESSAGE(@$.first_line);
+        }
+        ;
+
 command_element:
        command_req {
        $$ = $1;
@@ -1204,7 +1395,7 @@
 
                $$ = new Request_chord (SCM_EOL);
                $$->set_mus_property ("elements", gh_cons (l, SCM_EOL));
-         scm_gc_unprotect_object (l->self_scm());
+         scm_gc_unprotect_object (l->self_scm ());
                $$->set_spot (THIS->here_input ());
 #endif
        }
@@ -1220,7 +1411,7 @@
                $$ = new Request_chord (SCM_EOL);
                $$->set_mus_property ("elements", gh_cons (l, SCM_EOL));
                $$->set_spot (THIS->here_input ());
-         scm_gc_unprotect_object (l->self_scm());
+         scm_gc_unprotect_object (l->self_scm ());
 #endif
        }
        | E_BACKSLASH {
@@ -1240,54 +1431,31 @@
 
                  n->user_string = g_strconcat($1.user_string, $2.user_string,
NULL);/* FIXME memory leaks */
                  $$ = g_list_append(NULL, n);
-#ifdef LATER
-
-               Music *t = set_property_music (ly_symbol2scm ("whichBar"), $2);
-
-               Context_specced_music *csm = new Context_specced_music 
(SCM_EOL);
-               csm->set_mus_property ("element", t);
-               scm_gc_unprotect_object (t);
-
-               $$ = csm;
-               $$->set_spot (THIS->here_input ());
-
-               csm->set_mus_property ("context-type", scm_makfrom0str 
("Score"));
-#endif
        }
-       | PARTIAL duration_length       {
-               mudelaobject *mud = newchord( $2.t1.a, $2.t1.b,0);
-               mud->type = (enum objtype)PARTIAL;
+       | PARTIAL_ duration_length      {
+       //      g_warning ("\\partial not currently supported");
+               DenemoObject *mud = newchord( $2.t1.a, $2.t1.b,0);
+               mud->type = PARTIAL;
 /* FIXME - we need to store all four ints then use them to determine
how much measure to skip */
                mud->user_string = g_strconcat($1.user_string, 
$2.user_string,NULL);
                /* FIXME memory leaks on strings concatenated */
                $$ = g_list_append(NULL,mud);
-
-
-#if 0
-
-               Moment m = - unsmob_duration ($2)->length_mom ();
-               Music * p = set_property_music (ly_symbol2scm
( "measurePosition"),m.smobbed_copy ());
-
-               Context_specced_music * sp = new Context_specced_music 
(SCM_EOL);
-               sp->set_mus_property ("element", p);
-               scm_gc_unprotect_object (p);
-
-               $$ =sp ;
-               sp-> set_mus_property ("context-type", scm_makfrom0str ( 
"Score"));
-#endif
        }
        | CLEF_ STRING_  {
-               mudelaobject *mud = newclefobj (cleftypefromname($2.gstr->str));
+               DenemoObject *mud = dnm_newclefobj
(cleftypefromname($2.gstr->str));
                mud->user_string = g_strconcat($1.user_string, 
$2.user_string,NULL);
                /* FIXME memory leaks on strings concatenated */
                $$ = g_list_append(NULL,mud);
        }
        | TIME_T fraction  {
-               mudelaobject *mud = newtimesigobj ($2.t.a, $2.t.b);
+               DenemoObject *mud = dnm_newtimesigobj ($2.t.a, $2.t.b);
                mud->user_string = g_strconcat($1.user_string, 
$2.user_string,NULL);
                /* FIXME memory leaks on strings concatenated */
                $$ = g_list_append(NULL,mud);
        }
+       | BREAK { /* ignore */
+               $$ = NULL;
+       }
        ;
 
 command_req:
@@ -1302,42 +1470,15 @@
        | hyphen_req {
                $$ = $1;
        }
-       | '~'   {
-       MALLOC_NODE(n, $1)
-       $$ = g_list_append(NULL, n);
-#if 0
-
-               $$ = new Tie_req;
-#endif
-       }
        | '['           {
        MALLOC_NODE(n, $1)
        $$ = g_list_append(NULL, n);/* FIXME denemo should know about this */
-
-
-#if 0
-
-               Span_req*b= new Span_req;
-               b->set_span_dir (START);
-               b->set_mus_property ("span-type", scm_makfrom0str ("beam"));
-               $$ =b;
-
-
-               THIS->last_beam_start_ = b;
-#endif
        }
        | ']'           {       
        MALLOC_NODE(n, $1)
        $$ = g_list_append(NULL, n);/* FIXME denemo should know about this */
 
 
-#if 0
-
-               Span_req*b= new Span_req;
-               b->set_span_dir ( STOP);
-               b->set_mus_property ("span-type", scm_makfrom0str ("beam"));
-               $$ = b;
-#endif
        }
        | BREATHE {
 LATER_MESSAGE(@$.first_line);
@@ -1383,19 +1524,6 @@
                $$ = m;
 #endif
        }
-       | PENALTY SCM_T         {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Break_req * b = new Break_req;
-               SCM s = $2;
-               if (!gh_number_p (s))
-                       s  =gh_int2scm (0);
-
-               b->set_mus_property ("penalty", s);
-               b->set_spot (THIS->here_input ());
-               $$ = b;
-#endif
-       }
        | SKIP duration_length {
        /* denemo doesn't want to know? */
        MALLOC_NODE(n, $1)
@@ -1411,8 +1539,9 @@
                $$ = skip;
 #endif
        }
-       | tempo_request {
-               $$ = $1;
+       | tempo_event {
+LATER_MESSAGE(@$.first_line);
+//             $$ = $1;
        }
        | KEY DEFAULT {
 LATER_MESSAGE(@$.first_line);
@@ -1422,144 +1551,67 @@
                $$ = key;
 #endif
        }
-       | KEY NOTENAME_PITCH SCM_IDENTIFIER     {
+       | KEY NOTENAME_PITCH MUSICMODE  {
                gchar *keyname = keytoname($2.t.a, $2.t.b);
-               mudelaobject *mud;
+               DenemoObject *mud;
                /* the convoluted conversion is due to historical mismatch of 
lily
and denemo*/
                if (!strcmp($3.gstr->str, "minor"))     
-                       mud = newkeyobj(keynametonumber(keyname)-3, TRUE, 0);
+                       mud = dnm_newkeyobj(keynametonumber(keyname)-3, TRUE, 
0);
                else
-                       mud = newkeyobj(keynametonumber(keyname), FALSE, 0);
+                       mud = dnm_newkeyobj(keynametonumber(keyname), FALSE, 0);
                mud->user_string = g_strconcat($1.user_string, $2.user_string,
$3.user_string, NULL);
                $$ = g_list_append(NULL,mud);
        }
        ;
 
-post_requests:
+post_events:
        {
        $$ = NULL;
        }
-       | post_requests post_request {
+       | post_events post_event {
                if($1) {
                        $$ = g_list_concat($1, $2);
                        }
                else 
                        $$ = $2;
-#if 0
-               $2->set_spot (THIS->here_input ());
-               $$->push ($2);
-#endif
        }
        ;
 
-post_request:
-       verbose_request
-       | request_with_dir
-       | close_request {
-       $$ = $1;
-       }
+post_event:
+        direction_less_event {
+                $$ = $1;
+        }
+        | script_dir direction_reqd_event {
+          /* script_dir is an integer saying whether up down or centred
+             denemo doesn't understand this yet */
+           u_str($2) = g_strconcat ( $1.user_string, u_str($2), NULL);
+           $$ = $2;
+        }
+        | script_dir direction_less_event {
+          /* script_dir is an integer saying whether up down or centred
+             denemo doesn't understand this yet */
+           u_str($2) = g_strconcat ( $1.user_string, u_str($2), NULL);
+           $$ = $2;
+        }
        ;
 
 
-request_that_take_dir:
-       gen_text_def
-       | verbose_request
-       | script_abbreviation {
-       $$ = $1;
-#if 0
-               SCM s = THIS->lexer_->lookup_identifier ("dash" + ly_scm2string
($1));
-               Articulation_req *a = new Articulation_req;
-               if (gh_string_p (s))
-                       a->set_mus_property ("articulation-type", s);
-               else THIS->parser_error (_ ("Expecting string as script
definition"));
-               $$ = a;
-#endif
-       }
-       ;
-
-request_with_dir:
-       script_dir request_that_take_dir        {
-       /* script_dir is an integer saying whether up down or centred
-          denemo doesn't understand this yet */
-       u_str($2) = g_strconcat ( $1.user_string, u_str($2), NULL);
-       $$ = $2;
-#if 0
-               if (Script_req * gs = dynamic_cast<Script_req*> ($2))
-                       gs->set_direction (Direction ($1));
-               else if ($1)
-                       $2->origin ()->warning (_ ("Can't specify direction for 
this
request"));
-               $$ = $2;
-#endif
-       }
-       ;
-       
-verbose_request:
-       REQUEST_IDENTIFIER      {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               $$ = dynamic_cast<Request*> (unsmob_music ($1)->clone ());
-               $$->set_spot (THIS->here_input ());
-#endif
-       }
-       | DYNAMICSCRIPT embedded_scm {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               /*
-                       TODO: junkme, use text-type == dynamic
-               */
-               Text_script_req *d = new Text_script_req;
-               SCM dyn = ly_symbol2scm ("dynamic");
-               d->set_mus_property ("text-type" , dyn);
-               d->set_mus_property ("text", $2);
-               d->set_spot (THIS->here_input ());
-               $$ = d;
-#endif
-       }
-       | SPANREQUEST bare_int STRING_ {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Span_req * sp = new Span_req;
-               sp->set_span_dir ( Direction ($2));
-               sp->set_mus_property ("span-type", $3);
-               sp->set_spot (THIS->here_input ());
-               $$ = sp;
-#endif
-       }
-       | tremolo_type  {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Tremolo_req* a = new Tremolo_req;
-               a->set_spot (THIS->here_input ());
-               a->set_mus_property ("tremolo-type", gh_int2scm ($1));
-               $$ = a;
+direction_reqd_event:
+        gen_text_def {
+                $$ = $1;
         }
-       | SCRIPT STRING_        { 
-               Articulation_req * a = new Articulation_req;
-               a->set_mus_property ("articulation-type", $2);
-               a->set_spot (THIS->here_input ());
-               $$ = a;
-#endif
-       }
-       /*
-duh, junk this syntax from the parser, if possible. 
-       */
-       | ARPEGGIO {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Arpeggio_req *a = new Arpeggio_req;
-               a->set_spot (THIS->here_input ());
-               $$ = a;
-#endif
-       }
-       | GLISSANDO {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Glissando_req *g = new Glissando_req;
-               g->set_spot /* No pun intended */ (THIS->here_input ());
-               $$ = g;
-#endif
-       }       
-       ;
+        | script_abbreviation {
+               $$ = $1;
+        }
+        ;
+
+octave_check:
+        /**/ {  }
+        | '='  { $$.i = 0; }
+        | '=' sub_quotes { $$ = $2; }
+        | '=' sup_quotes { $$ = $2; }
+        ;
+
 
 sup_quotes:
        '\'' {
@@ -1700,88 +1752,51 @@
        }
        ;
 
-close_request:
-       close_request_parens {
+direction_less_event:
+        direction_less_char {
               $$ = $1;
-#if 0
-               $$ = $1;
-               dynamic_cast<Span_req*> ($$)->set_span_dir ( START);
-#endif
+       }
+       | DYNAMICMARK {
+           MALLOC_NODE(n, $1);
+           ((nodegstr*)n)->gstr = $1.gstr;
+           $$ = g_list_append(NULL, n);
+       }
+       | TONEOPTION {
+           MALLOC_NODE(n, $1);
+           ((nodegstr*)n)->gstr = $1.gstr;
+           $$ = g_list_append(NULL, n);
+       }
+       | tremolo_type  {
+LATER_MESSAGE(@$.first_line);
        }
        ;
  
-close_request_parens:
+direction_less_char:
        '('     {
-         $$ = g_list_append(NULL, &$1);
-#if 0
-               Span_req* s= new Span_req;
-               $$ = s;
-               s->set_mus_property ("span-type", scm_makfrom0str ( "slur"));
-               s->set_spot (THIS->here_input());
-#endif
+           MALLOC_NODE(n, $1)
+            $$ = g_list_append(NULL, n);
        }
-       | E_OPEN        {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Span_req* s= new Span_req;
-               $$ = s;
-               s->set_mus_property ("span-type", scm_makfrom0str
( "phrasing-slur"));
-               s->set_spot (THIS->here_input());
-#endif
+       | ')'   {
+           MALLOC_NODE(n, $1)
+            $$ = g_list_append(NULL, n);
+       }
+       | '~'   {       /* tie */
+           MALLOC_NODE(n, $1)
+            $$ = g_list_append(NULL, n);
        }
        | E_SMALLER {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Span_req*s =new Span_req;
-               $$ = s;
-               s->set_mus_property ("span-type", scm_makfrom0str ( 
"crescendo"));
-               s->set_spot (THIS->here_input());
-#endif
+           MALLOC_NODE(n, $1)
+            $$ = g_list_append(NULL, n);
        }
        | E_BIGGER {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Span_req*s =new Span_req;
-               $$ = s;
-               s->set_mus_property ("span-type", scm_makfrom0str 
("decrescendo"));
-               s->set_spot (THIS->here_input());
-#endif
-       }
-       ;
-
-
-open_request:
-       open_request_parens {
-               $$ = $1;
-#if 0
-               $$ = $1;
-               dynamic_cast<Span_req*> ($$)->set_span_dir (STOP);
-#endif
+           MALLOC_NODE(n, $1)
+            $$ = g_list_append(NULL, n);
        }
-       ;
-
-open_request_parens:
-       E_EXCLAMATION   {
-LATER_MESSAGE(@$.first_line);
-#ifdef LATER
-               Span_req *s =  new Span_req;
-               s->set_mus_property ("span-type", scm_makfrom0str ( 
"crescendo"));
-               s->set_spot (THIS->here_input());
-
-               $$ = s;
-#endif
-       }
-       | ')'   {
-       $$ = g_list_append(NULL, &$1);
-#if 0
-               Span_req* s= new Span_req;
-               $$ = s;
-               s->set_mus_property ("span-type", scm_makfrom0str ( "slur"));
-               s->set_spot (THIS->here_input());
-
-#endif
+       | E_EXCLAMATION {
+           MALLOC_NODE(n, $1)
+            $$ = g_list_append(NULL, n);
        }
-       | E_CLOSE       {
+       | E_OPEN        {
 LATER_MESSAGE(@$.first_line);
 #ifdef LATER
                Span_req* s= new Span_req;
@@ -1792,24 +1807,32 @@
        }
        ;
 
-gen_text_def:
-       embedded_scm {
-        $$ = $1;
-#if 0
-               Text_script_req *t = new Text_script_req;
-               t->set_mus_property ("text", $1);
-               t->set_spot (THIS->here_input ());
-               $$ = t;
-#endif
+full_markup:
+       MARKUP {
+LATER_MESSAGE(@$.first_line);
        }
-       | string {
+       ;
+gen_text_def:
+        full_markup {
 LATER_MESSAGE(@$.first_line);
 #ifdef LATER
-               Text_script_req *t = new Text_script_req;
-               t->set_mus_property ("text", $1);
-               t->set_spot (THIS->here_input ());
-               $$ = t;
+                Music *t = MY_MAKE_MUSIC ("TextScriptEvent");
+                t->set_property ("text", $1);
+                t->set_spot (@$);
+                $$ = t;
 #endif
+        }
+/* JAN
+       DYNAMICMARK {
+       MALLOC_NODE(n, $1);
+       ((nodegstr*)n)->gstr = $1.gstr;
+       $$ = g_list_append(NULL, n);
+       }
+*/
+       | string {
+           MALLOC_NODE(n, $1);
+           ((nodegstr*)n)->gstr = $1.gstr;
+           $$ = g_list_append(NULL, n);
        }
        | DIGIT {
 LATER_MESSAGE(@$.first_line);
@@ -1876,22 +1899,6 @@
        | '-'   {  /* $$ = CENTER; */ }
        ;
 
-pre_requests:
-       {
-       $$ = NULL;
-       }
-       | pre_requests open_request {
-               if($1) {
-                       $$ = g_list_concat($1, $2);
-                       }
-               else 
-                       $$ = $2;
-#if 0
-
-               $$->push ($2);
-#endif
-       }
-       ;
 
 absolute_pitch:
        steno_pitch     {
@@ -1974,7 +1981,7 @@
        stradd($1,$2);  
        stradd($1,$3);
        $1.t2.a *= $3.t.a; /* numerator of fraction */
-       $1.t2.b *= $3.t.b; /* denominator of fraction */
+       $1.t2.b  = $3.t.b; /* denominator of fraction */
        $$ = $1;
 
 #ifdef LATER
@@ -2084,20 +2091,26 @@
        | REST { $$.i = 1; }
        ;
 
+       ;
+
 simple_element:
-       pitch exclamations questions optional_notemode_duration optional_rest
{
-               /* pitch is a node* with union a denemo note, exclamations and
questions are nodei,
-                optional_notemode_duration is now a node4i, but I don't know 
how to
calculate
-               with the multiplier fraction in the top two ints, optional rest 
is
boolean for
-               the \rest keyword appearing after a note - it turns it into a 
rest
-               the duration is on the chord structure, the pitch on the note
structure.
-               print
*(note*)(((mudelaobject*)(((GList*)(((staff*)si->thescore->data)->measures->data))->data))->u.chordval.tones.data)
+       pitch exclamations questions octave_check optional_notemode_duration
optional_rest  {
+               /* pitch is a node* with union a denemo note, 
+                  exclamations and questions are nodei,
+                  optional_notemode_duration is now a node4i, 
+                       but I don't know how to calculate with 
+                       the multiplier fraction in the top two ints, 
+                 optional rest is boolean for the \rest keyword 
+                       appearing after a note - it turns it into a rest
+                 the duration is on the chord structure, 
+                 the pitch on the note structure.
+               print
*(note*)(((DenemoObject*)(((GList*)(((staff*)si->thescore->data)->measures->data))->data))->u.chordval.tones.data)
                 */ 
-               mudelaobject *mud = newchord( $4.t1.a, $4.t1.b,0);
+               DenemoObject *mud = newchord( $5.t1.a, $5.t1.b, 0);
 
                if (!note_state_b ())
                        g_error (_ ("Have to be in Note mode for notes"));
-               if ($5.i)
+               if ($6.i)
                        /* this is a rest vertically placed at the note
                           no special representation in denemo yet */;
                else {
@@ -2116,49 +2129,33 @@
 #undef no
                }
                mud->user_string = $1.user_string;
-               if($2.i) stradd((*mud),$2);
-               if($3.i) stradd((*mud),$3);
-               stradd((*mud),$4);
-               if($5.i) stradd((*mud),$5); /* FIXME memory leaks on strings
concatenated */
+               if ($2.i) stradd ( (*mud),$2);
+               if ($3.i) stradd ( (*mud),$3);
+               stradd ( (*mud),$5);
+               if ($6.i) stradd ( (*mud),$6); /* FIXME memory leaks on strings
concatenated */
 
-               $$ = g_list_append(NULL,mud);
+               $$ = g_list_append (NULL,mud);
        }
        | figure_spec optional_notemode_duration {
                /* based on simple_element */
-               mudelaobject *mud = newfigure($2.t1.a, $2.t1.b, $1.user_string);
+               DenemoObject *mud = newfigure ($2.t1.a, $2.t1.b, 
$1.user_string);
                mud->user_string = $1.user_string;
-               stradd((*mud),$2);
-               $$ = g_list_append(NULL,mud);
+               stradd ( (*mud),$2);
+               $$ = g_list_append (NULL,mud);
        }       
        | RESTNAME optional_notemode_duration           {
        /* denemo wants a chord with no tones */
-       mudelaobject *mud = newchord( $2.t1.a, $2.t1.b,0);
+       DenemoObject *mud = newchord( $2.t1.a, $2.t1.b,0);
 
        mud->user_string = g_strconcat($1.user_string, $2.user_string, NULL);
        $$ = g_list_append(NULL,mud); 
-#if 0
-
-               Input i = THIS->pop_spot ();
-               SCM e = SCM_UNDEFINED;
-               if (ly_scm2string ($1) =="s") {
-                       /* Space */
-                       Skip_req * skip = new Skip_req;
-                       skip->set_mus_property ("duration" ,$2);
-                       skip->set_spot (i);
-                       e = skip;
-                 }
-                 else {
-                       Rest_req * rest_req = new Rest_req;
-                       rest_req->set_mus_property ("duration", $2);
-                       rest_req->set_spot (i);
-                       e = rest_req;
-                   }
-               Simultaneous_music* velt = new Request_chord (SCM_EOL);
-               velt-> set_mus_property ("elements", scm_list_n 
(e,SCM_UNDEFINED));
-               velt->set_spot (i);
-
-               $$ = velt;
-#endif
+       }
+       | SKIPNAME optional_notemode_duration           {
+       /* denemo wants a chord with no tones */
+       DenemoObject *mud = newchord( $2.t1.a, $2.t1.b,0);
+       mud->type = SKIPNAME;
+       mud->user_string = g_strconcat($1.user_string, $2.user_string, NULL);
+       $$ = g_list_append(NULL,mud); 
        }
        | MULTI_MEASURE_REST optional_notemode_duration         {
 LATER_MESSAGE(@$.first_line);
@@ -2189,8 +2186,9 @@
 #endif
        }
        | STRING_ optional_notemode_duration    {
-               mudelaobject *mud = newlyric($2.t1.a, $2.t1.b, $1.user_string);
+               DenemoObject *mud = newlyric($2.t1.a, $2.t1.b, $1.gstr->str);
                mud->user_string = $1.user_string;
+               mud->type = LYRICS;
                stradd((*mud),$2);
                $$ = g_list_append(NULL,mud);
        }
@@ -2206,6 +2204,12 @@
        }
        ;
 
+simul_open: DOUBLE_ANGLE_OPEN
+        ;
+
+simul_close: DOUBLE_ANGLE_CLOSE
+        ;
+
 
 chord:
        steno_tonic_pitch optional_notemode_duration chord_additions
chord_subtractions chord_inversion chord_bass {
@@ -2540,11 +2544,11 @@
 static objnode *
 use_up_ticks (objnode * h, gint ticks)
 {
-  mudelaobject *figmud = (mudelaobject *) h->data;
+  DenemoObject *figmud = (DenemoObject *) h->data;
   while (ticks > 0)
     {
       h = h->next;
-      figmud = h ? (mudelaobject *) h->data : NULL;
+      figmud = h ? (DenemoObject *) h->data : NULL;
       if (!figmud)
        {
          g_warning ("Insufficient figures for bass part");
@@ -2559,10 +2563,10 @@
 create_figures (GList * b, GList * f)
 {
   objnode *h = (objnode *) f->data;
-  mudelaobject *figmud;
+  DenemoObject *figmud;
 
-  for (figmud = (mudelaobject *) h->data; figmud;
-       h = h->next, figmud = h ? (mudelaobject *) h->data : NULL)
+  for (figmud = (DenemoObject *) h->data; figmud;
+       h = h->next, figmud = h ? (DenemoObject *) h->data : NULL)
     {
       if (figmud->type == CHORD)
        return FALSE;           /* there are already figures present */
@@ -2572,9 +2576,9 @@
   for (; b && b->data; b = b->next)
     {
       objnode *g = (objnode *) b->data;
-      mudelaobject *mud;
-      for (mud = (mudelaobject *) g->data; mud;
-          g = g->next, mud = (g ? (mudelaobject *) g->data : NULL))
+      DenemoObject *mud;
+      for (mud = (DenemoObject *) g->data; mud;
+          g = g->next, mud = (g ? (DenemoObject *) g->data : NULL))
        {
          if (mud->type == CHORD)
            {
@@ -2592,9 +2596,9 @@
          if (mud->type == TUPOPEN || mud->type == TUPCLOSE
              || mud->type == GRACE_START || mud->type == GRACE_END)
            {
-             mudelaobject *figmud =
-               (mudelaobject *) g_malloc0 (sizeof (mudelaobject));
-             memcpy (figmud, mud, sizeof (mudelaobject));
+             DenemoObject *figmud =
+               (DenemoObject *) g_malloc0 (sizeof (DenemoObject));
+             memcpy (figmud, mud, sizeof (DenemoObject));
              f->data = g_list_append ((GList *) f->data, figmud);
            }
        }
@@ -2608,9 +2612,9 @@
 static objnode *
 next_figure (objnode * h)
 {
-  mudelaobject *figmud;
-  for (figmud = (mudelaobject *) h->data; figmud;
-       h = h->next, figmud = h ? (mudelaobject *) h->data : NULL)
+  DenemoObject *figmud;
+  for (figmud = (DenemoObject *) h->data; figmud;
+       h = h->next, figmud = h ? (DenemoObject *) h->data : NULL)
     {
       if (figmud->type == CHORD)
        return h;
@@ -2623,7 +2627,7 @@
 FIGURES; create blank figures for each note present in BASS if none is
present in
 FIGURES, abort if incomplete figures present */
 static void
-fill_in_figures (staff * bass, staff * figures)
+fill_in_figures (DenemoStaff * bass, DenemoStaff * figures)
 {
   GList *b = bass->measures, *f = figures->measures;
   /* if there are no figures create a set cloning the durations from
bass */
@@ -2635,9 +2639,9 @@
     {
       objnode *g = (objnode *) b->data;
       objnode *h = (objnode *) f->data;
-      mudelaobject *mud;
-      for (mud = (mudelaobject *) g->data; mud;
-          g = g->next, mud = (g ? (mudelaobject *) g->data : NULL))
+      DenemoObject *mud;
+      for (mud = (DenemoObject *) g->data; mud;
+          g = g->next, mud = (g ? (DenemoObject *) g->data : NULL))
        {
 
          if (mud->type == CHORD)
@@ -2657,7 +2661,7 @@
                    h =
                      use_up_ticks (h,
                                    mud->basic_durinticks -
-                                   ((mudelaobject *) h->data)->
+                                   ((DenemoObject *) h->data)->
                                    basic_durinticks);
                }               /* if h */
 
@@ -2668,7 +2672,7 @@
                }
              h = h ? h->next : NULL;
            }                   /* if mud is CHORD */
-       }                       /* end of for each mudelaobject in the measure 
*/
+       }                       /* end of for each DenemoObject in the measure 
*/
     }                          /* for each measure */
 }
 
@@ -2677,10 +2681,10 @@
    Fill in any figured bass staff that is short of figures with blank
figures.
  */
 static void
-fixup_measure_widths_and_contexts (scoreinfo * si)
+fixup_measure_widths_and_contexts (DenemoScore * si)
 {
   GList *g = si->thescore;
-  staff *curstaffstruct = staffstruct (g);
+  DenemoStaff *curstaffstruct = staffstruct (g);
   int i, num_measures = 0;
   /* find num_measures of longest staff */
   for (g = si->thescore; g; g = g->next)
@@ -2856,7 +2860,7 @@
 
     }
   if( (parser_error_message == NULL) ) {
-        parser_error_message = text;
+        parser_error_message = strdup(text);
        parser_error_linenum = line_number;
   }
 
@@ -2864,24 +2868,13 @@
 
 
 static void
-free_scores (scoreinfo * si)
+free_scores (DenemoScore * si)
 {
   GList *g = si->scoreblocks;
-/*
-  if(!g)
-  {
-  currently, we just:
-*/
-      free_score (si);
-      return;
-/*
-  }
-  but we should:
-*/
-
+/*if(!g) */ return free_score (si);
   for (g = si->scoreblocks; g; g = g->next)
     {
-      free_score ((scoreinfo *) g->data);
+      free_score ((DenemoScore *) g->data);
     }
 }
 
@@ -2896,16 +2889,115 @@
        g_free(trailing_white_space);
        trailing_white_space = NULL;
 }
+
+char *
+header_str(char *key)
+{
+       nodeglist *x;
+       char *pt = NULL;
+       int n;
+
+         x = (nodeglist *) g_hash_table_lookup (name_value_pairs, key);
+       if (x)
+       {
+           pt = u_str(x->branch);
+           if (*pt == '"') pt++;
+           n = strlen(pt) - 1;
+           if (*(pt+n) == '"') *(pt+n) = 0;
+       }
+       return(pt);
+}
+static void
+score_prop_from_lily (DenemoScore *si)
+{
+    char *pt;
+    GList *scm;
+
+    if ((pt = header_str("midi_tempo")))
+    {
+       si->tempo = atoi(pt);
+    }
+    if ((pt = header_str("lilyversion")))
+    {
+       si->sconfig->lilyversion = g_string_new(pt);
+    }
+    if (findtok (lily_file, HEADER))
+    {
+       if ((pt = header_str ("title")))
+           g_string_assign (si->headerinfo->title, pt);
+       if ((pt = header_str ("subtitle")))
+           g_string_assign (si->headerinfo->subtitle, pt);
+       if ((pt = header_str ("poet")))
+           g_string_assign (si->headerinfo->poet, pt);
+       if ((pt = header_str ("composer")))
+           g_string_assign (si->headerinfo->composer, pt);
+       if ((pt = header_str ("meter")))
+           g_string_assign (si->headerinfo->meter, pt);
+       if ((pt = header_str ("opus")))
+           g_string_assign (si->headerinfo->opus, pt);
+       if ((pt = header_str ("arranger")))
+           g_string_assign (si->headerinfo->arranger, pt);
+       if ((pt = header_str ("instrument")))
+           g_string_assign (si->headerinfo->instrument, pt);
+       if ((pt = header_str ("dedication")))
+           g_string_assign (si->headerinfo->dedication, pt);
+       if ((pt = header_str ("piece")))
+           g_string_assign (si->headerinfo->piece, pt);
+       if ((pt = header_str ("head")))
+           g_string_assign (si->headerinfo->head, pt);
+       if ((pt = header_str ("copyright")))
+           g_string_assign (si->headerinfo->copyright, pt);
+       if ((pt = header_str ("footer")))
+           g_string_assign (si->headerinfo->footer, pt);
+       if ((pt = header_str ("tagline")))
+           g_string_assign (si->headerinfo->tagline, pt);
+    }
+    for(scm = findtok (lily_file, SCM_T); scm ; scm = scm->next)
+    {
+       if ((pt = strstr (u_str (scm), "set-global-staff-size")))
+       {
+               int font;
+               if (sscanf (pt+21, " %d", &font) == 1)
+               {
+                       si->sconfig->fontsize = font;
+               }
+               else
+                       g_warning("%s no font", pt);
+       }
+       if ((pt = strstr (u_str (scm), "set-default-paper-size")))
+       {
+           char *tmp;
+           char *pt2 = strchr(pt, '\"');
+           if (pt2)
+           {
+               tmp = g_strdup(pt2+1);
+               pt2 = strchr(tmp, '\"');
+               if (pt2)
+               {
+                   *pt2 = 0;
+       //          g_print ("Paper size %s\n", tmp);
+                    g_string_assign (si->sconfig->papersize, tmp);
+                   *tmp = 0;
+                    g_free (tmp);
+               }
+           }
+           if (!pt2)
+               g_warning("%s paper size error", pt);
+       }
+    }
+}
+
+
 /* from denemo's easylyparser.y
    note that this function generates a list
-   of scoreinfo structures (one for each \score{} block
+   of DenemoScore structures (one for each \score{} block
    in the lilypond file, returning the current one (as set in
    si->theFile->current_scoreblock). This rather clumsy
    arrangement is historical from when si was the root data
    structure: see denemo.h     
  */
 int
-lyinput (gchar * filename, struct scoreinfo *si)
+lyinput (gchar * filename, DenemoGUI *gui)
 {
   FILE *lyin;
   GList *score_block_list = NULL;
@@ -2913,6 +3005,9 @@
   name_value_pairs = g_hash_table_new (g_str_hash, g_str_equal);/*
FIXME memory leak */
   default_duration_.t1.a = 2;
   default_duration_.t1.b = 0;
+  
+  init_crescendo_state();
+  DenemoScore *si = gui->si;
 
   while (1)
     {                          /* keep trying to open the file */
@@ -2928,13 +3023,14 @@
          parser_error_dialog = NULL;
          parser_error_message = NULL;
          /* free_score (si); CHANGE THIS TO FREE ALL THE si in 
-            si->thefile->currentscoreinfo list... */
+            si->thefile->currentDenemoScore list... */
          free_scores (si);
 
          /* in case we are re-entering via reload after error */
          lyrestart (lyin);     
 
          lylineno = 1;         /* not done by lexer for some reason */
+         push_note_state ();
 
          while (!feof (lyin))
            {
@@ -2942,53 +3038,57 @@
            }
          if (parser_error_message == NULL)
            {
-
              GList *score = findtok (lily_file, SCORE);
              if (score)
                if (create_score_from_lily (si, br (score)) == 0)
                  {
                    GList *top;
                    nodemin *n = (nodemin *) g_malloc0 (sizeof (nodemin));
+                   score_prop_from_lily(si);
 
                    while (score && score->next)
                      {
                        score = findtok (score->next, SCORE);
                        if (score)
                          {
-                           scoreinfo *nextsi =
-                             (scoreinfo *) g_malloc0 (sizeof (scoreinfo));
-                           init_score (nextsi);
+                           DenemoScore *nextsi =
+                             (DenemoScore *) g_malloc0 (sizeof (DenemoScore));
+                           init_score (nextsi, header_str("lilyversion"));
                            create_score_from_lily (nextsi, br (score));
                            score_block_list =
                              g_list_append (score_block_list, nextsi);
                          }
                      }
+
                    n->type = TEXT;
                    /* must be g_free-able pointer */
                    n->user_string = g_strdup ("");     
                    top = g_list_append (NULL, n);
                    /* simplify the tree into TEXT and DENEMO_MEASURES nodes */
+#ifdef LILYEDIT
                    lily_write_out (top, lily_file, TO_NODE);   
+#endif
                    attach_trailing_white_space (top);
                    si->lily_file = top;
+                   fixup_measure_widths_and_contexts (si);
+#ifdef LILYEDIT
                    /* write out the text to editable display */
-                   create_text_display (si);   
+                   create_text_display (gui);  
 #if GTK_MAJOR_VERSION > 1
 /* so that the following toggle starts the scorearea display */
                    gtk_widget_hide (si->scorearea);    
-                   toggle_top_node (NULL, si);
+                   toggle_top_node (NULL, gui);
 /* present denemo's graphical window first */
-                   gtk_window_present ((GtkWindow *) si->window);      
+                   gtk_window_present ((GtkWindow *) gui->window);     
 #endif
-                   fixup_measure_widths_and_contexts (si);
 
                    if (g_list_length (score_block_list) > 0)
                      {
                        GList *g;
-                       scoreinfo *nextsi;
+                       DenemoScore *nextsi;
                        for (g = score_block_list; g; g = g->next)
                          {
-                           nextsi = (scoreinfo *) g->data;
+                           nextsi = (DenemoScore *) g->data;
                            fixup_measure_widths_and_contexts (nextsi);
                            nextsi->window = si->window;
                            nextsi->scorearea = si->scorearea;
@@ -3016,22 +3116,30 @@
                        /* append a copy of the score block si (the one that 
the display is
hardwired to)
                           to the list of score_blocks, so that the display can 
be cycled
around by copying
                           from score_block_list to si  */
-                       nextsi = (scoreinfo *) g_malloc0 (sizeof (scoreinfo));
-                       memcpy (nextsi, si, sizeof (scoreinfo));
+                       nextsi = (DenemoScore *) g_malloc0 (sizeof 
(DenemoScore));
+                       memcpy (nextsi, si, sizeof (DenemoScore));
                        score_block_list =
                          g_list_append (score_block_list, nextsi);
                        si->scoreblocks = score_block_list;
                      }
 
+#endif // LILYEDIT
 
 
                    return 0;
                  }
            }                   /* if successful lily parse */
+           else
+           {
+               fprintf(stderr, "Parse Error Line %d: %s\n", 
+                   parser_error_linenum, parser_error_message);
+               exit(1);
+           }
 
        }
       reset_initial_lexer_state ();
       g_assert (lily_file);
+#ifdef LILYEDIT
       if (!getenv ("EDITOR"))
        {
          long len;
@@ -3080,7 +3188,25 @@
          if (ret)
            break;
        }
+#endif //LILYEDIT
+        g_error ("File load failed\n");
+        return -1;     
     }                          /* forever */
   g_error ("File load failed\n");
   return -1;                   /* there is no handler for this yet - never has 
been! */
 }
+#ifdef YYPRINT
+
+static gchar *
+type_name(gint type)
+{
+       gint i;
+       for(i=0; yytoknum[i] != type; i++)
+       {
+           if (i > YYNTOKENS)
+               return("");
+       }
+       return yytname[i];
+}
+
+#endif
diff -urN -X xdiff ../denemo/src/lyric.c ./src/lyric.c
--- ../denemo/src/lyric.c       2006-08-07 04:11:09.000000000 +1000
+++ ./src/lyric.c       2007-01-30 22:20:31.000000000 +1100
@@ -101,8 +101,6 @@
   DenemoScore *si = gui->si;
   DenemoObject *curObj = (DenemoObject *)
     (si->currentobject ? si->currentobject->data : NULL);
-  if (si->lily_file)
-    return;                    /* no code for this yet - just edit textually */
   dialog = gtk_dialog_new_with_buttons (_("Insert Lyric"),
                                        GTK_WINDOW (gui->window),
                                        (GtkDialogFlags) (GTK_DIALOG_MODAL |
diff -urN -X xdiff ../denemo/src/Makefile.am ./src/Makefile.am
--- ../denemo/src/Makefile.am   2007-01-01 21:57:19.000000000 +1100
+++ ./src/Makefile.am   2007-01-11 22:34:26.000000000 +1100
@@ -1,33 +1,38 @@
 bin_PROGRAMS = denemo
 dist_pkgdata_DATA = denemoui.xml instruments.xml
 denemo_SOURCES = articulations.c calculatepositions.c changenotehead.c
\
-                       chordops.c clefdialog.c commandfuncs.c contexts.c draw.c
drawaccidentals.c \
-       drawclefs.c drawcursor.c drawkey.c drawdynamic.c                
drawnotes.c
drawselection.c \
-       drawfakechord.c drawstemdir.c drawtimesig.c                     
drawtuplets.c
drawlyric.c dynamic.c drawfigure.c \
-       exportabc.c exportmudela.c              exportpdf.c exportxml.c file.c 
frogio.c
gcs.c \
-       headerdialog.c hairpin.c                help.c importxml.c importmidi.c
kbd-custom.c \
-       kbd-interface.c                 keyresponses.c keysigdialog.c figure.c 
fakechord.c
lyparserfuncs.c                                         main.c \
-                       measureops.c midi.c moveviewport.c mousing.c barline.c  
                                view.c
mwidthdialog.c \
-       objops.c exportmidi.c   instrumentname.c        external.c      
playback.c
playbackprops.c \
-       plugin.c prefdialog.c prefops.c                                         
processstaffname.c
csoundplayback.c \
-       lyric.c scoreops.c scoreprops.c selectops.c                             
        staffops.c
staffpropdialog.c \
-       drawbarline.c slurs.c timedialog.c                              
tomeasuredialog.c               tupletops.c
utils.c \
-       graceops.c runsilent.c drawgrace.c                              print.c 
                exportcsound.c
frogparser.c \
-               froglexer.c                     accwidths.h             
articulations.h         calculatepositions.h
changenotehead.h chordops.h \
-                                       commandfuncs.h          
csoundplayback.h contexts.h     dynamic.h dialogs.h
draw.h \
-       drawingprims.h                                          exportabc.h 
exportmudela.h      exportxml.h file.h
frogio.h \
-       frogdefs.h                              gcs.h           figure.h 
fakechord.h barline.h view.h hairpin.h
help.h importxml.h \
-       importmidi.h            kbd-custom.h kbd-interface.h keysigdialog.h 
graceops.h
keyresponses.h \
-                                       lyparserfuncs.h                 
measureops.h midi.h mousing.h   moveviewport.h
notewidths.h objops.h \
-                                       frogparser.h            playbackprops.h 
plugin.h prefops.h
processstaffname.h redefs.h \
-                                       scoreops.h              selectops.h 
staffops.h slurs.h twoints.h        tupletops.h
utils.h \
-                                       exportxml.h             xmldefs.h 
exportmidi.h instrumentname.h
frogparser.h print.h \
-                                       exportcsound.h          lyric.h 
external.h      playback.h runsilent.h
binreloc.c      binreloc.h exportpdf.h \
-                       alsaplayback.c alsaplayback.h bookmarks.c bookmarks.h 
scorewizard.c
scorewizard.h \
-                       parseinstruments.c parseinstruments.h keyboard.c        
        midiseq.h
alsaseq.h alsaseq.c 
-#drawlilydir.c lilydirectives.h lilydirectives.c lylexer.c lyparser.c
lyparser.h
-EXTRA_DIST = frogparser.y froglexer.l 
-#lylexer.l lyparser.y
+       chordops.c clefdialog.c commandfuncs.c contexts.c draw.c \
+       drawaccidentals.c drawclefs.c drawcursor.c drawkey.c drawdynamic.c \
+       drawnotes.c drawselection.c drawstemdir.c drawtimesig.c drawtuplets.c
\
+       drawlyric.c dynamic.c drawfigure.c exportabc.c exportmudela.c \
+       exportpdf.c exportxml.c file.c frogio.c gcs.c headerdialog.c hairpin.c
\
+       help.c importxml.c importmidi.c kbd-custom.c kbd-interface.c \
+       keyresponses.c keysigdialog.c figure.c  main.c \
+       measureops.c midi.c moveviewport.c mousing.c barline.c  view.c \
+       mwidthdialog.c objops.c exportmidi.c    instrumentname.c external.c \
+       playback.c drawfakechord.c fakechord.c \
+       playbackprops.c plugin.c prefdialog.c prefops.c processstaffname.c \
+       csoundplayback.c lyric.c scoreops.c scoreprops.c selectops.c
staffops.c \
+       staffpropdialog.c drawbarline.c slurs.c timedialog.c tomeasuredialog.c
\
+       tupletops.c utils.c graceops.c runsilent.c drawgrace.c  print.c \
+       exportcsound.c lyparser.c  lylexer.c lyparserfuncs.c frogparser.c \
+       froglexer.c     accwidths.h \
+       articulations.h calculatepositions.h changenotehead.h chordops.h
commandfuncs.h \
+       csoundplayback.h contexts.h  dynamic.h dialogs.h draw.h drawingprims.h
lyparser.h \
+       exportabc.h exportmudela.h  exportxml.h file.h frogio.h frogdefs.h
gcs.h \
+       figure.h barline.h view.h hairpin.h  help.h importxml.h importmidi.h \
+       kbd-custom.h kbd-interface.h graceops.h  keyresponses.h
lyparserfuncs.h \
+       measureops.h midi.h mousing.h  moveviewport.h notewidths.h objops.h
frogparser.h \
+       playbackprops.h plugin.h prefops.h processstaffname.h redefs.h
scoreops.h \
+       selectops.h staffops.h slurs.h twoints.h  tupletops.h utils.h
exportxml.h \
+       xmldefs.h exportmidi.h instrumentname.h  frogparser.h print.h
exportcsound.h \
+       lyric.h playback.h runsilent.h binreloc.c  binreloc.h exportpdf.h \
+       alsaplayback.c alsaplayback.h bookmarks.c bookmarks.h scorewizard.c \
+       external.h scorewizard.h fakechord.h \
+       parseinstruments.c parseinstruments.h keyboard.c \
+       midiseq.h alsaseq.h alsaseq.c
+#drawlilydir.c lilydirectives.h lilydirectives.c
+EXTRA_DIST = frogparser.y froglexer.l lylexer.l lyparser.y
 
 localedir = $(datadir)/locale
 INCLUDES = -I../intl -I$(top_srcdir)/intl -I$(top_srcdir)/include \
@@ -47,13 +52,13 @@
 froglexer.c: froglexer.l
        flex -Pfrog  -o$(srcdir)/froglexer.c $(srcdir)/froglexer.l  
 
-#lyparser.c lyparser.h: lyparser.y
-#      bison -d -ply $(srcdir)/lyparser.y 
-#      mv lyparser.tab.c lyparser.c
-#      mv lyparser.tab.h lyparser.h
+lyparser.c lyparser.h: lyparser.y
+       bison -d -ply $(srcdir)/lyparser.y 
+       mv lyparser.tab.c lyparser.c
+       mv lyparser.tab.h lyparser.h
 
-#lylexer.c: lylexer.l
-#      flex -Ply  -o$(srcdir)/lylexer.c $(srcdir)/lylexer.l  
+lylexer.c: lylexer.l
+       flex -Ply  -o$(srcdir)/lylexer.c $(srcdir)/lylexer.l  
 
 MAINTAINERCLEANFILES = lylexer.c lyparser.c lyparser.h \
 frogparser.c frogparser.h 
diff -urN -X xdiff ../denemo/src/scoreprops.c ./src/scoreprops.c
--- ../denemo/src/scoreprops.c  2007-01-08 08:44:07.000000000 +1100
+++ ./src/scoreprops.c  2007-01-12 21:02:38.000000000 +1100
@@ -66,126 +66,124 @@
                      TRUE, 0);
 
   // Headers
-  /* no code for this yet - just edit textually */
-  if (!si->lily_file)
-    {
-      scrolled_window = gtk_scrolled_window_new (NULL, NULL);
-      gtk_container_set_border_width (GTK_CONTAINER (scrolled_window),
12);
-      gtk_widget_set_size_request (scrolled_window, 350, 300);
-      gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW
(scrolled_window),
+    
+  scrolled_window = gtk_scrolled_window_new (NULL, NULL);
+  gtk_container_set_border_width (GTK_CONTAINER (scrolled_window), 12);
+  gtk_widget_set_size_request (scrolled_window, 350, 300);
+  gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW
(scrolled_window),
                                      GTK_POLICY_AUTOMATIC,
                                      GTK_POLICY_AUTOMATIC);
-      gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW
+  gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW
                                           (scrolled_window), GTK_SHADOW_IN);
 
-      label = gtk_label_new_with_mnemonic (_("_Headers"));
-      gtk_notebook_append_page (GTK_NOTEBOOK (notebook),
scrolled_window,
+  label = gtk_label_new_with_mnemonic (_("_Headers"));
+  gtk_notebook_append_page (GTK_NOTEBOOK (notebook), scrolled_window,
                                label);
 
-      list_store = gtk_list_store_new (3, G_TYPE_STRING,       /* label */
-                                      G_TYPE_STRING,   /* value */
-                                      G_TYPE_POINTER); /* pointer to the 
corresponding header
field */
-
-      list = gtk_tree_view_new_with_model (GTK_TREE_MODEL
(list_store));
-      gtk_tree_view_insert_column_with_attributes (GTK_TREE_VIEW
(list),
-                                                  0, "Name",
-                                                  gtk_cell_renderer_text_new
-                                                  (), "text", 0, NULL);
-      gtk_container_add (GTK_CONTAINER (scrolled_window), list);
-      renderer = gtk_cell_renderer_text_new ();
-      g_object_set (renderer, "editable", TRUE, NULL);
-      g_object_set (renderer, "width", 200, NULL);
-      g_signal_connect (renderer, "edited", (GCallback) cell_edited,
+  list_store = gtk_list_store_new (3, G_TYPE_STRING,   /* label */
+                                     G_TYPE_STRING,    /* value */
+                                     G_TYPE_POINTER);  /* pointer to the 
corresponding header field
*/
+
+  list = gtk_tree_view_new_with_model (GTK_TREE_MODEL (list_store));
+  gtk_tree_view_insert_column_with_attributes (GTK_TREE_VIEW (list),
+                                                0, "Name",
+                                                gtk_cell_renderer_text_new
+                                                (), "text", 0, NULL);
+  gtk_container_add (GTK_CONTAINER (scrolled_window), list);
+  renderer = gtk_cell_renderer_text_new ();
+  g_object_set (renderer, "editable", TRUE, NULL);
+  g_object_set (renderer, "width", 200, NULL);
+  g_signal_connect (renderer, "edited", (GCallback) cell_edited,
                        list_store);
-      gtk_tree_view_insert_column_with_attributes (GTK_TREE_VIEW
(list), 1,
+  gtk_tree_view_insert_column_with_attributes (GTK_TREE_VIEW (list), 1,
                                                   "Value", renderer, "text",
                                                   1, NULL);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Title"),
                          COL_VALUE, si->headerinfo->title->str,
                          COL_PTR, &(si->headerinfo->title->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Subtitle"),
                          COL_VALUE, si->headerinfo->subtitle->str,
                          COL_PTR, &(si->headerinfo->subtitle->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Poet"),
                          COL_VALUE, si->headerinfo->poet->str,
                          COL_PTR, &(si->headerinfo->poet->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Composer"),
                          COL_VALUE, si->headerinfo->composer->str,
                          COL_PTR, &(si->headerinfo->composer->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Meter"),
                          COL_VALUE, si->headerinfo->meter->str,
                          COL_PTR, &(si->headerinfo->meter->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Opus"),
                          COL_VALUE, si->headerinfo->opus->str,
                          COL_PTR, &(si->headerinfo->opus->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Arranger"),
                          COL_VALUE, si->headerinfo->arranger->str,
                          COL_PTR, &(si->headerinfo->arranger->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Instrument"),
                          COL_VALUE, si->headerinfo->instrument->str,
                          COL_PTR, &(si->headerinfo->instrument->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Dedication"),
                          COL_VALUE, si->headerinfo->dedication->str,
                          COL_PTR, &(si->headerinfo->dedication->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Piece"),
                          COL_VALUE, si->headerinfo->piece->str,
                          COL_PTR, &(si->headerinfo->piece->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Head"),
                          COL_VALUE, si->headerinfo->head->str,
                          COL_PTR, &(si->headerinfo->head->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Copyright"),
                          COL_VALUE, si->headerinfo->copyright->str,
                          COL_PTR, &(si->headerinfo->copyright->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Footer"),
                          COL_VALUE, si->headerinfo->footer->str,
                          COL_PTR, &(si->headerinfo->footer->str), -1);
 
-      gtk_list_store_append (list_store, &iter);
-      gtk_list_store_set (list_store, &iter,
+  gtk_list_store_append (list_store, &iter);
+  gtk_list_store_set (list_store, &iter,
                          COL_NAME, _("Tagline"),
                          COL_VALUE, si->headerinfo->tagline->str,
                          COL_PTR, &(si->headerinfo->tagline->str), -1);
 
-    }
+   
 
   // Layout
   label = gtk_label_new_with_mnemonic (_("La_yout"));

-- 
Roy Rankin <address@hidden>




reply via email to

[Prev in Thread] Current Thread [Next in Thread]