[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: grob-object information
From: |
Marc Hohl |
Subject: |
Re: grob-object information |
Date: |
Tue, 11 Sep 2012 22:28:02 +0200 |
User-agent: |
Mozilla/5.0 (X11; Linux x86_64; rv:15.0) Gecko/20120827 Thunderbird/15.0 |
Am 11.09.2012 21:54, schrieb address@hidden:
On 11 sept. 2012, at 22:29, Marc Hohl <address@hidden> wrote:
Are you certain that every vertical axis group will always contain the same
number of bar lines? If not, it's possible that the matrix you're talking
about may not have complete rows, in which case it's difficult to know how to
break it.
I am not 100% sure – there could be corner cases where a staff line stops
before the
volta bracket is closed, but this could lead to an error when compiling the .ly
file.
What about pieces with different simultaneous time signatures? They'd have
different numbers of bars for a given section.
Hey, good catch!
One way to check it is to look at the left or right of the spanned_rank_interval of the
grobs (the values will be the same as you're dealing with items which only ever
"span" one column). Once it goes backwards, you know that you've skipped to
the next row.
What kind of values does spanned_rank_interval return?
The column number of a grob's left and right bound. Columns are linearly
ordered from the beginning of a score to the end, so you can use it to know
when a new staff is beginning in your array. For bar lines, the grob only
spans one column so the left and right values of the returned will be the same
- you can use either one.
Ok, so I try to wrap a scheme caller around spanned_rank_interval and see
how far I can get with that.
In C++, if I had a vector <Grob *> foo that I wanted to sort into vector <vector
<Grob *> > bar, if I understand you correctly, I'd do:
int current_column = INT_MAX;
for (vsize i = 0; i < foo.size (); i++)
{
int column = foo[i]->spanned_rank_interval ()[LEFT];
if (column <= current_column)
bar.push_back (vector<Grob *> ());
bar.back ().push_back (foo[i]);
current_column = column;
}
The same thing is doable in Scheme - I just write pseudo-code faster in C++.
Yup, I think that's more or less what I want to achieve.
Just a side information: In lily/volta-bracket.cc the bar linformation
is obtained by
extract_grob_set (me, "bars", bars);
Grob *endbar = bars.size () ? bars.back () . 0 ;
SCM glyph = endbar ? endbar->get_property ("glyph_name") : SCM_EOL;
The scheme equivalent is
(let* ((bar-array (ly:grob-object me 'bars))
(bar-array-length (ly:grob-array-length bar-array))
(endbar (ly:grob-arraybar-array (1- bar-array-length)))
(glyph (ly:grob-property endbar 'glyph-name))
modulo some checks whether the array is not empty etc.
So the last element in the array is the one used for the
volta bracket, isn't it?
I found out that the last element in bar-array can be a SpanBar grob,
which leads to problems when I want to extract some other properties
that are only defined for BarLine grobs and not for SpanBar grobs.
I don't know whether it is safe just to check whether the last
element is a SpanBar; if yes, take the predecessor, if no, it
is a BarLine grob and erverything is fine.
Hopefully I explained it in a way that's understandable;
I want to know if I can achieve what I need *without* kind of
"parsing" the array.
On the other hand, when I need more detailed layout informations
about the "staffs and stuff", there is probably no way to bypass
this ordering routine.
Regards,
Marc
Re: grob-object information, Marc Hohl, 2012/09/14