Autor Thema: Alphabetisch sortierter Index  (Gelesen 4675 mal)

complanar

  • Member
Alphabetisch sortierter Index
« am: Freitag, 1. April 2011, 15:25 »
Hallo ihr,

die Inhaltsverzeichnisfunktion ist ja an sich ganz gut verwendbar (sieht man davon ab, dass header-Variablen nicht einfach automatisch übernommen werden können, jedenfalls nicht, wenn sie innerhalb einer bookpart-Umgebung oder innerhalb eines score-Blocks stehen).

Ich wünschte mir aber eine einfache Möglichkeit, für ein Liederbuch einen alphabetisch sortierten Index der Liedanfänge zu bekommen. Gern auch mit händisch vergebenen \indexItem Markierungen, die ich schon alphabetisch korrekt vergeben könnte – also ohne das (unmögliche) Auslesen der #'header:title Eigenschaften.

Ich habe für meine Zwecke bisher erst einmal die Funktionen aus toc-init.ly kopiert und die Variablen umbenannt, so dass ich mit \indexItem und \alphabetical-index eine Kopie des Inhaltsverzeichnisses habe.

Kann man mit einer Scheme-Funktion die internen Listen dieses Indexes vor der Ausgabe umsortieren lassen nach #'index:text statt nach #'index:pagenumber?

Ich habe zwar einige Programmierkenntnisse, die Syntax von Scheme finde ich aber irgendwie kompliziert zu verstehen – da bräuchte ich einen hohen Einarbeitungsaufwand. Wenn jemand sich da etwas auskennt, käme mir Hilfe in dieser Hinsicht sehr gelegen.

Vielen Dank,
Holger
« Letzte Änderung: Sonntag, 3. April 2011, 12:43 von complanar »

complanar

  • Member
Re:Alphabetisch sortierter Index
« Antwort #1 am: Dienstag, 5. April 2011, 16:45 »
Habe mich doch durch Scheme durchgekämpft – gar so schwer war es gar nicht.

Ich habe jetzt eine Variante, die funktioniert. Mit einer Kopie der Datei ./ly/toc-init.ly ging es ganz gut. Die Funktionen und Variablen habe ich entsprechend umbenannt und modifiziert.

Ein Problem habe ich aber leider noch nicht in den Griff bekommen: Wenn man die Datei mehrfach einbindet, dann werden die Listen immer wieder zurückgesetzt und es erscheinen nur die indexItems aus der letzten Datei.

Ich möchte gern ein Buch erstellen, in das die einzelnen Lieder dann eingebunden werden. Die einzelnen Lieder sollen aber auch für sich lauffähig sein, d.h. ohne Fehler kompilierbar sein. Da komme ich nicht umhin in jede der Dateien mein Snippet einzubinden und stehe vor dem beschriebenen Problem.

Weiß jemand, ob ich eine bestimmte Datei erst zur Laufzeit (also direkt beim Aufruf von lilypond) einbinden kann, ohne das die Datei in die einzelnen Files eingebunden wird? Es gibt leider in Scheme keine Möglichkeit zu testen ob eine Variable bereits existiert und sie nur im Fall der Nichtexistenz neu anzulegen. Auf dieser Ebene bekomme ich das Problem jedenfalls nicht gelöst. Man kann Variablen afaik auch nicht anlgegen, ohne ihnen einen Wert zuzuweisen.

Demnächst werde ich die Ergebnisse meiner Grübeleien mal posten. Ich denke, so eine Funktion könnte für viele nützlich sein…

complanar

  • Member
Re:Alphabetisch sortierter Index
« Antwort #2 am: Donnerstag, 7. April 2011, 09:17 »
Wie schon gesagt, habe ich eine Lösung gefunden, die für mich sehr gut funktioniert. Ich habe festgestellt, dass sich dieser Ansatz sogar dazu eignet Themengebundene Liedverzeichnisse, wie sie in kirchlichen Gesangbüchern oder Schulbüchern üblich sind, umzusetzen.

Hier mein Code und ein Beispiel:

% Usage:
% - define and index item with \indexItem $sortstring $markup
% - use \indexSection $sortstring $markup to divide the index into several sections
% - display the alphabetical index with \markuplines \index

% code ist mostly taken from ./ly/toc-init.ly and just slightly modfied
%% defined later, in a closure
#(define-public (add-index-item! markup-symbol text sorttext) #f)
#(define-public (index-items) #f)

#(let ((index-item-list (list)))
   (set! add-index-item!
   (lambda (markup-symbol text sorttext)
     (let ((label (gensym "index")))
       (set! index-item-list
       ;; We insert index items sorted from the beginning on and do
       ;; not sort them later - this saves pretty much computing time
       (insert-alphabetical-sorted! (list label markup-symbol text sorttext)
       index-item-list))
       (make-music 'EventChord
         'page-marker #t
         'page-label label
         'elements (list (make-music 'LabelEvent
         'page-label label))))))
   (set! index-items (lambda ()
         index-item-list)))

#(define (insert-alphabetical-sorted! iitem ilist)
  (if
    (null? ilist) (list iitem)
    (if
      (string-ci<? (cadddr iitem) (cadddr (car ilist))) (cons iitem ilist)
      (cons (car ilist) (insert-alphabetical-sorted! iitem (cdr ilist)))
    )
  )
)

\paper {
  indexTitleMarkup = \markup \column {
    \fontsize #5 \sans \bold \fill-line { \null "Alphabetical Index" \null }
    \hspace #1
  }
  indexItemMarkup = \markup \large \fill-line {
    \fromproperty #'index:text
    \fromproperty #'index:page
  }
  indexSectionMarkup = \markup \column {
    \hspace #1
    \fill-line { \sans \bold \fontsize #3 \fromproperty #'index:text }
    \hspace #1
  }

}

#(define-markup-list-command (index layout props) ()
  ( _i "Outputs an alphabetical sorted index, using the paper
  variable @code{indexTitleMarkup} for its title, then the list of
  lines built using the @code{indexItem} music function
  Usage: @code{\\markuplines \\index}" )
  (cons (interpret-markup layout props
        (ly:output-def-lookup layout 'indexTitleMarkup))
  (space-lines (chain-assoc-get 'baseline-skip props)
        (map (lambda (index-item)
         (let ((label (car index-item))
         (index-markup (cadr index-item))
         (text (caddr index-item)))
           (interpret-markup
             layout
             (cons (list (cons 'index:page
              (markup #:page-ref label "XXX" "?"))
             (cons 'index:text text))
             props)
             (ly:output-def-lookup layout index-markup))))
       (index-items)))))

indexItem =
#(define-music-function (parser location sorttext text) (string? markup?)
   "Add a line to the alphabetical index, using the @code{indexItemMarkup} paper variable markup."
   (add-index-item! 'indexItemMarkup text sorttext))

indexSection =
#(define-music-function (parser location sorttext text) (string? markup?)
   "Add a section line to the alphabetical index, using @code{indexSectionMarkup} paper variable markup. This can be used to divide the alphabetical index into different sections, for example one section for each first letter."
   (add-index-item! 'indexSectionMarkup text sorttext))


% ---------------------------------------------------------------
\markuplines \index

\indexSection #"B" \markup { "B" }
\indexSection #"K" \markup { "K" }
\indexSection #"Z" \markup { "Z" }

\bookpart {
  \score {
    \relative c' {
      \repeat unfold 10 { c d e f }
      \indexItem #"Karola" \markup{ "Karola" }
      \repeat unfold 10 { c d e f }
      \bar "|."
    }
  }
}
\bookpart {
  \score {
    <<
      \new Staff \new Voice = "voc" {
        \relative c' {
          \indexItem #"Zora" \markup { \italic "Zora" }
          \repeat unfold 10 { c d e f }
          \indexItem #"Bettina" \markup { \larger "Bettina" }
          \indexItem #"Barbara" \markup { \smallCaps "Barbara" }
          \repeat unfold 10 { c d e f }
          \bar "|."
        }
      }
      \new Lyrics \lyricsto "voc" \lyricmode {
        \repeat unfold 10 { la la la la }
        \repeat unfold 10 { mi mi mi mi }
    } >>
    \header {
      piece = "third"
    }
  }
}

Ich habe den Code auch ins LSR übertragen, dort ist er aber noch nicht freigeschaltet. Aber die ID und den Titel kann ich ja schonmal verraten: „Alphabetical sorted index“, ID 763

Grüße,
Holger

Manuela

  • Member
Re: Alphabetisch sortierter Index
« Antwort #3 am: Montag, 26. September 2016, 12:16 »
Und ich verwende jetzt dieses sortierten Index und bin total happy, dass es das gibt.  ;D

Wollte ich nur mal sagen, auch wenn es schon lange her ist.

harm6

  • Member
Re: Alphabetisch sortierter Index
« Antwort #4 am: Montag, 26. September 2016, 12:58 »
Ein noch darüber hinausgehender thread hier:
https://liarchiv.joonet.de/index.php?topic=1040.0

Gruß,
  Harm

Manuela

  • Member
Re: Alphabetisch sortierter Index
« Antwort #5 am: Montag, 26. September 2016, 13:15 »
Danke für den Hinweise, Harm.  :)

Jetzt bin ich noch auf der Suche, wie ich im Inhaltsverzeichnis römische Seitennummern verwenden kann und wie ich es schaffe, dass das erste Lied auf Seite 1 steht.

Update: ich nehme die Sache mit den römischen Seitenzahlen geht folgerndermaßen

page-number-type = #'roman-lower bzw. #'roman-upper
« Letzte Änderung: Montag, 26. September 2016, 13:21 von Manuela »

Manuela

  • Member
Re: Alphabetisch sortierter Index
« Antwort #6 am: Montag, 26. September 2016, 15:55 »

Update: ich nehme die Sache mit den römischen Seitenzahlen geht folgerndermaßen

page-number-type = #'roman-lower bzw. #'roman-upper

Das habe ich jetzt ausprobiert mit dem Effekt, dass auch die Seitenzahlen romanisiert werden  :(

fugenkomponist

  • Member
Re: Alphabetisch sortierter Index
« Antwort #7 am: Montag, 26. September 2016, 17:53 »
Ich hab eine Idee, was man da machen könnte: evenHeaderMarkup und oddHeaderMarkup überschreiben:      evenHeaderMarkup = \markup
      \fill-line {
        \on-the-fly #print-page-number-check-first
        #(format #f "~@r" (string->number
                           „\fromproperty #'page:page-number-string“))
        \on-the-fly #not-part-first-page \fromproperty #'header:instrument
        ""
      }
Die 5. Zeile dieses Codes funktioniert so natürlich nicht (deshalb in „“), ich weiß aber auch nicht, wie anders. Hab vermutet, dass man nen markup-command schreiben könnte, der das übernimmt und die 3.–5. Zeile ersetzt, aber auch das krieg ich nicht hin, da fehlen mir Erfahrung mit markups in Scheme und sinnvolle Fehlermeldungen:\version "2.19.47"

#(define-markup-command (my-roman-page-number layout props)
     (#:on-the-fly print-page-number-check-first
     (format #f "~@r"
       (string->number
        (chain-assoc-get 'page:page-number-string props)))))
ergibtdocument.ly:3:2: error: GUILE signaled an error for the expression beginning here
#
 (define-markup-command (my-roman-page-number layout props)
Wrong type (expecting pair): ()

Edit: Das wär jetzt aber eigentlich ein Thema für nen neuen Thread ;)

harm6

  • Member
Re: Alphabetisch sortierter Index
« Antwort #8 am: Dienstag, 27. September 2016, 01:27 »