strc-flt.mklx /size: 105 Kb    last modification: 2023-12-21 09:44
1%D \module
2%D   [       file=strc-flt,
3%D        version=2008.10.20,
4%D          title=\CONTEXT\ Structure Macros,
5%D       subtitle=Float Numbering,
6%D         author=Hans Hagen,
7%D           date=\currentdate,
8%D      copyright={PRAGMA ADE \& \CONTEXT\ Development Team}]
9%C
10%C This module is part of the \CONTEXT\ macro||package and is
11%C therefore copyrighted by \PRAGMA. See mreadme.pdf for
12%C details.
13
14%D This module will be redone with conditionals and everythings. Anyway, text floats
15%D are a rather historic feature so changing something is also braking something.
16
17\writestatus{loading}{ConTeXt Structure Macros / Float Numbering}
18
19\unprotect
20
21\ifdefined\d_page_sides_vsize \else \newdimension\d_page_sides_vsize \fi
22
23\registerctxluafile{strc-flt}{autosuffix}
24
25% todo: a keyword for this (and then a settings->hash for speed)
26%
27% \setuplayout[width=middle,backspace=3cm]
28%
29% \appendtoks
30%     \inhibitmargindata\conditionaltrue
31% \to \everyinsidefloat
32%
33% \starttext
34%     \dorecurse{20}{
35%         \par \inleft{\red\infofont<#1>} \par
36%         \placefigure[leftmargin]{}{\framed[height=1cm,width=2cm]{}}
37%       % \placefigure{#1}{\framed[height=1cm,width=2cm]{}}
38%         \par line #1.1 \par line #1.2 \par
39%     }
40% \stoptext
41
42% todo: delay caption creation and make setups for each method instead
43%       so that we can have a list of methods and redo them as we can
44%       keep the list or even better: recreate it
45%
46% todo: strc_floats_analyze_variables_two could trigger a setup
47%       and we could have nofmethods of them
48%
49% todo: move variables from page-flt to strc-flt
50%
51% todo: p_name etc
52%
53% todo: less globals!
54%
55% todo: do all options in lua
56
57%D This module is being converted into a mkvi one.
58%D
59%D - rename macros
60%D - get rid of dead code
61%D - less gobal mess
62%D - more mkiv-ish
63
64\installcorenamespace{float}
65\installcorenamespace{floatbuilder}
66\installcorenamespace{floatcaption}
67\installcorenamespace{floatframed}
68
69\installframedcommandhandler \??float        {float}        \??float
70\installframedcommandhandler \??floatcaption {floatcaption} \??floatcaption
71\installframedcommandhandler \??floatframed  {floatframed}  \??floatframed
72
73\aliased\let\setupfloats  \setupfloat
74\aliased\let\setupcaption \setupfloatcaption
75\aliased\let\setupcaptions\setupfloatcaption
76
77\permanent\protected\def\dohandlenextfloatindent
78  {\useindentnextparameter\floatparameter
79   \dorechecknextindentation}
80
81\setupcaptions
82  [\c!location=\v!bottom,
83   \c!grid=,
84   \c!before=, % not used (yet)
85   \c!inbetween={\blank[\v!medium]},
86   \c!after=, % not used (yet)
87   \c!spacebefore=,
88   \c!spaceinbetween=, % replaces fuzzy inbetween dual usage
89   \c!spaceafter=,
90   \c!width=\v!fit,
91   \c!minwidth=\v!fit, % id est: the width of the floatbox in some cases
92   \c!headstyle=\v!bold,
93   \c!headcolor=,
94   \c!leftmargin=\zeropoint,
95   \c!rightmargin=\zeropoint,
96   \c!outermargin=\zeropoint,
97   \c!innermargin=\zeropoint,
98   \c!setups=,
99   \c!style=\v!normal,
100   \c!color=,
101   \c!textstyle=,
102   \c!textcolor=,
103   \c!align=,
104   \c!number=\v!yes,
105   \c!offset=\v!overlay,
106   \c!frame=\v!off,
107 % \c!expansion=,
108 % \c!prefix=,
109 % \c!prefixconnector=,
110 % \c!way=,
111 % \c!prefixsegments=,
112 % \c!way=,
113 % \c!blockway=,
114 % \c!sectionnumber=,
115 % \c!separator=,
116 % \c!starter=,
117 % \c!stopper=,
118   \c!suffixseparator=, % currently rather hard coded
119   \c!suffix=\floatcaptionsuffix,
120   \c!distance=\emwidth, % plus .5\emwidth minus .25\emwidth
121   \c!conversion=\v!numbers,
122   \c!maxwidth=\hsize,
123   \c!command=]
124
125% we can comment some of these
126
127\setupfloats
128  [\c!location=\v!middle,
129   \c!width=8\lineheight,
130   \c!height=6\lineheight,
131   \c!offset=\v!overlay,
132   \c!frame=\v!off,
133   \c!strut=\v!no,
134   \c!radius=.5\bodyfontsize,
135   \c!corner=\v!rectangular,
136   \c!grid=,
137  %\c!background=,
138  %\c!backgroundcolor=,
139   \c!backgroundoffset=\!!zeropoint,
140  %\c!topframe=,
141  %\c!bottomframe=,
142  %\c!leftframe=,
143  %\c!rightframe=,
144   \c!frameoffset=\!!zeropoint,
145  %\c!before=,
146  %\c!after=,
147   \c!spacebefore=\v!big,
148   \c!spaceafter=\v!big,
149   \c!sidespacebefore=\rootfloatparameter\c!spacebefore,
150   \c!sidespaceafter=\rootfloatparameter\c!spaceafter,
151   \c!sidespaceinbetween=\rootfloatparameter\c!spacebefore,
152   \c!spacebeforeside=, % extra, not part of, can be used to add whitespace before text
153   \c!spaceafterside=,  % idem
154   \c!sidealign=\v!normal,
155   \c!textmethod=\ifgridsnapping2\else0\fi, % 0=raw 1=safe (.99pg) 2=tight (-1pt) % THIS WILL CHANGE
156   \c!sidemethod=\ifgridsnapping2\else1\fi, % 0=raw 1=safe (.99pg) 2=tight (-1pt) % THIS WILL CHANGE
157   \c!indentnext=\v!no,
158   \c!margin=\emwidth,
159   \c!method=1,
160   \c!cache=\v!yes, % when no, then intermediate flush
161   \c!leftmargin=\zeropoint,  % displacement in 'normal floats'
162   \c!rightmargin=\zeropoint, % idem
163   \c!innermargin=\zeropoint, % idem
164   \c!outermargin=\zeropoint, % idem
165   \c!leftmargindistance=\zeropoint,
166   \c!rightmargindistance=\floatparameter\c!leftmargindistance,
167   \c!step=\v!small, % the flush side float step (big, medium, small : always depth)
168   \c!ntop=2,
169   \c!nbottom=0,
170   \c!nlines=4, % used?
171   \c!topoffset=\zeropoint,
172   \c!bottomoffset=\zeropoint,
173   \c!freeregion=\v!yes,
174  %\c!local=,
175  %\c!bottombefore=, % e.g. \vfill
176  %\c!bottomafter=,
177  %\c!default=, % default location
178   \c!sidethreshold=.5\strutdp, % set to "old" to check with old method
179   \c!numbering=\v!yes,
180   \c!compress=\v!yes, % when possible pack floats when flushing
181   \c!compressdistance=\emwidth]
182
183\setupfloatframed
184  [\c!frame=\v!off,
185   \c!offset=\v!overlay,
186   \c!strut=\v!no]
187
188\newconditional\c_page_floats_pack_flushed
189
190\appendtoks
191    \ifcstok{\floatparameter\c!compress}\v!yes
192      \c_page_floats_pack_flushed\conditionaltrue
193    \else
194      \c_page_floats_pack_flushed\conditionalfalse
195    \fi
196    \d_page_floats_compress_distance\floatparameter\c!compressdistance\relax
197\to \everysetupfloat
198
199\mutable\lettonothing\currentfloatattribute
200\mutable\lettonothing\currentfloatcounter
201\mutable\lettonothing\currentfloatgroup
202\mutable\lettonothing\currentfloatnumber
203\mutable\lettonothing\currentfloatsynchronize
204
205\lettonothing\m_strc_floats_previous_number % we can also just push/pop
206
207%D We need to do it again here:
208
209\setupfloat
210  [\c!compress=\v!yes, % when possible pack floats when flushing
211   \c!compressdistance=\emwidth]
212
213%D Individial settings:
214
215\installcounterassociation{floatcaption}
216
217\appendtoks
218    \let\currentfloat\currentfloatcaption % ?
219    \synchronizefloatcaptioncounters
220\to \everysetupfloatcaption
221
222\appendtoks
223    \let\currentfloat\currentfloatcaption % ?
224    \synchronizefloatcaptioncounters
225\to \everydefinefloatcaption
226
227%D Definitions:
228
229\let\strc_floats_define_saved\definefloat
230
231\permanent\tolerant\protected\overloaded\def\definefloat[#1]#*[#S#2]#*[#S#3]% name+plural+parent | name+parent+settings
232  {\ifarguments\or
233     \strc_floats_define_c[#1][#1]%
234   \or
235     \doifelsecommandhandler\??float{#2}%
236       {\strc_floats_define_a[#1][#1][#2]}%
237       {\strc_floats_define_c[#1][#2]}%
238   \orelse\ifhastok={#3}%
239     \strc_floats_define_b[#1][#2][#3]%
240   \else
241     \strc_floats_define_a[#1][#2][#3]%
242   \fi}
243
244\def\strc_floats_define_a[#1][#2][#3]% name names parent
245  {\definefloatcaption[#1][#3]%
246   \definefloatframed[#1][#3]%
247   \definecounter[#1][#3]%
248   \definelist[#1][#3]%
249   \copylabeltext[#1=#3]%
250   \strc_floats_define_saved[#1][#3]%
251   \strc_floats_define_commands{#1}{#2}}
252
253\def\strc_floats_define_b[#1][#2][#3]% name parent settings
254  {\definefloatcaption[#1][#2]%
255   \definefloatframed[#1][#2]%
256   \definecounter[#1][#2]%
257   \definelist[#1][#2]%
258   \copylabeltext[#1=#2]%
259   \strc_floats_define_saved[#1][#2][#3]%
260   \strc_floats_define_commands{#1}{#1}}
261
262\def\strc_floats_define_c[#1][#2]% name names
263  {\registerfloatcaptioncounter{#1}%
264   \definefloatcaption[#1]%
265   \definefloatframed[#1]%
266   \definecounter[#1]%
267   \definelist[#1]%
268   \presetlabeltext[#1=\Word{#1}~]%
269   \presetheadtext[#2=\Word{#2}]%
270   \strc_floats_define_saved[#1]%
271   \strc_floats_define_commands{#1}{#2}}
272
273\def\strc_floats_define_commands#1#2%
274  {\frozen\protected\instance\edefcsname\e!place      \e!listof#2\endcsname{\strc_lists_place[#1]}% call will change
275   \frozen\protected\instance\edefcsname\e!complete   \e!listof#2\endcsname{\strc_lists_complete[#1][#2]}% call will change
276   \frozen\protected\instance\edefcsname\e!place               #1\endcsname{\placefloat[#1]}%
277   \frozen\protected\instance\edefcsname\e!start       \e!place#1\endcsname{\startplacefloat[#1]}%
278   \frozen\protected\instance\edefcsname\e!stop        \e!place#1\endcsname{\stopplacefloat}%
279   \frozen\protected\instance\edefcsname\e!start        #1\e!text\endcsname{\startfloattext[#1]}%
280   \frozen\protected\instance\edefcsname\e!stop         #1\e!text\endcsname{\stopfloattext}%
281   \frozen\protected\instance\edefcsname\e!start\e!place#1\e!text\endcsname{\startplacefloattext[#1]}%
282   \frozen\protected\instance\edefcsname\e!stop \e!place#1\e!text\endcsname{\stopplacefloattext}%
283   % these will become obsolete:
284   \frozen\instance\protected\edefcsname\e!reserve               #1\endcsname{\strc_floats_reserve[#1]}%
285   \frozen\instance\protected\edefcsname\e!start\e!reserve#1\e!text\endcsname{\strc_floats_start_reserve_text[#1]}%
286   \frozen\instance\protected\edefcsname\e!stop \e!reserve#1\e!text\endcsname{\strc_floats_stop_reserve_text}}
287
288%D Fallback float body:
289
290\protected\def\strc_floats_place_empty_box % \inheritedfloatframed
291  {\framed
292     [\c!frame=\v!on,
293      \c!width=\rootfloatparameter\c!width,
294      \c!height=\rootfloatparameter\c!height,
295      \c!location=\v!normal,
296      \c!offset=\rootfloatparameter\c!offset]%
297     {\getmessage\m!floatblocks{12}\empty}}
298
299%D Data. We can generalize this to lists.
300
301\newif\ifnofloatcaption
302\newif\ifnofloatnumber
303\newif\ifemptyfloatcaption
304
305\installstructurelistprocessor\s!float{\usestructurelistprocessor{number+title}}
306
307\permanent\protected\def\thecurrentfloatnumbersuffix
308  {\ifempty{\floatcaptionparameter\c!suffix}\else
309     \floatcaptionparameter\c!suffixseparator
310     \floatcaptionparameter\c!suffix
311     \floatcaptionparameter\c!suffixstopper
312   \fi}
313
314\permanent\protected\def\thecurrentfloatnumber
315  {\ifnofloatcaption \orelse \ifnofloatnumber \orelse \ifrelax\currentfloatnumber \else
316     \namedtaggedlabeltexts
317       \t!floatlabel \currentfloat
318       \t!floatnumber\currentfloat
319       {\begstrut
320        \floatcaptionparameter\c!numbercommand
321          {\clf_savedlistprefixednumber{\currentfloat}\currentfloatnumber\relax
322           \thecurrentfloatnumbersuffix}%
323        \endstrut}%
324   \fi}
325
326\permanent\protected\def\thecurrentfloatcaption
327  {\ifnofloatcaption \orelse \ifemptyfloatcaption \orelse \ifrelax\currentfloatnumber \else
328     \dostarttagged\t!floattext\empty
329     \begstrut
330     \floatcaptionparameter\c!textcommand
331       {\clf_savedlisttitle{\currentfloat}\numexpr\currentfloatnumber\relax}%
332     \endstrut
333     \dostoptagged
334   \fi}
335
336%D Captions.
337
338\mutable\lettonothing\floatcaptionarrangement
339\mutable\lettonothing\floatcaptionattribute
340\mutable\lettonothing\floatcaptiondirectives
341\mutable\lettonothing\floatcaptionlocation
342\mutable\lettonothing\floatcaptionnumber
343\mutable\lettonothing\floatcaptionsuffix
344
345% For a while these were placeholders:
346%
347%D \starttyping
348%D \protected\def\placefloatcaption{\dodoubleempty\strc_floats_place_caption}
349%D \protected\def\setfloatcaption  {\dodoubleempty\strc_floats_set_caption}
350%D
351%D \def\strc_floats_place_caption[#tag][#reference]#caption{[not supported]}
352%D \def\strc_floats_set_caption  [#tag][#reference]#caption{[not supported]}
353%D
354%D \protected\def\placefloatcaptiontext     [#tag]{[not suported yet]}
355%D \protected\def\placefloatcaptionnumber   [#tag]{[not suported yet]}
356%D \protected\def\placefloatcaptionreference[#tag]{[not suported yet]}
357%D \stoptyping
358%D
359%D because in \MKII\ we had:
360%D
361%D \starttyping
362%D \let\placefloatlabel         \placefloatcaption
363%D \let\placefloatlabeltext     \placefloatcaptiontext
364%D \let\placefloatlabelreference\placefloatcaptionreference
365%D \stoptyping
366%D
367%D But as it was never advertised we don't provide it in \MKIV. However, at some
368%D point HvdM wanted this:
369%D
370%D \starttyping
371%D \placefigure                     {labeltext-1}  {\externalfigure[figure-1]}
372%D \placefloatcaption[figure][title={labeltext-2}]  \externalfigure[figure-2]
373%D \placefigure                     {labeltext-3}  {\externalfigure[figure-3]}
374%D \stoptyping
375%D
376%D So there you have it:
377
378\permanent\tolerant\protected\def\placefloatcaption[#category]#spacer[#S#settings]#spacer[#S#userdata]%
379  {\ifarguments\or\else % >= 2
380     % we need at least a category and title
381     \dontleavehmode
382     \bgroup
383     \cdef\currentfloat{#category}%
384     \let\currentfloatcaption\currentfloat
385     \resetfloatcaptionparameter\c!reference
386     \resetfloatcaptionparameter\c!title
387     \resetfloatcaptionparameter\c!marking
388     \resetfloatcaptionparameter\c!list
389     \resetfloatcaptionparameter\c!bookmark
390     \resetfloatcaptionparameter\c!referencetext
391     \setupcurrentfloatcaption[#settings]%
392     \edef\currentfloatcounter{\namedcounterparameter\currentfloat\s!name}%
393     \iftrialtypesetting\strc_counters_save\currentfloatcounter\fi
394     \ifcstok{\floatcaptionparameter\c!number}\v!yes
395       \global\nofloatnumberfalse
396     \else
397       \global\nofloatnumbertrue
398     \fi
399     \ifnofloatnumber\else
400       \strc_counters_increment\currentfloatcounter
401     \fi
402     \strc_counters_register_component
403       \s!float
404       \setupcurrentfloatcaption
405       \floatcaptionparameter
406       \detokenizedfloatcaptionparameter
407       \relax
408       \relax
409       \relax
410       [\s!name=\currentfloat,
411        \s!counter=\currentfloatcounter,%
412        \s!hascaption=\v!yes,%
413        \s!hasnumber=\ifnofloatnumber\v!no\else\v!yes\fi,%
414        \s!hastitle=\v!yes]%
415       [#userdata]%
416     \glet\m_strc_floats_previous_number\m_strc_counters_last_registered_index
417     \glet\currentfloatnumber           \m_strc_counters_last_registered_index
418     \glet\currentfloatattribute        \m_strc_counters_last_registered_attribute
419     \glet\currentfloatsynchronize      \m_strc_counters_last_registered_synchronize
420     %
421   % \iflocation
422   %    \c_attr_destination\currentfloatattribute\relax
423   % \fi
424     \currentfloatsynchronize
425     \strc_floats_make_complete_caption
426     %
427     \iftrialtypesetting\strc_counters_restore\currentfloatcounter\fi
428     \egroup
429   \fi}
430
431\newbox      \b_strc_floats_caption
432\newbox      \b_strc_floats_content
433\newdimension\d_strc_floats_caption_height
434\newdimension\d_strc_floats_caption_depth
435
436\lettonothing\m_strc_floats_last_caption_tag
437
438\def\strc_floats_make_complete_caption
439  {\ifempty{\floatcaptionparameter\c!spacebefore}\else
440     \blank[\floatcaptionparameter\c!spacebefore]%
441   \fi
442   \strc_floats_make_complete_caption_before
443   \synchronizedisplaydirection % temp hack, till we have a proper model
444   \noindent
445   \gdef\m_strc_floats_last_caption_tag{\strut\thecurrentfloatnumber}% was xdef ... needs checking
446   \begingroup
447     \ifnofloatcaption
448       \global\d_strc_floats_caption_height\zeropoint
449       \global\d_strc_floats_caption_depth \zeropoint
450     \else
451       \usefloatcaptionstyleandcolor\c!style\c!color
452       \clf_doifelselisthastitle{\currentfloat}\numexpr\currentfloatnumber\relax
453         \donothing
454         \emptyfloatcaptiontrue
455       \ifnofloatnumber \orelse \ifnofloatcaption \else
456         \ifemptyfloatcaption
457           \hbox{\usefloatcaptionstyleandcolor\c!headstyle\c!headcolor\thecurrentfloatnumber}%
458         \else
459           \ifempty{\floatcaptionparameter\c!spaceinbetween}%
460             \scratchskip\floatcaptionparameter\c!distance\relax
461             \setbox\scratchbox\hbox
462               {\usefloatcaptionstyleandcolor\c!headstyle\c!headcolor
463                \thecurrentfloatnumber
464                \floatcaptionparameter\c!headseparator
465                \dotfskip\scratchskip}%
466             \ifcstok{\floatcaptionparameter\c!hang}\v!yes
467               \leftskip\wd\scratchbox
468               \llap{\box\scratchbox}%
469             \else
470               \unhbox\scratchbox
471             \fi
472             \emergencystretch.5\scratchskip
473           \else
474             \hbox{\usefloatcaptionstyleandcolor\c!headstyle\c!headcolor\thecurrentfloatnumber}%
475             \blank[\floatcaptionparameter\c!spaceinbetween]%
476           \fi
477         \fi
478       \fi
479       \usefloatcaptionstyleandcolor\c!textstyle\c!textcolor
480       \global\d_strc_floats_caption_height\strutheight
481       \global\d_strc_floats_caption_depth \strutdepth
482       \thecurrentfloatcaption\endgraf
483     \fi
484   \endgroup
485   \strc_floats_make_complete_caption_after
486   \ifempty{\floatcaptionparameter\c!spaceafter}\else
487     \blank[\floatcaptionparameter\c!spaceafter]%
488   \fi}
489
490%let\strc_floats_make_complete_caption_before\relax
491\let\strc_floats_make_complete_caption_after \relax
492
493\def\strc_floats_make_complete_caption_before
494  {\doifelseframed\floatcaptionparameter\strc_floats_make_complete_caption_before_indeed\relax}
495
496\def\strc_floats_make_complete_caption_before_indeed
497  {\edef\m_strc_align{\floatcaptionparameter\c!align}%
498   \edef\m_strc_strut{\floatcaptionparameter\c!strut}%
499   \letfloatcaptionparameter\c!align\v!normal
500   \letfloatcaptionparameter\c!strut\v!no
501   \inheritedfloatcaptionframed
502   \bgroup
503   \letfloatcaptionparameter\c!align\m_strc_align
504   \letfloatcaptionparameter\c!strut\m_strc_strut
505   \let\strc_floats_make_complete_caption_after\egroup}
506
507% \definefloat  [figure-1] [figure]
508% \definefloat  [figure-2] [figure]
509% \setupfloat   [figure-1] [location=left,leftmargin=10mm]
510% \setupfloat   [figure-2] [location=left,leftmargin=-5mm]
511% \setupcaption [figure-1] [align=flushleft]
512% \setupcaption [figure-2] [align=flushleft,leftmargin=15mm]
513%
514% \startsetups somefigure
515%     \ifdim\wd\nextbox>\textwidth
516%         \placefloat[figure-2][][]{}{\box\nextbox}
517%     \else
518%         \placefloat[figure-1][][]{}{\box\nextbox}
519%     \fi
520% \stopsetups
521%
522% \protected\def\setupswithbox[#1]{\dowithnextbox{\setups[#1]}\vbox}
523%
524% test \setupswithbox[somefigure]{\framed[width=3cm]                         {}} test
525% test \setupswithbox[somefigure]{\framed[width=\dimexpr\textwidth+3cm\relax]{}} test
526
527% temporary removed ... was not applied systematically
528%
529% \def\dosetcaptionthings
530%   {\usesetupsparameter\floatcaptionparameter}
531
532\def\strc_floats_check_caption_content
533  {\ifnofloatcaption\else
534     \setbox\b_strc_floats_caption\hbox
535       {\settrialtypesetting
536        \notesenabledfalse
537        \strc_floats_make_complete_caption}%
538     % new, \placefigure{\xmlfirst{#1}{somecaption}}{} passes earlier empty check
539     % so here we misuse the scratch box; actually this means that the previous
540     % test can go away (some day, when i redo this module)
541     \ifzeropt\wd\b_strc_floats_caption
542       \global\emptyfloatcaptiontrue
543       \ifnofloatnumber
544         \global\nofloatcaptiontrue
545       \fi
546     \else
547       \global\emptyfloatcaptionfalse
548       \setbox\b_strc_floats_caption\hpack{\hskip\leftskip\box\b_strc_floats_caption}%
549     \fi
550   \fi}
551
552\def\strc_floats_apply_caption_command
553  {\setbox\b_strc_floats_caption\hbox\bgroup
554    %\unless\ifempty{\floatcaptionparameter\c!command}
555       \floatcaptionparameter\c!command{\box\b_strc_floats_caption}%
556    %\orunless\ifempty{\floatcaptionparameter\c!deeptextcommand}%
557    %  \floatcaptionparameter\c!deeptextcommand{\unvbox\b_strc_floats_caption}%
558    %\else
559    %  \box\b_strc_floats_caption
560    %\fi
561   \egroup}
562
563%D Some trickery (example by MS):
564%D
565%D \starttyping
566%D \defineframed
567%D   [MyCaptionFramed]
568%D   [align={lohi,flushleft},
569%D    width=fit,
570%D    frame=off,
571%D    strut=no,
572%D    topframe=on,
573%D    loffset=1em,
574%D    toffset=0.25\lineheight]
575%D
576%D \starttexdefinition protected MyCaption #1
577%D     \MyCaptionFramed {
578%D         % we ignore #1 as we want to unpack
579%D         \unvbox\floatcaptionbox
580%D     }
581%D \stoptexdefinition
582%D
583%D \definefloat[pagefloat][pagefloats][graphic]
584%D
585%D \setupfloat
586%D   [pagefloat]
587%D   [default={page,header,footer}]
588%D
589%D \setupcaption
590%D   [pagefloat]
591%D   [location={top,inner},
592%D    align=inner,
593%D    command=\MyCaption,
594%D    spaceinbetween=nowhite]
595%D \stoptyping
596
597\permanent\protected\def\floatcaptionbox{\b_strc_floats_caption}
598
599%D We can do this ...
600%D
601%D \starttyping
602%D \newinteger\c_strc_floats_n
603%D
604%D \definedataset[\s!float][\c!delay=\v!yes]
605%D
606%D \let\strc_float_realpage\realpageno
607%D
608%D \def\strc_float_save_data
609%D   {\setdataset[\s!float][\the\c_strc_floats_n][]}
610%D
611%D \def\strc_float_load_data % precedes save !
612%D   {\global\advanceby\c_strc_floats_n\plusone
613%D    \xdef\strc_float_realpage{\datasetvariable\s!float{\the\c_strc_floats_n}\s!page}%
614%D    \ifempty\strc_float_realpage
615%D      \glet\strc_float_realpage\realpageno % \realfolio
616%D    \fi}
617%D \stoptyping
618%D
619%D ... but this is more efficient:
620
621\definepagestate[\s!float][\c!delay=\v!yes]
622
623\newinteger\c_strc_floats_n
624
625\let\strc_float_realpage\realpageno
626
627\def\strc_float_save_data
628  {\setpagestate[\s!float][\the\c_strc_floats_n]}
629
630\def\strc_float_load_data % precedes save !
631  {\global\advanceby\c_strc_floats_n\plusone
632   \xdef\strc_float_realpage{\pagestaterealpage\s!float{\the\c_strc_floats_n}}%
633   \ifempty\strc_float_realpage
634     \glet\strc_float_realpage\realpageno % \realfolio
635   \fi}
636
637%D test case:
638%D
639%D \starttyping
640%D \setupfloat[figure][criterium=\marginwidth,fallback=bottom]
641%D \dorecurse{3}{
642%D     \chapter{test}
643%D     \placefigure[bottom]{1}{\framed{bottom}}
644%D     test
645%D     \placetable[bottom]{1}{\framed{table}}
646%D     test
647%D     \placetable{2}{\framed{table}}
648%D     test
649%D     \placefigure[left]{2}{\framed{left but way too wide}}
650%D     \input tufte
651%D     \placefigure[left]{3}{\framed{left but ok}}
652%D     \input tufte }
653%D \stoptyping
654
655% A complication is that we may have to handle a pagebreak first, which in turn may
656% issue a (postponed) float. Therefore we may not trust on variable assignments
657% before we're really dealing with the float. Some day I'll root out the global
658% settings.
659
660\aliased\lettonothing\lastplacedfloat
661
662\def\strc_floats_set_current_tag#tag%
663  {\cdef\currentfloat{#tag}%
664   \ifempty\currentfloat
665     \let\currentfloat\v!figure % a bit of a hack
666   \fi
667   \doifelsecommandhandler\??float\currentfloat
668     \donothing
669     {\writestatus\m!floatblocks{unknown float type '\currentfloat'}%
670      \let\currentfloat\v!figure}% also a hack
671   \enforced\glet\lastplacedfloat\currentfloat
672   \lettonothing\m_strc_floats_saved_userdata
673   \let\currentfloatcaption\currentfloat}
674
675\mutable\lettonothing\askedfloatmethod
676\mutable\lettonothing\askedfloatoptions
677
678\def\strc_floats_reset_variables
679  {\global\emptyfloatcaptionfalse
680   \global\nofloatcaptionfalse
681   \global\nofloatnumberfalse
682   \glettonothing\askedfloatmethod
683   \glettonothing\askedfloatoptions}
684
685% place
686
687\mutable\lettonothing\floatlabel
688\mutable\lettonothing\floatcolumn
689\mutable\lettonothing\floatrow
690\mutable\lettonothing\floatlocation
691\mutable\lettonothing\floatlocationmethod
692\mutable\lettonothing\floatlocationdefault
693
694\def\strc_floats_analyze_location
695  {% more will be moved here
696   \lettonothing\floatlabel
697   \lettonothing\floatcolumn
698   \lettonothing\floatrow
699   %
700   \edef\floatcaptionlocation{\floatcaptionparameter\c!location}%
701   %
702   \setfloatmethodvariables\floatlocation}
703
704\newtoks\t_floats_every_table_float
705
706\appendtoks
707    \edef\floatlocation{\v!force,\v!always,\floatlocation}%
708    \setupfloat[\c!spacebefore=\v!none,\c!spaceafter=\v!none]%
709\to \t_floats_every_table_float
710
711\ifdefined\dotagregisterfloat \else \aliased\let\dotagregisterfloat\gobbletwoarguments \fi
712
713\tolerant\def\strc_floats_place[#tag]#spacer[#location]#spacer[#reference]#:#caption%
714  {\strc_floats_set_current_tag{#tag}%
715   \strc_floats_reset_variables
716   \xdef\askedfloatoptions{#location}%
717   \edef\floatlocationdefault{\floatparameter\c!default}%
718   \edef\floatlocation{#location}%
719   \ifempty\floatlocation
720     \let\floatlocation\floatlocationdefault % beware of a clash between alignment locations
721   \fi
722   \ifintable
723     \expand\t_floats_every_table_float
724   \fi
725   \strc_floats_analyze_location
726   % todo: use \lets
727   \setupcurrentfloatcaption[\c!reference={#reference},\c!title={#caption},\c!marking=,\c!list=,\c!bookmark=,\c!referencetext=]%
728   \ifinset\v!split\floatlocation
729     \expandafter\strc_floats_place_next_box_split
730   \else
731     \expandafter\strc_floats_place_next_box_normal
732   \fi}
733
734\permanent\protected\def\placefloat
735  {\flushnotes
736   \page_otr_command_flush_side_floats % here !
737   \strc_floats_begin_group
738   \strc_floats_place}
739
740% start-stop
741
742% \startplacefigure[title=oeps][subtitle=whatever]
743%     \framed[width=10cm,height=5cm]{\floatuserdataparameter{subtitle}}
744% \stopplacefigure
745
746\installcorenamespace{floatuserdata}
747
748\installsetuponlycommandhandler \??floatuserdata {floatuserdata}
749
750\lettonothing\m_strc_floats_saved_userdata % todo: reset this in non start|stop cases
751
752%D We abuse the settings to pick up some float parameters too which makes it
753%D messy.
754
755%D Do we need a \setuplayout here (kind of costly) in case we mix multi page text
756%D with a side float and less height.
757
758\permanent\tolerant\protected\def\startplacefloat[#tag]#spacer[#S#settings]#spacer[#S#userdata]%
759  {\flushnotes
760  %\setuplayout
761   \page_otr_command_flush_side_floats % here !
762   \strc_floats_begin_group
763   \strc_floats_set_current_tag{#tag}%
764   \strc_floats_reset_variables
765   % save
766   \edef\p_location    {\floatcaptionparameter\c!location}%
767   \edef\p_topoffset   {\floatcaptionparameter\c!topoffset}%
768   \edef\p_bottomoffset{\floatcaptionparameter\c!bottomoffset}%
769   \edef\p_freeregion  {\floatcaptionparameter\c!freeregion}%
770   % preset
771   \resetfloatcaptionparameter      \c!location
772   \setexpandedfloatcaptionparameter\c!topoffset   {\floatparameter\c!topoffset}%
773   \setexpandedfloatcaptionparameter\c!bottomoffset{\floatparameter\c!bottomoffset}%
774   \setexpandedfloatcaptionparameter\c!freeregion  {\floatparameter\c!freeregion}%
775   \resetfloatcaptionparameter      \c!reference
776   \resetfloatcaptionparameter      \c!title
777   \resetfloatcaptionparameter      \c!marking
778   \resetfloatcaptionparameter      \c!list
779   \resetfloatcaptionparameter      \c!bookmark
780   \resetfloatcaptionparameter      \c!referencetext
781   % pickup
782   \ifparameter#settings\or
783     \setupcurrentfloatcaption[#settings]%
784   \fi
785   \ifparameter#userdata\or
786     \setupcurrentfloatuserdata[#userdata]%
787     \def\m_strc_floats_saved_userdata{#userdata}%
788   \else
789     \lettonothing\m_strc_floats_saved_userdata
790   \fi
791   \edef\p_mode{\floatcaptionparameter\s!mode}%
792   \ifempty\p_mode
793     \let\strc_floats_stop_place\strc_floats_stop_place_yes
794     \strc_floats_start_place_yes
795   \orelse\ifmode{\p_mode}%
796     \let\strc_floats_stop_place\strc_floats_stop_place_yes
797     \strc_floats_start_place_yes
798   \else
799     \let\strc_floats_stop_place\strc_floats_stop_place_nop
800     \strc_floats_start_place_nop
801   \fi}
802
803\def\strc_floats_start_place_yes
804  {% check (see elsewhere
805   \edef\floatlocationdefault{\floatparameter\c!default}%
806   \edef\floatlocation{\floatcaptionparameter\c!location}%
807   \ifempty\floatlocation
808     \let\floatlocation\floatlocationdefault % beware of a clash between alignment locations
809   \fi
810   % inherit
811   \setexpandedfloatparameter\c!topoffset   {\floatcaptionparameter\c!topoffset}%
812   \setexpandedfloatparameter\c!bottomoffset{\floatcaptionparameter\c!bottomoffset}%
813   \setexpandedfloatparameter\c!freeregion  {\floatcaptionparameter\c!freeregion}%
814   % restore
815   \letfloatcaptionparameter\c!location    \p_location
816   \letfloatcaptionparameter\c!topoffset   \p_topoffset
817   \letfloatcaptionparameter\c!bottomoffset\p_bottomoffset
818   \letfloatcaptionparameter\c!freeregion  \p_freeregion
819   %
820   \strc_floats_analyze_location
821   \ifinset\v!split\floatlocation
822     \expandafter\strc_floats_place_next_box_split
823   \else
824     \expandafter\strc_floats_place_next_box_normal
825   \fi
826   \bgroup
827   \ignorespaces}
828
829\def\strc_floats_stop_place_yes
830  {\removeunwantedspaces
831   \egroup}
832
833\def\strc_floats_start_place_nop
834  {\directsetup{\p_mode:\currentfloat:\v!before}%
835   \bgroup
836   \ignorespaces}
837
838\def\strc_floats_stop_place_nop
839  {\removeunwantedspaces
840   \egroup
841   \directsetup{\p_mode:\currentfloat:\v!after}%
842   \strc_floats_end_group}
843
844\permanent\protected\def\stopplacefloat
845  {\strc_floats_stop_place}
846
847% reserve
848
849\protected\def\strc_floats_reserve
850  {\flushnotes
851   \page_otr_command_flush_side_floats % here !
852   \strc_floats_begin_group
853   \strc_floats_place}
854
855\def\strc_floats_reserve_box#settings%
856  {\begingroup
857   \setupcurrentfloat[\c!frame=\v!on,#settings]%
858   \inheritedfloatframed{}%
859   \endgroup}
860
861% text
862
863\permanent\tolerant\protected\def\startfloattext[#tag]#spacer[#location]#spacer[#reference]%
864  {\flushnotes      % Here indeed?
865   \page_otr_command_flush_side_floats % Here indeed?
866   \strc_floats_begin_text_group
867   \strc_floats_place[#tag][\v!text,#location,\v!left][#reference]}
868
869\protected\def\stopfloattext
870  {\strc_floats_stop_text_indeed}
871
872\ifdefined\startcontent \else \aliased\let\startcontent\relax \fi
873\ifdefined\stopcontent  \else \aliased\let\stopcontent \relax \fi
874\ifdefined\startentry   \else \aliased\let\startentry  \relax \fi
875\ifdefined\stopentry    \else \aliased\let\stopentry   \relax \fi
876
877\permanent\tolerant\protected\def\startplacefloattext[#tag]#spacer[#S#settings]#spacer[#S#userdata]%
878  {\begingroup
879   %
880   \flushnotes % Here indeed?
881   \page_otr_command_flush_side_floats % Here indeed?
882   %
883   \strc_floats_set_current_tag{#tag}%
884   \strc_floats_reset_variables
885   \resetfloatcaptionparameter\c!location
886   \resetfloatcaptionparameter\c!reference
887   \resetfloatcaptionparameter\c!title
888   \resetfloatcaptionparameter\c!marking
889   \resetfloatcaptionparameter\c!list
890   \resetfloatcaptionparameter\c!bookmark
891   \resetfloatcaptionparameter\c!referencetext
892   % pickup
893   \ifparameter#settings\or
894     \setupcurrentfloatcaption[#settings]%
895   \fi
896   \xdef\askedfloatoptions{\v!text,\floatcaptionparameter\c!location,\v!left}%
897   \edef\floatlocationdefault{\floatparameter\c!default}%
898   \let\floatlocation\askedfloatoptions
899   \strc_floats_analyze_location
900   \resetfloatcaptionparameter\c!location
901   \ifparameter#userdata\or
902     \setupcurrentfloatuserdata[#userdata]%
903     \def\m_strc_floats_saved_userdata{#userdata}%
904   \else
905     \lettonothing\m_strc_floats_saved_userdata
906   \fi
907   \enforced\let\startcontent\strc_floats_text_content_start
908   \enforced\let\stopcontent\strc_floats_text_content_stop
909   \enforced\let\startentry\strc_floats_text_entry_start
910   \enforced\let\stopentry \strc_floats_text_entry_stop}
911
912\protected\def\stopplacefloattext
913  {\strc_floats_stop_text_indeed
914   \endgroup}
915
916\protected\def\strc_floats_text_content_start
917  {\setbox\floatbox\vbox\bgroup
918   \ignorespaces}
919
920\protected\def\strc_floats_text_content_stop
921  {\removeunwantedspaces
922   \egroup
923   \strc_floats_begin_text_group
924   \strc_floats_place_next_box_normal{\box\floatbox}}
925
926\protected\def\strc_floats_text_entry_start
927  {\ignorespaces}
928
929\protected\def\strc_floats_text_entry_stop
930  {\removeunwantedspaces}
931
932% reserved text
933
934\tolerant\protected\def\strc_floats_start_reserve_text[#tag]#spacer[#S#settings]#spacer[#location]#spacer[#reference]#:#caption%%
935  {\flushnotes
936   \page_otr_command_flush_side_floats
937   \strc_floats_begin_text_group
938   \strc_floats_place[#tag][\v!text,#location,\v!left][#reference]{#caption}{\strc_floats_reserve_box{#settings}}}
939
940\protected\def\strc_floats_stop_reserve_text
941  {\strc_floats_stop_text_indeed}
942
943% special hack
944
945\def\strc_floats_begin_group     {\begingroup}
946\def\strc_floats_end_group       {\carryoverpar\endgroup} % hm
947\def\strc_floats_end_split_group {\endgroup}
948\def\strc_floats_begin_text_group{\begingroup\let\strc_floats_end_group\relax}
949\def\strc_floats_end_text_group  {\endgroup}
950
951% implementation
952
953%setnewconstant\c_page_one_float_method  \zerocount % 0=raw 1=safe (.99) 2=tight (-1pt) / belongs in page-one
954\setnewconstant\c_strc_floats_rotation   \zerocount % 0 90 180 270
955\newconditional\c_strc_floats_par_float
956
957\ifdefined\page_margin_strc_floats_before    \else \let\page_margin_strc_floats_before   \relax \fi
958\ifdefined\page_margin_strc_floats_set_hsize \else \let\page_margin_strc_floats_set_hsize\relax \fi
959
960\immutable\def\flushfloatslist
961  {\v!left,\v!right,\v!inner,\v!outer,%
962   \v!backspace,\v!cutspace,%
963   \v!inleft,\v!inright,\v!inmargin,%
964   \v!leftmargin,\v!rightmargin,\v!leftedge,\v!rightedge,%
965   \v!innermargin,\v!outermargin,\v!inneredge,\v!outeredge,%
966   \v!text,\v!opposite}% \v!page
967
968% \protected\def\strc_floats_place_next_box_split
969%   {\let\splitfloatfinalizer\strc_floats_end_split_group
970%    \let\strc_floats_end_group\relax
971%    \splitfloat{\strc_floats_place_next_box_normal}}
972
973\protected\def\strc_floats_place_next_box_split
974  {\let\splitfloatfinalizer\strc_floats_end_split_group
975   \let\strc_floats_end_group\relax
976  %\ifnumexpression \c_strc_floats_rotation=90 or \c_strc_floats_rotation=270 \relax
977   \ifnumexpression (\c_strc_floats_rotation=90) or (\c_strc_floats_rotation=270) \relax
978     \splitfloatfixedheight\conditionaltrue
979     \def\splitfloatheight{\textwidth}%
980   \fi
981   \splitfloat{\strc_floats_place_next_box_normal}}
982
983\protected\def\strc_floats_place_next_box_normal
984  {\ifconditional\c_page_floats_some_waiting
985     % this was \checkwaitingfloats spread all over
986     \ifinset\v!always\floatlocation
987       \showmessage\m!floatblocks5\empty
988     \orelse\ifcommon\floatlocation\flushfloatslist
989       \page_otr_command_flush_floats
990     \fi
991     % but which should be done before using box \floatbox
992   \fi
993   \page_margin_strc_floats_before % todo: each float handler gets a before
994   \global\insidefloattrue
995   \dostarttaggedchained\t!float\currentfloat\??float
996   \page_margin_strc_floats_set_hsize % todo: each float handler gets a set_hsize
997   \expand\everyinsidefloat
998   \strc_floats_analyze_variables_one
999   \dostarttagged\t!floatcontent\empty
1000   \dowithnextboxcontent
1001     {\strc_floats_set_local_hsize
1002      \floatparameter\c!inner
1003      \postponenotes} % new
1004     {\page_postprocessors_linenumbers_box\nextbox % for aditya
1005      \dostoptagged
1006      \strc_floats_finish_placement}
1007     \vbox}
1008
1009%D \starttyping
1010%D \definefloat
1011%D   [one] [figure]
1012%D   [default=right,
1013%D    rightmargindistance=-20cm,
1014%D    criterium=129pt,
1015%D    fallback=rightmargin]
1016%D
1017%D \definefloat
1018%D   [two] [figure]
1019%D   [default=right,
1020%D    rightmargindistance=-20cm,
1021%D    criterium=129pt,
1022%D    fallback=three]
1023%D
1024%D \definefloat
1025%D   [three] [figure]
1026%D   [default=rightmargin,
1027%D    rightmargindistance=0cm]
1028%D
1029%D \placefloat[one]{}{\blackrule[width=30pt]}  \samplefile{tufte}
1030%D \placefloat[one]{}{\blackrule[width=60pt]}  \samplefile{tufte}
1031%D \placefloat[one]{}{\blackrule[width=90pt]}  \samplefile{tufte}
1032%D \placefloat[one]{}{\blackrule[width=130pt]} \samplefile{tufte}
1033%D \placefloat[two]{}{\blackrule[width=130pt]} \samplefile{tufte}
1034%D \stoptyping
1035
1036\def\strc_floats_finish_placement
1037  {\ifempty{\floatparameter\c!criterium}\else
1038     \ifdim\wd\nextbox>\floatparameter\c!criterium\relax
1039       \edef\forcedfloatmethod{\floatparameter\c!fallback}%
1040       \ifempty\forcedfloatmethod \else
1041         \doifelsecommandhandler\??float\forcedfloatmethod
1042           {\let\currentfloat\forcedfloatmethod
1043            \edef\floatlocationdefault{\floatparameter\c!default}%
1044            \let\floatlocation\floatlocationdefault
1045            \let\forcedfloatmethod\floatlocationdefault}
1046           \donothing
1047       \fi
1048       \ifempty\forcedfloatmethod
1049         \let\forcedfloatmethod\v!here
1050       \fi
1051     \fi
1052   \fi
1053   \strc_floats_check_extra_actions
1054   \strc_floats_analyze_variables_two
1055   \strc_floats_place_packaged_boxes
1056   \dotagregisterfloat\askedfloatoptions\askedfloatmethod
1057   \dostoptagged % tricky .... needs checking
1058   % we need to carry over the par because of side floats
1059   \global\d_page_sides_downshift \zeropoint
1060   \global\d_page_sides_extrashift\zeropoint
1061   \ifconditional\c_strc_floats_par_float
1062     \ifinset\v!reset\floatlocation
1063       \page_sides_forget_floats
1064     \fi
1065     \doinhibitblank
1066   \fi
1067   \strc_floats_end_group}
1068
1069% nicer is a bunch of states and one loop that sets those states
1070
1071\newdimension\d_strc_floats_top
1072\newdimension\d_strc_floats_bottom
1073\newdimension\d_strc_floats_overflow
1074
1075% \def\strc_floats_calculate_skip#target#skip%
1076%   {\begingroup
1077%    \edef\askedfloatskip{\rootfloatparameter#skip}%
1078%    \ifempty\askedfloatskip
1079%      \global#target\zeropoint
1080%    \orelse\ifx\askedfloatskip\v!none
1081%      \global#target\zeropoint
1082%    \else
1083%      \setbox\scratchbox\vbox{\whitespace\blank[\askedfloatskip]}% todo: move whitespace inside blank
1084%      \global#target\ht\scratchbox
1085%    \fi
1086%    \endgroup}
1087
1088\def\strc_floats_calculate_skip#target#skip%
1089  {\begingroup
1090   \edef\p_blank{\rootfloatparameter#skip}%
1091   \ifx\p_blank\v!nowhite
1092     \edef\p_blank{-\v!white}%
1093   \fi
1094   \prerollblank[\p_blank]%
1095   \global#target\prerolledblank
1096   \endgroup}
1097
1098\def\strc_floats_analyze_variables_two
1099  {\ifinsidecolumns
1100     \global\c_strc_floats_par_float\conditionalfalse
1101   \orelse\ifcommon\floatlocation\flushfloatslist
1102     \global\c_strc_floats_par_float\conditionaltrue
1103   \else
1104     \global\c_strc_floats_par_float\conditionalfalse
1105   \fi
1106   % variable initializations
1107   \global\d_page_sides_shift       \zeropoint
1108   \global\d_page_sides_maximum     \zeropoint
1109   \global\c_page_sides_align       \zerocount
1110   \global\c_page_sides_tolerance   \zerocount
1111   \global\c_page_sides_skipmode    \zerocount
1112   \global\c_strc_floats_rotation   \zerocount
1113   \global\d_page_sides_margin      \floatparameter\c!margin
1114   \global\d_page_sides_leftshift   \floatparameter\c!leftmargindistance
1115   \global\d_page_sides_rightshift  \floatparameter\c!rightmargindistance
1116   \global\d_page_sides_topoffset   \floatparameter\c!topoffset
1117   \global\d_page_sides_bottomoffset\floatparameter\c!bottomoffset
1118   \global\c_page_sides_method      \floatparameter\c!sidemethod
1119   \global\c_page_one_float_method  \floatparameter\c!textmethod
1120   \global\c_page_floats_n_of_top   \rootfloatparameter\c!ntop
1121   \global\c_page_floats_n_of_bottom\rootfloatparameter\c!nbottom
1122   \global\d_strc_floats_overflow   \zeropoint
1123   \global\c_page_sides_shape_down\conditionalfalse
1124   \ifconditional\c_strc_floats_par_float
1125     \global\d_strc_floats_top        \zeropoint
1126     \global\d_strc_floats_bottom     \zeropoint
1127     \strc_floats_calculate_skip\d_page_sides_topskip   \c!sidespacebefore
1128     \strc_floats_calculate_skip\d_page_sides_bottomskip\c!sidespaceafter
1129     \strc_floats_calculate_skip\d_page_sides_midskip   \c!sidespaceinbetween
1130     \strc_floats_calculate_skip\d_strc_floats_top      \c!spacebeforeside
1131     \strc_floats_calculate_skip\d_strc_floats_bottom   \c!spaceafterside
1132   \else
1133     \global\d_page_sides_topskip     \zeropoint
1134     \global\d_page_sides_bottomskip  \zeropoint
1135     \strc_floats_calculate_skip\d_strc_floats_top   \c!spacebefore
1136     \strc_floats_calculate_skip\d_strc_floats_bottom\c!spaceafter
1137   \fi
1138   % keyword handling
1139   \ifconditional\c_strc_floats_par_float
1140     \processaction
1141       [\floatparameter\c!sidealign]
1142       [\v!height=>\global\c_page_sides_align\plusone  ,%
1143          \v!line=>\global\c_page_sides_align\plustwo  ,% (***)
1144         \v!depth=>\global\c_page_sides_align\plusthree,%
1145          \v!grid=>\global\c_page_sides_align\plusfour ,%
1146      \v!halfline=>\global\c_page_sides_align\plusfive ]%
1147     \ifcase\c_page_sides_align\relax % todo: optie v!lokaal => \else
1148       \ifinset\v!height  \floatlocation\global\c_page_sides_align\plusone  \fi
1149       \ifinset\v!line    \floatlocation\global\c_page_sides_align\plustwo  \fi
1150       \ifinset\v!depth   \floatlocation\global\c_page_sides_align\plusthree\fi
1151       \ifinset\v!grid    \floatlocation\global\c_page_sides_align\plusfour \fi
1152       \ifinset\v!halfline\floatlocation\global\c_page_sides_align\plusfive \fi % meant for 'none'
1153     \fi
1154     \ifinset\v!high        \floatlocation\global\c_page_sides_skipmode \plusone  \fi
1155     \ifinset\v!low         \floatlocation\global\c_page_sides_skipmode \plustwo  \fi
1156     \ifinset\v!fit         \floatlocation\global\c_page_sides_skipmode \plusthree\fi
1157     \ifinset\v!tolerant    \floatlocation\global\c_page_sides_tolerance\plusone  \fi
1158     \ifinset\v!verytolerant\floatlocation\global\c_page_sides_tolerance\plustwo  \fi
1159   \else
1160     \processallactionsinset
1161       [\floatlocation]%
1162       [ 90=>\global\c_strc_floats_rotation\commalistelement\relax,%
1163        180=>\global\c_strc_floats_rotation\commalistelement\relax,%
1164        270=>\global\c_strc_floats_rotation\commalistelement\relax]%
1165   \fi
1166   \ifinset\v!force\floatlocation
1167     \global\c_page_sides_shape_down\conditionaltrue
1168   \else
1169     \global\c_page_sides_shape_down\conditionalfalse
1170   \fi
1171   \ifinset\v!keeptogether\floatlocation
1172     \global\c_page_sides_keep_together\conditionaltrue
1173   \else
1174     \global\c_page_sides_keep_together\conditionalfalse
1175   \fi
1176   \ifinset\v!nonumber\floatlocation
1177     \global\nofloatnumbertrue
1178   \orelse\ifcstok{\floatcaptionparameter\c!number}\v!yes
1179     \global\nofloatnumberfalse
1180   \else
1181     \global\nofloatnumbertrue
1182   \fi
1183   \ifinset\v!none\floatlocation
1184     \global\nofloatcaptiontrue
1185   \else
1186     \global\nofloatcaptionfalse
1187   \fi
1188   \ifcstok{\floatcaptionparameter\c!number}\v!none % new
1189     \global\nofloatcaptiontrue
1190   \fi
1191   \ifinset\v!effective\floatlocation
1192     \letfloatparameter       \c!leftmargin \effectiveleftskip
1193     \letfloatparameter       \c!rightmargin\effectiverightskip
1194     \letfloatcaptionparameter\c!leftmargin \effectiveleftskip
1195     \letfloatcaptionparameter\c!rightmargin\effectiverightskip
1196   \fi
1197   \ifemptyfloatcaption \ifnofloatnumber
1198     \global\nofloatcaptiontrue
1199   \fi \fi}
1200
1201% documenteren in details
1202
1203\def\strc_floats_analyze_variables_one
1204  {\ifcstok{\floatparameter\c!local}\v!yes % fout keyword
1205     \c_page_floats_center_box_global\conditionaltrue
1206   \else
1207     \c_page_floats_center_box_global\conditionalfalse
1208   \fi
1209   \ifconditional\c_page_floats_center_box_global
1210     \c_page_floats_center_box_local\conditionaltrue
1211   \orelse\ifinset\v!local\floatlocation
1212     \c_page_floats_center_box_local\conditionaltrue
1213   \else
1214     \c_page_floats_center_box_local\conditionalfalse
1215   \fi
1216   \ifcstok{\floatparameter\c!freeregion}\v!yes
1217     \c_strc_floats_mark_as_free\conditionaltrue
1218   \else
1219     \c_strc_floats_mark_as_free\conditionalfalse
1220   \fi
1221   \ifcommon{\v!always,\v!here,\v!force}\floatlocation
1222     % ! ! ! ! ! !
1223   \else
1224     \c_page_floats_center_box_global\conditionalfalse
1225     \c_page_floats_center_box_local\conditionalfalse
1226   \fi}
1227
1228\permanent\def\naturalfloatheight{\the\naturalfloatwd}
1229\permanent\def\naturalfloatwidth {\the\naturalfloatht}
1230\permanent\def\naturalfloatdepth {\the\naturalfloatdp}
1231
1232\permanent\def\floatcaptionheight{\the\floatcaptionwd}
1233\permanent\def\floatcaptionwidth {\the\floatcaptionht}
1234\permanent\def\floatcaptiondepth {\the\floatcaptiondp}
1235
1236\newdimension\naturalfloatwd
1237\newdimension\naturalfloatht
1238\newdimension\naturalfloatdp
1239
1240\newdimension\floatcaptionwd
1241\newdimension\floatcaptionht
1242\newdimension\floatcaptiondp
1243
1244\def\strc_floats_set_natural_dimensions#box%
1245  {\global\naturalfloatwd\wd#box\relax
1246   \global\naturalfloatht\ht#box\relax
1247   \global\naturalfloatdp\dp#box\relax}
1248
1249\def\strc_floats_set_caption_dimensions#box%
1250  {\global\floatcaptionwd\wd#box\relax
1251   \global\floatcaptionht\ht#box\relax
1252   \global\floatcaptiondp\dp#box\relax}
1253
1254\permanent\def\doifelsemainfloatbody
1255  {\unless\ifinsidesplitfloat
1256     \expandafter\firstoftwoarguments
1257   \orelse\ifconditional\splitfloatfirstdone
1258     \expandafter\secondoftwoarguments
1259   \else
1260     \expandafter\firstoftwoarguments
1261   \fi}
1262
1263\aliased\let\doifmainfloatbodyelse\doifelsemainfloatbody
1264
1265% todo: optional user pars
1266
1267\def\floatcaptionattribute
1268  {\iflocation
1269     \ifempty\currentfloatattribute
1270       % safeguard, can be samepage too
1271     \orelse\ifnofloatcaption
1272     \orelse\ifinsidesplitfloat
1273       \ifconditional\splitfloatfirstdone
1274       \else
1275         attr \destinationattribute \currentfloatattribute
1276       \fi
1277     \else
1278       attr \destinationattribute \currentfloatattribute
1279     \fi
1280   \fi}
1281
1282% \def\floatcaptionattribute
1283%   {\iflocation
1284%      \ifempty\currentfloatattribute
1285%        % safeguard, can be samepage too
1286%      \orelse\ifnofloatcaption
1287%        % nothing
1288%      \orunless\ifinsidesplitfloat
1289%        attr \destinationattribute \currentfloatattribute
1290%      \orunless\ifconditional\splitfloatfirstdone
1291%        attr \destinationattribute \currentfloatattribute
1292%      \fi
1293%    \fi}
1294
1295\newconditional\usesamefloatnumber
1296
1297% \startplacefigure[location=here,reference=first, title=first, group=alpha,groupsuffix=.a]
1298%     \externalfigure[dummy][height=2cm]
1299% \stopplacefigure
1300% \startplacefigure[location=here,reference=second,title=second,group=alpha,groupsuffix=.b]
1301%     \externalfigure[dummy][height=2cm]
1302% \stopplacefigure
1303%
1304% uses:
1305
1306\def\strc_floats_group_index
1307  {\numexpr\clf_listgroupindex{\currentfloat}{\currentfloatgroup}\relax}
1308
1309%D A lightweight subnumber feature:
1310%D
1311%D \starttyping
1312%D \startplacefigure [location=none]
1313%D   \startsubfloatnumbering
1314%D     \startfloatcombination [nx=3]
1315%D       \startplacefigure [title=Left]   \externalfigure \stopplacefigure
1316%D       \startplacefigure [title=Middle] \externalfigure \stopplacefigure
1317%D       \startplacefigure [title=Right]  \externalfigure \stopplacefigure
1318%D     \stopfloatcombination
1319%D   \stopsubfloatnumbering
1320%D \stopplacefigure
1321%D \stoptyping
1322
1323\glettonothing\currentsubfloatcounter
1324
1325\permanent\protected\def\startsubfloatnumbering
1326  {\glet\currentsubfloatcounter\s!unknown}
1327
1328\permanent\protected\def\stopsubfloatnumbering
1329  {\strc_counters_reset_sub\currentsubfloatcounter\plustwo
1330   \glettonothing\currentsubfloatcounter}
1331
1332\defineconversionset[subfloats][number,characters]
1333
1334\setupcaptions
1335 %[figure]
1336  [\c!numberconversionset=subfloats]
1337
1338\def\strc_floats_place_packaged_boxes
1339  {\expandafter\strc_floats_place_packaged_boxes_indeed\expandafter{\m_strc_floats_saved_userdata}}
1340
1341\def\strc_floats_place_packaged_boxes_indeed#userdata%
1342  {\bgroup
1343   \ifconditional\usesamefloatnumber
1344     \glet\currentfloatnumber\m_strc_floats_previous_number
1345     \glettonothing\currentfloatattribute
1346     \glet\currentfloatsynchronize\relax
1347   \else
1348     \edef\currentfloatcounter{\namedcounterparameter\currentfloat\s!name}%
1349     \edef\currentfloatgroup  {\floatcaptionparameter\c!group}%
1350     \ifnofloatnumber
1351     \orelse\ifnofloatcaption
1352     \orelse\ifempty\currentfloatgroup
1353       % independent
1354       \iftrialtypesetting\strc_counters_save\currentfloatcounter\fi
1355       \ifempty\currentsubfloatcounter
1356         \strc_counters_increment\currentfloatcounter
1357         \strc_counters_reset_sub\currentfloatcounter\plustwo
1358       \else
1359         \ifcase\strc_counters_raw_sub\currentfloatcounter\plustwo\relax
1360           \strc_counters_increment\currentfloatcounter
1361           \strc_counters_reset_sub\currentfloatcounter\plustwo
1362         \fi
1363         \strc_counters_increment_sub\currentfloatcounter\plustwo
1364         \glet\currentsubfloatcounter\currentfloatcounter
1365       \fi
1366     \orelse\ifcase\strc_floats_group_index
1367       % first in group
1368       \iftrialtypesetting\strc_counters_save\currentfloatcounter\fi
1369       \strc_counters_increment\currentfloatcounter
1370     \else
1371       % next in group
1372     \fi
1373     % *1* as an alternative we could set counter parameters here if needed
1374     \strc_counters_register_component
1375       \s!float
1376       \setupcurrentfloatcaption
1377       \floatcaptionparameter
1378       \detokenizedfloatcaptionparameter
1379       \relax
1380       \relax
1381       \relax
1382       [\s!name=\currentfloat,% was c!name
1383        \s!counter=\currentfloatcounter,%
1384        \s!hascaption=\ifnofloatcaption \v!no\else\v!yes\fi,%
1385        \s!hasnumber=\ifnofloatnumber   \v!no\else\v!yes\fi,%
1386        \s!hastitle=\ifemptyfloatcaption\v!no\else\v!yes\fi]%
1387       [#userdata]%
1388     \glet\m_strc_floats_previous_number\m_strc_counters_last_registered_index
1389     \glet\currentfloatnumber           \m_strc_counters_last_registered_index
1390     \glet\currentfloatattribute        \m_strc_counters_last_registered_attribute
1391     \glet\currentfloatsynchronize      \m_strc_counters_last_registered_synchronize
1392   \fi
1393   %
1394   \iftrialtypesetting\else\global\usesamefloatnumber\conditionalfalse\fi % one shot
1395   % check float box
1396   \strc_floats_set_natural_dimensions\nextbox
1397   \global\setbox\floatbox\vbox{\floatparameter\c!command{\box\nextbox}}% can be anything so no pack
1398   \strc_floats_set_natural_dimensions\floatbox
1399   \ifzeropt\htdp\floatbox
1400     \showmessage\m!floatblocks{11}\empty
1401     \global\setbox\floatbox\vpack
1402       {\dostarttagged\t!floatcontent\empty
1403        \strc_floats_place_empty_box
1404        \dostoptagged}%
1405   \fi
1406   % deal with lack of caption
1407   \global\setbox\floatbox\vpack \floatcaptionattribute
1408     {\doifelsemainfloatbody\currentfloatsynchronize\donothing
1409      \unvbox\floatbox
1410      \ifnofloatcaption
1411        \vss
1412      \fi}% gets rid of the depth (unless tabulate)
1413   \iftrialtypesetting\strc_counters_restore\currentfloatcounter\fi
1414   \egroup
1415   % place the float
1416   \strc_floats_set_box
1417   \strc_floats_get_box
1418   \global\insidefloatfalse}
1419
1420\newdimension\availablefloatwidth
1421\newdimension\availablefloatheight
1422
1423\def\strc_floats_set_local_hsize
1424  {\ifconditional\c_page_floats_center_box_local
1425     % also available check here?
1426     \seteffectivehsize
1427     \hsize\localhsize
1428   \orelse\ifinset\v!margin\floatlocation % brr, really needed! see wm will be redone
1429     \hsize\namedmarginblockparameter\empty\c!width
1430   \fi
1431   \edef\p_availablewidth {\floatparameter\c!availablewidth }%
1432   \edef\p_availableheight{\floatparameter\c!availableheight}%
1433   \availablefloatwidth \ifempty\p_availablewidth \hsize\else\p_availablewidth \relax\fi
1434   \availablefloatheight\ifempty\p_availableheight\vsize\else\p_availableheight\relax\fi}
1435
1436\ifdefined\everyinsidefloat \else \newevery \everyinsidefloat \relax \fi
1437
1438\appendtoks
1439    \everyinsidefloat\emptytoks % in case it's called earlier
1440    \strc_float_load_data
1441\to \everyinsidefloat
1442
1443\permanent\def\doifelserightpagefloat
1444  {\unless\ifdoublesided
1445     \expandafter\firstoftwoarguments
1446   \orelse\ifsinglesided
1447     \expandafter\firstoftwoarguments
1448   \orelse\ifodd\purenumber\strc_float_realpage\space
1449     \expandafter\firstoftwoarguments
1450   \else
1451     \expandafter\secondoftwoarguments
1452   \fi}
1453
1454\permanent\def\doifelseoddpagefloat
1455  {\ifodd\purenumber\strc_float_realpage\space
1456     \expandafter\firstoftwoarguments
1457   \else
1458     \expandafter\secondoftwoarguments
1459   \fi}
1460
1461\aliased\let\doifrightpagefloatelse\doifelserightpagefloat
1462\aliased\let\doifoddpagefloatelse  \doifelseoddpagefloat
1463
1464\appendtoks
1465    \enforced\let\rightorleftpageaction\doifelserightpagefloat
1466\to \everyinsidefloat
1467
1468% \let\movesidefloat\gobbleoneargument
1469
1470% new : \place...[leftmargin,-2*line]; we need to catch fxtb:2*3
1471% watch out: line alone aligns on the line ! ! !
1472
1473\permanent\protected\def\movesidefloat[#S#settings]% (-)n*line|x=,y=
1474  {\global\d_page_sides_downshift \zeropoint
1475   \global\d_page_sides_extrashift\zeropoint
1476   \ifhastok={#settings}%
1477     \begingroup
1478     \setupcurrentfloat[\c!x=\zeropoint,\c!y=\zeropoint,#settings]%
1479     \ifgridsnapping
1480       \getnoflines{\floatparameter\c!y}%
1481       \global\d_page_sides_downshift\noflines\lineheight
1482     \else
1483       \global\d_page_sides_downshift\floatparameter\c!y
1484     \fi
1485     \global\d_page_sides_extrashift\floatparameter\c!x
1486     \endgroup
1487   \else
1488     \movedownsidefloat[#settings]%
1489   \fi}
1490
1491\installcorenamespace{floatmovement}
1492
1493\defcsname\??floatmovement \v!line\endcsname{\strc_floats_move_down_line+}
1494\defcsname\??floatmovement+\v!line\endcsname{\strc_floats_move_down_line+}
1495\defcsname\??floatmovement-\v!line\endcsname{\strc_floats_move_down_line-}
1496\defcsname\??floatmovement \v!hang\endcsname{\strc_floats_move_down_hang\plusone}
1497\defcsname\??floatmovement+\v!hang\endcsname{\strc_floats_move_down_hang\plusone}
1498\defcsname\??floatmovement-\v!hang\endcsname{\strc_floats_move_down_hang\minusone}
1499
1500\defcsname\??floatmovement-2*\v!line\endcsname{\strc_floats_move_down_line{-2}}
1501\defcsname\??floatmovement+2*\v!line\endcsname{\strc_floats_move_down_line{2}}
1502\defcsname\??floatmovement 2*\v!line\endcsname{\strc_floats_move_down_line{2}}
1503
1504\permanent\protected\def\installfloatmovement#1#2{\defcsname\??floatmovement#1\endcsname{#2}}
1505
1506\def\strc_floats_move_down#setting%
1507  {\begincsname\??floatmovement#setting\endcsname}
1508
1509\def\strc_floats_move_down_line#sign%
1510  {\ifscratchconditionone \else
1511     \global\d_page_sides_downshift\zeropoint
1512     \scratchconditiononetrue
1513   \fi
1514   \global\advanceby\d_page_sides_downshift#sign\lineheight}
1515
1516\def\strc_floats_move_down_hang#lines%
1517  {\ifscratchconditiontwo \else
1518     \global\c_page_sides_n_of_lines\zerocount
1519     \scratchconditiontwotrue
1520   \fi
1521   \global\advanceby\c_page_sides_n_of_lines#lines\relax}
1522
1523\permanent\protected\def\movedownsidefloat[#S#settings]% already in core
1524  {\unless\ifhastok:{#settings}%
1525     \begingroup
1526     \scratchconditiononefalse
1527     \scratchconditiontwofalse
1528     \normalexpanded{\dorepeatwithcommand[#settings]}\strc_floats_move_down
1529     \endgroup
1530   \fi}
1531
1532\permanent\protected\def\hangsidefloat[#number]%
1533  {\global\c_page_sides_n_of_lines#number\relax}
1534
1535\mutable\lettonothing\extrafloatlocation
1536
1537\def\strc_floats_set_extra_action#rightpagelocation#leftpagelocation%
1538  {\rightorleftpageaction
1539     {\let\extrafloatlocation#rightpagelocation}%
1540     {\let\extrafloatlocation#leftpagelocation}}
1541
1542
1543\installcorenamespace{extrafloataction}
1544
1545\defcsname\??extrafloataction      \v!inner\endcsname#1{\strc_floats_set_extra_action\v!left       \v!right}
1546\defcsname\??extrafloataction      \v!outer\endcsname#1{\strc_floats_set_extra_action\v!right      \v!left}
1547\defcsname\??extrafloataction\v!innermargin\endcsname#1{\strc_floats_set_extra_action\v!leftmargin \v!rightmargin}
1548\defcsname\??extrafloataction\v!outermargin\endcsname#1{\strc_floats_set_extra_action\v!rightmargin\v!leftmargin}
1549\defcsname\??extrafloataction  \v!inneredge\endcsname#1{\strc_floats_set_extra_action\v!leftedge   \v!rightedge}
1550\defcsname\??extrafloataction  \v!outeredge\endcsname#1{\strc_floats_set_extra_action\v!rightedge  \v!leftedge}
1551\defcsname\??extrafloataction  \v!backspace\endcsname#1{\strc_floats_set_extra_action\v!backspace  \v!cutspace}
1552\defcsname\??extrafloataction   \v!cutspace\endcsname#1{\strc_floats_set_extra_action\v!cutspace   \v!backspace}
1553%defcsname\??extrafloataction     \v!margin\endcsname#1{\strc_floats_set_extra_action\v!cutspace   \v!backspace}
1554\defcsname\??extrafloataction       \v!left\endcsname#1{\strc_floats_set_extra_action\v!left       \v!left}
1555\defcsname\??extrafloataction      \v!right\endcsname#1{\strc_floats_set_extra_action\v!right      \v!right}
1556\defcsname\??extrafloataction       \v!line\endcsname#1{} % only -n*line is handled (see ***)
1557\defcsname\??extrafloataction    \s!unknown\endcsname#1{\movedownsidefloat[#1]}
1558
1559\def\strc_floats_check_extra_actions % less tracingthis way ....
1560  {\ifinset\v!text\floatlocation\else % fuzzy, text overloads left, since then it's a directive
1561     \lettonothing\extrafloatlocation
1562     % \d_page_sides_downshift will be reset afterwards, and can
1563     % already be set at this point
1564     \processcommacommand[\floatlocation]\strc_floats_check_extra_actions_step
1565     \ifempty\extrafloatlocation\else
1566       \edef\floatlocation{\extrafloatlocation,\floatlocation}%
1567       \setfloatmethodvariables\floatlocation
1568     \fi
1569   \fi}
1570
1571\def\strc_floats_check_extra_actions_step#step%
1572  {\csname\??extrafloataction
1573     \ifcsname\??extrafloataction#step\endcsname#step\else\s!unknown\fi
1574   \endcsname{#step}}
1575
1576% pas op, maxbreedte niet instellen als plaats=links/rechts
1577
1578\def\strc_floats_set_local_dimensions
1579  {\global\d_page_sides_shift  \zeropoint       % duplicate
1580   \global\d_page_sides_maximum\zeropoint\relax % duplicate
1581   \ifzeropt\d_page_sides_downshift\else
1582     \global\setbox\floatbox\vpack
1583       {\vskip\d_page_sides_downshift
1584        \nointerlineskip
1585        \box\floatbox}%
1586   \fi
1587   \edef\p_minwidth{\floatparameter\c!minwidth}%
1588   \ifempty\p_minwidth
1589     % nothing
1590   \else
1591     \scratchwidth\p_minwidth\relax
1592     \ifdim\wd\floatbox<\scratchwidth
1593       \strc_floats_realign_floatbox_horizontal_two
1594     \fi
1595   \fi
1596   % we can also support edges .. in that case no common but a fast loop
1597   \ifinset\v!hanging\floatlocation
1598     \ifcommon{\v!inleft,\v!leftmargin}\floatlocation
1599       \let\p_maxwidth\leftmarginwidth
1600     \orelse\ifcommon{\v!inright,\v!rightmargin}\floatlocation
1601       \let\p_maxwidth\rightmarginwidth
1602     \else
1603       \edef\p_maxwidth{\floatparameter\c!maxwidth}%
1604     \fi
1605   \else
1606     \edef\p_maxwidth{\floatparameter\c!maxwidth}%
1607   \fi
1608   \ifempty\p_maxwidth
1609     % nothing
1610   \else
1611     \scratchwidth\p_maxwidth\relax
1612     \ifdim\wd\floatbox>\scratchwidth
1613       \ifcommon{\v!inright,\v!rightmargin,\v!rightedge,\v!inleft,\v!leftmargin,\v!leftedge}\floatlocation
1614         \global\d_page_sides_maximum\scratchwidth
1615       \orelse\ifcommon{\v!right,\v!left}\floatlocation
1616         \strc_floats_realign_floatbox_horizontal_one
1617       \else
1618         \strc_floats_realign_floatbox_horizontal_two
1619       \fi
1620     \fi
1621   \fi}
1622
1623\def\strc_floats_realign_floatbox_horizontal_one
1624  {\global\setbox\floatbox\hpack to \scratchwidth
1625     {\ifinset\v!right\floatlocation\else\hss\fi
1626      \box\floatbox
1627      \ifinset\v!left\floatlocation\else\hss\fi}}
1628
1629\def\strc_floats_realign_floatbox_horizontal_two % why is this
1630  {\global\setbox\floatbox\hpack to \scratchwidth
1631     {\ifcstok{\floatparameter\c!location}\v!left\else\hss\fi
1632      \box\floatbox
1633      \ifcstok{\floatparameter\c!location}\v!right\else\hss\fi}}
1634
1635\permanent\protected\def\placefloats
1636  {\page_otr_command_flush_floats}
1637
1638\permanent\protected\def\betweenfloatblanko % assumes that spaceafter is present
1639  {\blank[\rootfloatparameter\c!spacebefore]} % or v!back,....
1640
1641% keep as old 1
1642%
1643% \protected\def\doplacefloatbox % used elsewhere
1644%   {%\forgetall % NO
1645%    \whitespace
1646%    \blank[\rootfloatparameter\c!spacebefore]
1647%    \page_otr_command_flush_float_box
1648%    \blank[\rootfloatparameter\c!spaceafter]}
1649%
1650% keep as old 2
1651%
1652% \protected\def\doplacefloatbox % used elsewhere
1653%   {%\forgetall % NO
1654%    \whitespace
1655%    \blank[\rootfloatparameter\c!spacebefore]
1656%    \nointerlineskip
1657%    \flushnotes % new per 2014-05-29 : todo: move them up in the mvl
1658%    \nointerlineskip
1659%    \page_otr_command_flush_float_box
1660%    \nointerlineskip
1661%    \blank[\rootfloatparameter\c!spaceafter]}
1662
1663\def\strc_floats_apply_skip#1%
1664  {\edef\m_space{\rootfloatparameter#1}%
1665   \ifempty\m_space\orelse\ifx\m_space\v!none\else
1666      \directvspacing\m_space
1667   \fi}
1668
1669\permanent\protected\def\doplacefloatbox % used elsewhere
1670  {%\forgetall % NO
1671   \whitespace
1672   \strc_floats_apply_skip\c!spacebefore
1673   \nointerlineskip
1674   \flushnotes % new per 2014-05-29 : todo: move them up in the mvl
1675   \nointerlineskip
1676   \page_otr_command_flush_float_box
1677 % \nointerlineskip % interferes with depth of caption
1678   \strc_floats_apply_skip\c!spaceafter}
1679
1680% test case:
1681%
1682% \placefigure[page,none]{}{\blackrule[width=\textwidth,height=0.9\textheight,color=green]}
1683% \placefigure[page,none]{}{\blackrule[width=\textwidth,height=1.0\textheight,color=green]}
1684% \placefigure[page,none]{}{\blackrule[width=\textwidth,height=1.1\textheight,color=green]}
1685
1686% the [#1] will go away
1687
1688\def\page_one_place_float_text % this macro should be defined elsewhere
1689  {%\checkwaitingfloats\floatlocationmethod
1690   % todo: check if #1 is indeed \floatlocation or maybe more
1691   \global\floatwidth    \wd\floatbox
1692   \global\floatheight   \ht\floatbox % forget about the depth
1693   \global\floattextwidth\dimexpr\hsize-\floatwidth-\rootfloatparameter\c!margin\relax
1694   \edef\floatlocation{\floatlocationmethod}% to be sure .. why
1695   \ifinset\v!tall\floatlocationmethod
1696     \floattextheight\dimexpr\pagegoal-\pagetotal-\bigskipamount\relax % ugly, this bigskip
1697     \ifdim\floattextheight>\textheight
1698       \floattextheight\textheight
1699     \fi
1700     \boxmaxdepth\zeropoint\relax            % toegevoegd
1701     \ifdim\floattextheight<\floatheight
1702       \floattextheight\floatheight
1703     \fi
1704     \setbox\floattext\vbox to \floattextheight
1705   \else
1706     \setbox\floattext\vbox
1707   \fi
1708   \bgroup
1709   \forgetall
1710   \setupblank
1711   \setupwhitespace % new, also needed for footnotes
1712   \blank[\v!disable]
1713   \hsize\floattextwidth
1714   \ignorespaces}
1715
1716\def\strc_floats_stop_text_indeed % todo
1717  {\egroup
1718   \ifinset\v!tall\floatlocation\else
1719     \floattextheight\ifdim\ht\floattext<\floatheight\floatheight\else\ht\floattext\fi
1720   \fi
1721   \setbox\floatbox\vpack to \floattextheight
1722     {\hsize\floatwidth
1723      \ifinset\v!both\floatlocation
1724        \ifinset\v!low\floatlocation
1725          \vfill\box\floatbox
1726        \orelse\ifinset\v!middle\floatlocation
1727          \vfill\box\floatbox\vfill
1728        \else
1729          \box\floatbox\vfill
1730        \fi
1731      \else
1732        \box\floatbox\vfill
1733      \fi}%
1734    \setbox\floattext\vpack to \floattextheight
1735      {\hsize\floattextwidth
1736       \ifinset\v!low\floatlocation
1737         \vfill
1738         \box\floattext
1739         \ifinset\c!offset\floatlocation\whitespace\blank\fi
1740       \orelse\ifinset\v!middle\floatlocation
1741         \vfill
1742         \box\floattext
1743         \vfill
1744       \else
1745         \ifinset\v!offset\floatlocation\whitespace\blank\fi
1746         \box\floattext
1747         \vfill
1748       \fi}%
1749   \ifinset\v!right\floatlocation
1750     \setbox\floatbox\hpack to \hsize
1751       {\box\floattext
1752        \hfill
1753        \box\floatbox}%
1754   \else
1755     \setbox\floatbox\hpack to \hsize
1756       {\box\floatbox
1757        \hfill
1758        \box\floattext}%
1759   \fi
1760   \baselinecorrection
1761   \whitespace
1762   \blank[\rootfloatparameter\c!spacebefore]%
1763   \ifinset\v!tall\floatlocation\else
1764     \dp\floatbox\openstrutdepth% \strutdp % toegevoegd
1765   \fi
1766   \box\floatbox
1767   \dostoptagged
1768   \blank[\rootfloatparameter\c!spaceafter]%
1769   \strc_floats_end_text_group
1770   \page_floats_report_total}
1771
1772\permanent\def\borderedfloatbox
1773  {\begingroup
1774   \setupcurrentfloat[\c!location=\v!normal,\c!width=\v!fit,\c!height=\v!fit]%
1775   \inheritedfloatframed{\box\floatbox}%
1776   \endgroup}
1777
1778% minwidth=fit,width=max : no overshoot, as wide as graphic
1779
1780% keep these as reference:
1781%
1782% \def\strc_floats_align_content_indeed
1783%   {\alignstrutmode\zerocount
1784%    \doifnotcommon\floatcaptionlocation{\v!outermargin,\v!innermargin,\v!leftmargin,\v!rightmargin}
1785%      {\shiftalignedline
1786%         {\floatparameter\c!leftmargin }{\floatparameter\c!rightmargin}%
1787%         {\floatparameter\c!innermargin}{\floatparameter\c!outermargin}}%
1788%    \alignedline{\floatparameter\c!location}\v!middle}
1789%
1790% \def\strc_floats_align_caption_indeed
1791%   {\alignstrutmode\zerocount
1792%    \shiftalignedline
1793%      {\floatcaptionparameter\c!leftmargin }{\floatcaptionparameter\c!rightmargin}%
1794%      {\floatcaptionparameter\c!innermargin}{\floatcaptionparameter\c!outermargin}%
1795%    \alignedline{\floatparameter\c!location}\v!middle}
1796%
1797% Test case:
1798%
1799% \setupfloats[location=left]
1800% \setupfloatcaption[width=max]
1801%
1802% \startfloatcombination
1803%     \placefigure{}{}
1804%     \placefigure{}{}
1805% \stopfloatcombination
1806
1807%D In a floatcombination we ignore the margins .. if that is ever needed we need another
1808%D state (instead of local).
1809
1810\def\strc_floats_align_indeed
1811  {\alignedline{\floatparameter\c!location}\v!middle}
1812
1813\def\strc_floats_shift_indeed#1%
1814  {\shiftalignedline{#1\c!leftmargin}{#1\c!rightmargin}{#1\c!innermargin}{#1\c!outermargin}}
1815
1816\def\strc_floats_align_content_indeed
1817  {\alignstrutmode\zerocount
1818   \ifx\forcedfloatmethod\v!local \else
1819     \ifcommon\floatcaptionlocation{\v!outermargin,\v!innermargin,\v!leftmargin,\v!rightmargin}\else
1820       \strc_floats_shift_indeed\floatparameter
1821     \fi
1822     \expandafter\strc_floats_align_indeed
1823   \fi}
1824
1825\def\strc_floats_align_caption_indeed
1826  {\alignstrutmode\zerocount
1827   \ifx\forcedfloatmethod\v!local
1828     \expandafter\strc_floats_align_indeed_local
1829   \else
1830     \strc_floats_shift_indeed\floatcaptionparameter
1831     \expandafter\strc_floats_align_indeed
1832   \fi}
1833
1834% \def\strc_floats_align_indeed_local#1%
1835%   {\begingroup
1836%    \hsize\wd\floatbox
1837%    \strc_floats_align_indeed{#1}%
1838%    \endgroup}
1839
1840\let\strc_floats_align_indeed_local\firstofoneargument
1841
1842\newdimension\d_strc_floats_content
1843\newdimension\d_strc_float_temp_height
1844\newdimension\d_strc_float_temp_width
1845
1846\newconditional\c_floats_adapt_to_caption_width
1847\newconditional\c_floats_store_minimal_package
1848
1849\newdimension\d_strc_floats_caption_hsize
1850\newdimension\d_strc_floats_caption_min_width
1851\newdimension\d_strc_floats_caption_overshoot
1852
1853% These are expandable, for diagnostic purposes only, but might eventually go away:
1854
1855\permanent\def\captionhsize    {\the\d_strc_floats_caption_hsize}
1856\permanent\def\captionminwidth {\the\d_strc_floats_caption_min_width}
1857\permanent\def\captionovershoot{\the\d_strc_floats_caption_overshoot}
1858
1859\let\strc_floats_align_content\relax
1860\let\strc_floats_align_caption\relax
1861
1862\def\strc_floats_set_caption_criteria % can become parameter (but what name)
1863  {\d_strc_floats_caption_min_width15\bodyfontsize
1864   \d_strc_floats_caption_overshoot 2\emwidth}
1865
1866\let\strc_floats_mark_pag_as_free\relax
1867
1868\def\strc_floats_set_page_variant
1869  {\bgroup
1870   \strc_floats_set_local_hsize
1871   \ifcase\c_strc_floats_rotation\else
1872     % Swapping fails in overloadmode and is also wrong (as it then is persistent due
1873     % to global being inherited).
1874    %\swapdimens\hsize\vsize
1875     \scratchdimen\hsize
1876     \hsize\vsize
1877     \vsize\scratchdimen
1878   \fi
1879   \forgetall
1880   \postponenotes
1881   \dontcomplain
1882   \setbox\b_strc_floats_content\vpack{\borderedfloatbox}%
1883   \let\strc_floats_align_content\strc_floats_align_content_indeed
1884   \let\strc_floats_align_caption\strc_floats_align_caption_indeed
1885   \strc_floats_check_caption_content
1886   \d_strc_floats_content\wd\b_strc_floats_content
1887   \ifcase\floatparameter\c!method
1888     % nothing
1889   \or
1890     % automatic
1891     \ifnofloatcaption
1892       \strc_floats_prepare_no_caption
1893       \strc_floats_set_caption_dimensions\voidbox
1894      %\page_backgrounds_add_local_to_box\floatbox % was \doglobal but not needed
1895       \ifx\forcedfloatmethod\v!local
1896         % we need \ifinfloatcombination
1897         \strc_floats_build_box
1898       \fi
1899     \else
1900       % todo: installable maken, variant/method=auto vs macro
1901       \strc_floats_prepare_page_caption
1902      %\page_backgrounds_add_local_to_box\b_strc_floats_content
1903       \strc_floats_apply_caption_command
1904       \strc_floats_set_caption_dimensions\b_strc_floats_caption
1905      %\moveboxontogrid\b_strc_floats_caption{\floatcaptionparameter\c!grid}\d_strc_floats_caption_height
1906      %\page_backgrounds_add_local_to_box\b_strc_floats_caption
1907       \strc_floats_build_box
1908     \fi
1909   \or
1910     % semi automatic
1911   \or
1912     % manual
1913   \fi
1914   \ifconditional\c_floats_store_minimal_package
1915     % nothing
1916   \orelse\ifcase\c_strc_floats_rotation
1917     \ifinset\v!margin\floatlocation\else % brr, really needed! see wm
1918       \postcenterfloatbox\d_strc_floats_content
1919       \strc_floats_mark_pag_as_free
1920     \fi
1921     % mark as free not done here
1922   \else
1923     \global\setbox\floatbox\vpack
1924       {\rotate[\c!rotation=\the\c_strc_floats_rotation]{\box\floatbox}}%
1925     \strc_floats_mark_pag_as_free
1926   \fi
1927   \egroup}
1928
1929\def\strc_floats_prepare_no_caption
1930  {\global\setbox\floatbox\vpack % pas op als wd groter dan hsize
1931     {\ifinsidecolumns\ifdim\wd\b_strc_floats_content>\hsize
1932        \let\strc_floats_align_content\relax
1933      \fi\fi
1934      \strc_floats_align_content{\copy\b_strc_floats_content}}}
1935
1936\def\strc_floats_prepare_page_caption
1937  {\edef\p_strc_floats_caption_width   {\floatcaptionparameter\c!width}%
1938   \edef\p_strc_floats_caption_minwidth{\floatcaptionparameter\c!minwidth}%
1939   \edef\p_strc_floats_caption_align   {\floatcaptionparameter\c!align}%
1940   \dostarttagged\t!floatcaption\empty
1941   \ifcommon{\v!top,\v!bottom}\floatcaptionlocation
1942     \strc_floats_prepare_page_caption_top_bottom
1943   \orelse\ifx\p_strc_floats_caption_width\v!fit
1944     \strc_floats_prepare_side_auto_caption
1945   \orelse\ifx\p_strc_floats_caption_width\v!max
1946     \strc_floats_prepare_side_auto_caption
1947   \else
1948     \strc_floats_prepare_side_width_caption
1949   \fi
1950   \dostoptagged}
1951
1952\def\strc_floats_prepare_page_caption_top_bottom
1953  {\ifx\p_strc_floats_caption_width\v!fit
1954     \strc_floats_prepare_page_caption_top_bottom_fit_max
1955   \orelse\ifx\p_strc_floats_caption_width\v!max
1956     \strc_floats_prepare_page_caption_top_bottom_fit_max
1957   \else
1958     \strc_floats_prepare_side_width_caption % new, special effects (see icare)
1959   \fi}
1960
1961\def\strc_floats_prepare_page_caption_top_bottom_fit_max
1962  {\unless\ifx\p_strc_floats_caption_minwidth\v!fit
1963     \strc_floats_prepare_stack_caption_fixed
1964   \orelse\ifx\p_strc_floats_caption_width\v!max
1965     \strc_floats_prepare_stack_caption_max
1966   \orelse\ifdim\wd\b_strc_floats_caption>\wd\b_strc_floats_content % wider caption
1967     \ifx\p_strc_floats_caption_width\v!fit
1968       \strc_floats_prepare_stack_caption_auto
1969     \else
1970       \strc_floats_prepare_stack_caption_width
1971     \fi
1972   \else
1973     \strc_floats_prepare_stack_caption_min
1974   \fi}
1975
1976\def\strc_floats_caption_set_align
1977  {\edef\m_align{\v!reset\ifempty\p_strc_floats_caption_align\else,\fi\p_strc_floats_caption_align}%
1978   \ifinset\v!tolerant    \floatcaptionlocation\edef\m_align{\m_align,\v!tolerant    }\fi
1979   \ifinset\v!verytolerant\floatcaptionlocation\edef\m_align{\m_align,\v!verytolerant}\fi
1980   \ifinset\v!stretch     \floatcaptionlocation\edef\m_align{\m_align,\v!stretch     }\fi
1981   \setupalign[\m_align]}
1982
1983\def\strc_floats_prepare_side_auto_caption
1984  {\scratchdimen\dimexpr\hsize-\wd\b_strc_floats_content-\floatparameter\c!margin\relax
1985   \ifdim\wd\b_strc_floats_caption>\scratchdimen
1986     \ifdim\wd\b_strc_floats_caption<1.3\scratchdimen
1987       \scratchdimen0.8\scratchdimen
1988     \fi
1989   \fi
1990   \setbox\b_strc_floats_caption\vbox
1991     {\strc_floats_caption_set_align
1992      \hsize\scratchdimen
1993      \strc_floats_make_complete_caption}}
1994
1995\def\strc_floats_prepare_side_width_caption
1996  {\setbox\b_strc_floats_caption\vbox
1997     {\strc_floats_caption_set_align
1998      \hsize\floatcaptionparameter\c!width
1999      \strc_floats_make_complete_caption}}
2000
2001\def\strc_floats_prepare_stack_caption_fixed
2002  {\setbox\b_strc_floats_caption\vbox
2003     {\strc_floats_caption_set_align
2004      \hsize\floatcaptionparameter\c!minwidth % special effects
2005      \strc_floats_make_complete_caption}}
2006
2007\def\strc_floats_prepare_stack_caption_max
2008  {\setbox\b_strc_floats_caption\vbox
2009     {\strc_floats_caption_set_align
2010      \hsize\wd\b_strc_floats_content
2011      \strc_floats_make_complete_caption}}
2012
2013\def\strc_floats_prepare_stack_caption_width
2014  {\setbox\b_strc_floats_caption\vbox
2015     {\strc_floats_caption_set_align
2016      \hsize\floatcaptionparameter\c!width
2017      \strc_floats_make_complete_caption}}
2018
2019\def\strc_floats_prepare_stack_caption_min
2020  {\setbox\b_strc_floats_caption\vbox
2021     {\strc_floats_caption_set_align
2022      \hsize\wd\b_strc_floats_content
2023      \ifempty\p_strc_floats_caption_align
2024        \raggedcenter % on purpose overloads align !
2025      \fi
2026      \strc_floats_make_complete_caption}}
2027
2028\def\strc_floats_prepare_stack_caption_auto
2029%   {\ifempty\p_strc_floats_caption_align
2030%    \orelse\ifinset\v!middle\p_strc_floats_caption_align
2031%    \else
2032%      \d_strc_floats_caption_overshoot\zeropoint
2033%    \fi
2034  {\ifinset\v!middle\p_strc_floats_caption_align\else
2035     \d_strc_floats_caption_overshoot\zeropoint
2036   \fi
2037   \d_strc_floats_caption_hsize\wd\b_strc_floats_content
2038   \scratchwidth\floatcaptionparameter\c!maxwidth\relax
2039   \ifconditional\c_floats_adapt_to_caption_width
2040     \d_strc_floats_caption_min_width\zeropoint
2041     \d_strc_floats_caption_overshoot\zeropoint
2042   \fi
2043   \ifdim\d_strc_floats_caption_hsize>\scratchwidth
2044     % float is wider than \hsize
2045     \setbox\b_strc_floats_caption\vbox
2046       {\settrialtypesetting
2047        \strc_floats_caption_set_align
2048        \hsize\scratchwidth
2049        \notesenabledfalse
2050        \strc_floats_make_complete_caption}%
2051     \ifdim\ht\scratchbox>\lineheight % more lines
2052       \setbox\b_strc_floats_caption\vbox
2053         {\strc_floats_caption_set_align
2054          \hsize\dimexpr\d_strc_floats_caption_hsize-\d_strc_floats_caption_overshoot\relax
2055          \ifdim\hsize<\d_strc_floats_caption_min_width\relax
2056            \hsize\scratchwidth
2057          \fi
2058          \strc_floats_make_complete_caption}%
2059     \else
2060       \setbox\b_strc_floats_caption\vbox
2061         {\strc_floats_caption_set_align
2062          \hsize\scratchwidth
2063          \strc_floats_make_complete_caption}%
2064     \fi
2065   \else
2066     % float is smaller of equal to \hsize
2067     \ifdim\d_strc_floats_caption_hsize<\d_strc_floats_caption_min_width\relax
2068       \d_strc_floats_caption_hsize\d_strc_floats_caption_min_width % float smaller than min width
2069     % \ifconditional\c_floats_adapt_to_caption_width
2070     %   \setbox\b_strc_floats_content\hpack to \d_strc_floats_caption_hsize{\hss\box\b_strc_floats_content\hss}%
2071     % \fi
2072     \fi
2073     \setbox\scratchbox\vbox     % test with overshoot
2074       {\settrialtypesetting
2075        \scratchdimen\dimexpr\d_strc_floats_caption_hsize+\d_strc_floats_caption_overshoot+3\emwidth\relax % 3em is an average word length
2076        \ifdim\scratchdimen<\hsize
2077          \hsize\scratchdimen
2078        \fi
2079        \notesenabledfalse
2080        \strc_floats_make_complete_caption}%
2081     \ifdim\ht\scratchbox>\lineheight
2082       % at least an average word longer than a line
2083       \setbox\b_strc_floats_caption\vbox
2084         {\strc_floats_caption_set_align
2085          \scratchdimen\dimexpr\d_strc_floats_caption_hsize+\d_strc_floats_caption_overshoot\relax
2086          \ifdim\scratchdimen<\hsize
2087            \hsize\scratchdimen
2088          \fi
2089          \strc_floats_make_complete_caption}%
2090     \orelse\ifempty\p_strc_floats_caption_align
2091       \setbox\b_strc_floats_caption\vbox
2092         {\strc_floats_caption_set_align
2093          \hsize\d_strc_floats_caption_hsize
2094          \raggedcenter % overloads
2095          \strc_floats_make_complete_caption}%
2096     \else
2097       \setbox\b_strc_floats_caption\vbox
2098         {\strc_floats_caption_set_align
2099          \hsize\d_strc_floats_caption_hsize
2100          \strc_floats_make_complete_caption}%
2101     \fi
2102   \fi}
2103
2104\def\strc_floats_between_stack
2105  {\endgraf
2106   \nointerlineskip
2107   \floatcaptionparameter\c!inbetween
2108   \endgraf}
2109
2110\def\strc_floats_build_box_default % done
2111  {\strc_floats_align_content{\box\b_strc_floats_content}}
2112
2113\def\strc_floats_build_box_next_right#1%
2114  {\ifconditional\c_strc_floats_par_float \hpack \else \expandafter \strc_floats_align_content \fi % skip, no pack
2115     {\d_strc_float_temp_height\ht\b_strc_floats_content
2116      \box\b_strc_floats_content
2117      \ifinset\v!hang\floatcaptionlocation\else
2118        \dotfskip{\floatcaptionparameter\c!distance}%
2119      \fi
2120      \vbox to\d_strc_float_temp_height{#1}}}
2121
2122\def\strc_floats_build_box_next_left#1%
2123  {\ifconditional\c_strc_floats_par_float \hpack \else \expandafter \strc_floats_align_content \fi % skip, no pack
2124     {\d_strc_float_temp_height\ht\b_strc_floats_content
2125      \vbox to\d_strc_float_temp_height{#1}%
2126      \ifinset\v!hang\floatcaptionlocation\else
2127        \dotfskip{\floatcaptionparameter\c!distance}%
2128      \fi
2129      \box\b_strc_floats_content}}
2130
2131\def\strc_floats_build_box_next_outer
2132  {\doifelserightpagefloat\strc_floats_build_box_next_right\strc_floats_build_box_next_left}
2133
2134\def\strc_floats_build_box_next_inner
2135  {\doifelserightpagefloat\strc_floats_build_box_next_left\strc_floats_build_box_next_right}
2136
2137\def\strc_floats_build_box_next_right_hang#1%
2138  {\ifconditional\c_strc_floats_par_float \hpack \else \expandafter \strc_floats_align_content \fi
2139     {\d_strc_float_temp_height\ht\b_strc_floats_content
2140      \box\b_strc_floats_content
2141      \vbox to\d_strc_float_temp_height{#1}}}
2142
2143\def\strc_floats_build_box_next_left_hang#1%
2144  {\ifconditional\c_strc_floats_par_float \hpack \else \expandafter \strc_floats_align_content \fi
2145     {\d_strc_float_temp_height\ht\b_strc_floats_content
2146      \vbox to\d_strc_float_temp_height{#1}%
2147      \box\b_strc_floats_content}}
2148
2149\def\strc_floats_build_box_next_right_margin_indeed#1#2%
2150  {\ifconditional\c_strc_floats_par_float
2151     \hpack\bgroup
2152       \d_strc_float_temp_height\ht\b_strc_floats_content
2153       \box\b_strc_floats_content
2154       \hsmash{\hskip#1\vbox to\d_strc_float_temp_height{#2}}%
2155     \egroup
2156   \else
2157     \begingroup
2158     \d_strc_float_temp_height\ht\b_strc_floats_content
2159     \setbox\scratchboxone\vbox{#2}%
2160     \ifdim\htdp\scratchboxone>\htdp\b_strc_floats_content
2161       \global\d_strc_floats_overflow\dimexpr\htdp\scratchboxone-\htdp\b_strc_floats_content\relax
2162     \fi
2163     \ht\scratchboxone\d_strc_float_temp_height
2164     \everyrightofalignedline{\hsmash{\hskip#1\box\scratchboxone}}%
2165     \strc_floats_align_content{\box\b_strc_floats_content}%
2166     \endgroup
2167    \fi}
2168
2169\def\strc_floats_build_box_next_left_margin_indeed#1#2%
2170  {\ifconditional\c_strc_floats_par_float
2171     \hpack\bgroup
2172       \d_strc_float_temp_height\ht\b_strc_floats_content
2173       \hsmash{\hskip-\dimexpr#1+\wd\b_strc_floats_caption\relax\vbox to\d_strc_float_temp_height{#2}}%
2174       \box\b_strc_floats_content
2175     \egroup
2176   \else
2177     \begingroup
2178     \d_strc_float_temp_height\ht\b_strc_floats_content
2179     \setbox\scratchboxone\vbox{#2}%
2180     \ifdim\htdp\scratchboxone>\htdp\b_strc_floats_content
2181       \global\d_strc_floats_overflow\dimexpr\htdp\scratchboxone-\htdp\b_strc_floats_content\relax
2182     \fi
2183     \ht\scratchboxone\d_strc_float_temp_height
2184     \everyleftofalignedline{\hsmash{\hskip-\dimexpr#1+\wd\scratchboxone\relax\box\scratchboxone}}%
2185     \strc_floats_align_content{\box\b_strc_floats_content}%
2186     \endgroup
2187   \fi}
2188
2189\def\strc_floats_build_box_next_right_margin
2190  {\strc_floats_build_box_next_right_margin_indeed\rightmargindistance}
2191
2192\def\strc_floats_build_box_next_left_margin
2193  {\strc_floats_build_box_next_left_margin_indeed \leftmargindistance}
2194
2195\def\strc_floats_build_box_next_outer_margin
2196  {\doifelserightpagefloat
2197     {\strc_floats_build_box_next_right_margin_indeed\rightmargindistance}
2198     {\strc_floats_build_box_next_left_margin_indeed \rightmargindistance}}
2199
2200\def\strc_floats_build_box_next_inner_margin
2201  {\doifelserightpagefloat
2202     {\strc_floats_build_box_next_left_margin_indeed \leftmargindistance}
2203     {\strc_floats_build_box_next_right_margin_indeed\leftmargindistance}}
2204
2205\def\strc_floats_build_box_next % beware, we first check on left/rightmargin because there can be left/right also
2206  {\let\next\strc_floats_build_box_next_left
2207   \processallactionsinset[\floatcaptionlocation]
2208     [ \v!outermargin=>\let\next\strc_floats_build_box_next_outer_margin,
2209       \v!innermargin=>\let\next\strc_floats_build_box_next_inner_margin,
2210        \v!leftmargin=>\let\next\strc_floats_build_box_next_left_margin,
2211       \v!rightmargin=>\let\next\strc_floats_build_box_next_right_margin,
2212       \v!lefthanging=>\let\next\strc_floats_build_box_next_left_hang,
2213      \v!righthanging=>\let\next\strc_floats_build_box_next_right_hang,
2214             \v!outer=>\let\next\strc_floats_build_box_next_outer,
2215             \v!inner=>\let\next\strc_floats_build_box_next_inner,
2216              \v!left=>\let\next\strc_floats_build_box_next_left,
2217             \v!right=>\let\next\strc_floats_build_box_next_right]%
2218   \next}
2219
2220\def\strc_floats_build_box_side
2221  {\ifconditional\c_strc_floats_par_float
2222     \let\next\strc_floats_build_box_high
2223   \else
2224     \let\next\strc_floats_build_box_middle
2225     \processallactionsinset[\floatcaptionlocation]
2226       [   \v!low=>\let\next\strc_floats_build_box_low,
2227        \v!middle=>\let\next\strc_floats_build_box_middle,
2228          \v!high=>\let\next\strc_floats_build_box_high]%
2229   \fi
2230   \next}
2231
2232\def\strc_floats_flush_right_caption_hang
2233  {\hsmash{\rlap{\dotfskip{\floatcaptionparameter\c!distance}\box\b_strc_floats_caption}}}
2234
2235\def\strc_floats_flush_left_caption_hang
2236  {\hsmash{\llap{\box\b_strc_floats_caption\dotfskip{\floatcaptionparameter\c!distance}}}}
2237
2238\def\strc_floats_flush_caption_hang
2239  {\ifinset\v!righthanging\floatcaptionlocation
2240     \strc_floats_flush_right_caption_hang
2241   \orelse\ifinset\v!lefthanging\floatcaptionlocation
2242     \strc_floats_flush_left_caption_hang
2243   \orelse\ifinset\v!hang\floatcaptionlocation
2244     \ifinset\v!outer\floatcaptionlocation
2245       \doifelserightpagefloat
2246         {\strc_floats_flush_right_caption_hang}
2247         {\strc_floats_flush_left_caption_hang}%
2248     \orelse\ifinset\v!right\floatcaptiondirectives
2249       \strc_floats_flush_right_caption_hang
2250     \else
2251       \strc_floats_flush_left_caption_hang
2252     \fi
2253   \else
2254     \box\b_strc_floats_caption
2255   \fi} % is this ok
2256
2257\def\strc_floats_build_box_high
2258  {\strc_floats_build_box_next{\strc_floats_between_stack\strc_floats_flush_caption_hang\vfill}}
2259
2260\def\strc_floats_build_box_low
2261  {\strc_floats_build_box_next{\vfill\strc_floats_flush_caption_hang\strc_floats_between_stack}}
2262
2263\def\strc_floats_build_box_middle
2264  {\strc_floats_build_box_next{\vfill\box\b_strc_floats_caption\vfill}}
2265
2266% \definefloat
2267%   [lefty][lefties][figure]
2268% \setupfloat
2269%   [lefty]
2270%   [default=left,
2271%    rightmargindistance=-2cm,
2272%    leftmargindistance=-2cm]
2273% \setupcaption
2274%   [lefty]
2275%   [location={bottom,overlay}]
2276%
2277% \starttext
2278%     \placelefty{}{} \input tufte \input tufte
2279%     \placelefty{}{} \input tufte \input tufte
2280% \stoptext
2281
2282\def\strc_floats_build_box_top_stack_normal_overlay
2283  {\vbox to \ht\b_strc_floats_content{\vss\strc_floats_build_box_top_stack_normal_content}}
2284
2285\def\strc_floats_build_box_top_stack_normal_content
2286  {\d_strc_float_temp_width\wd\b_strc_floats_content
2287   \ifconditional\c_strc_floats_par_float
2288     \hpack{\strc_floats_locate_side_float{\box\b_strc_floats_caption}}%
2289     \strc_floats_between_stack
2290     \hpack{\hbox{\box\b_strc_floats_content}}%
2291   \else
2292     \page_otr_command_set_float_hsize
2293     \hpack{\strc_floats_locate_text_float{\box\b_strc_floats_caption}}
2294     \strc_floats_between_stack
2295     \hpack{\strc_floats_align_content{\box\b_strc_floats_content}}%
2296   \fi}
2297
2298\def\strc_floats_build_box_bottom_stack_normal_overlay
2299  {\vbox to \ht\b_strc_floats_content{\strc_floats_build_box_bottom_stack_normal_content\vss}}
2300
2301\def\strc_floats_build_box_bottom_stack_normal_content
2302  {\d_strc_float_temp_width\wd\b_strc_floats_content
2303   \ifconditional\c_strc_floats_par_float
2304     \hpack{\hpack{\box\b_strc_floats_content}}%
2305     \strc_floats_between_stack
2306     \hpack{\strc_floats_locate_side_float{\box\b_strc_floats_caption}}%
2307   \else
2308     \page_otr_command_set_float_hsize
2309     \hpack{\strc_floats_align_content{\box\b_strc_floats_content}}%
2310     \strc_floats_between_stack
2311     \hpack{\strc_floats_locate_text_float{\box\b_strc_floats_caption}}%
2312   \fi}
2313
2314\def\strc_floats_build_box_top_stack_normal_tight
2315  {\hpack{\box\b_strc_floats_caption}%
2316   \strc_floats_between_stack
2317   \hpack{\box\b_strc_floats_content}}
2318
2319\def\strc_floats_build_box_bottom_stack_normal_tight
2320  {\hpack{\box\b_strc_floats_content}%
2321   \strc_floats_between_stack
2322   \hpack{\box\b_strc_floats_caption}}
2323
2324\def\strc_floats_build_box_top_stack_normal
2325  {\ifinset\v!overlay{\floatcaptionparameter\c!location}%
2326     \strc_floats_build_box_top_stack_normal_overlay
2327   \orelse\ifinset\v!tight{\floatlocation}%
2328     \strc_floats_build_box_top_stack_normal_tight
2329   \else
2330     \strc_floats_build_box_top_stack_normal_content
2331   \fi}
2332
2333\def\strc_floats_build_box_bottom_stack_normal
2334  {\ifinset\v!overlay{\floatcaptionparameter\c!location}%
2335     \strc_floats_build_box_bottom_stack_normal_overlay
2336   \orelse\ifinset\v!tight{\floatlocation}%
2337     \strc_floats_build_box_bottom_stack_normal_tight
2338   \else
2339     \strc_floats_build_box_bottom_stack_normal_content
2340   \fi}
2341
2342\def\strc_floats_build_box_top_stack_grid
2343  {\dp\b_strc_floats_caption\strutdepth
2344   \setbox\scratchbox\vbox
2345     {\d_strc_float_temp_width\wd\b_strc_floats_content
2346      \hsize\d_strc_float_temp_width
2347      \ifconditional\c_strc_floats_par_float
2348        \strc_floats_locate_side_float{\box\b_strc_floats_caption}%
2349        \vss\strc_floats_between_stack
2350        \hpack{\box\b_strc_floats_content}%
2351      \else
2352        \page_otr_command_set_float_hsize
2353        \strc_floats_locate_text_float{\box\b_strc_floats_caption}%
2354        \vss\strc_floats_between_stack
2355        \strc_floats_align_content{\box\b_strc_floats_content}%
2356      \fi}%
2357   \getnoflines{\dimexpr\htdp\scratchbox-10\scaledpoint\relax}% get rid of inaccuracy
2358   \vpack to \noflines\lineheight{\unvbox\scratchbox}}
2359
2360\def\strc_floats_build_box_bottom_stack_grid
2361  {\dp\b_strc_floats_caption\strutdepth
2362   \setbox\scratchbox\vbox
2363     {\d_strc_float_temp_width\wd\b_strc_floats_content
2364      \hsize\d_strc_float_temp_width
2365      \ifconditional\c_strc_floats_par_float
2366        \hpack{\box\b_strc_floats_content}%
2367        \vss\strc_floats_between_stack
2368        \strc_floats_locate_side_float{\box\b_strc_floats_caption}%
2369      \else
2370        \page_otr_command_set_float_hsize
2371        \strc_floats_align_content{\box\b_strc_floats_content}%
2372        \vss\strc_floats_between_stack
2373        \strc_floats_locate_text_float{\box\b_strc_floats_caption}%
2374      \fi}%
2375   \getnoflines{\dimexpr\htdp\scratchbox-10\scaledpoint\relax}% get rid of inaccuracy
2376   \vpack to \noflines\lineheight{\unvbox\scratchbox}}
2377
2378\def\strc_floats_build_box_top_stack_stretch
2379  {\dp\b_strc_floats_caption\strutdepth
2380   \setbox\scratchbox\vpack
2381     {\strc_floats_align_caption{\copy\b_strc_floats_caption}%
2382      \strc_floats_align_content{\copy\b_strc_floats_content}}%
2383   \getnoflines{\dimexpr\htdp\scratchbox-10\scaledpoint\relax}% get rid of inaccuracy
2384   \vbox to \noflines\lineheight % pack ?
2385     {\d_strc_float_temp_width\wd\b_strc_floats_content
2386      \hsize\d_strc_float_temp_width
2387      \ifconditional\c_strc_floats_par_float
2388        \strc_floats_locate_side_float{\box\b_strc_floats_caption}%
2389        \vss\strc_floats_between_stack\vss
2390        \hpack{\box\b_strc_floats_content}%
2391      \else
2392        \page_otr_command_set_float_hsize
2393        \strc_floats_locate_text_float{\box\b_strc_floats_caption}%
2394        \vss\strc_floats_between_stack\vss
2395        \strc_floats_align_content{\box\b_strc_floats_content}%
2396      \fi}}
2397
2398\def\strc_floats_build_box_bottom_stack_stretch
2399  {\dp\b_strc_floats_caption\strutdepth
2400   \setbox\scratchbox\vpack
2401     {\strc_floats_align_content{\copy\b_strc_floats_content}%
2402      \strc_floats_align_caption{\copy\b_strc_floats_caption}}%
2403   \getnoflines{\dimexpr\htdp\scratchbox-10\scaledpoint\relax}% get rid of inaccuracy
2404   \vbox to \noflines\lineheight
2405     {\d_strc_float_temp_width\wd\b_strc_floats_content
2406      \hsize\d_strc_float_temp_width
2407      \ifconditional\c_strc_floats_par_float
2408        \hpack{\box\b_strc_floats_content}%
2409        \vss\strc_floats_between_stack\vss
2410        \strc_floats_locate_side_float{\box\b_strc_floats_caption}%
2411      \else
2412        \page_otr_command_set_float_hsize
2413        \strc_floats_align_content{\box\b_strc_floats_content}%
2414        \vss\strc_floats_between_stack\vss
2415        \strc_floats_locate_text_float{\box\b_strc_floats_caption}%
2416      \fi}}
2417
2418\def\strc_floats_build_box_top
2419  {\let\next\strc_floats_build_box_top_stack_normal
2420   \processfirstactioninset[\floatcaptionparameter\c!location]
2421     [   \v!grid=>\let\next\strc_floats_build_box_top_stack_grid,
2422        \v!lines=>\let\next\strc_floats_build_box_top_stack_stretch]% was \v!grid but interfered
2423   \next}
2424
2425\def\strc_floats_build_box_bottom
2426  {\let\next\strc_floats_build_box_bottom_stack_normal
2427   \processfirstactioninset[\floatcaptionparameter\c!location]
2428     [   \v!grid=>\let\next\strc_floats_build_box_bottom_stack_grid,
2429        \v!lines=>\let\next\strc_floats_build_box_bottom_stack_stretch]% was \v!grid but interfered
2430   \next}
2431
2432\def\strc_floats_relocate_caption_right#1{\strc_floats_align_caption{\hbox to \d_strc_float_temp_width{\hss#1}}}
2433\def\strc_floats_relocate_caption_left #1{\strc_floats_align_caption{\hbox to \d_strc_float_temp_width{#1\hss}}}
2434
2435\permanent\protected\def\installfloatboxbuilder#1#2{\defcsname\??floatbuilder#1\endcsname{#2}}
2436
2437\def\strc_floats_build_box
2438  {\strc_floats_build_box_before
2439   \global\setbox\floatbox\vbox % pack ? probably not
2440     {\strc_floats_set_local_hsize
2441      \forgetall
2442      \ifconditional\c_floats_store_minimal_package
2443        \strc_floats_build_box_separate_make
2444      \else
2445      % \let\floatcaptionarrangement\s!default
2446        \let\floatcaptionarrangement\v!bottom % for Alan
2447        \processcommacommand[\floatcaptionparameter\c!location]\strc_floats_build_box_step
2448        \ifcsname\??floatbuilder\floatcaptionarrangement\endcsname
2449          \lastnamedcs
2450        \else
2451          \strc_floats_build_box_default
2452        \fi
2453      \fi}%
2454   \strc_floats_build_box_after}
2455
2456% \let\strc_floats_build_box_before\relax
2457% \let\strc_floats_build_box_after \relax
2458
2459\def\strc_floats_build_box_before
2460  {\let\currentfloatframed\currentfloat
2461   \floatwidth\wd
2462     \ifdim\wd\b_strc_floats_content>\wd\b_strc_floats_caption
2463       \b_strc_floats_content\else\b_strc_floats_caption
2464     \fi}
2465
2466\def\strc_floats_build_box_after
2467  {\doifelseframed\floatframedparameter\strc_floats_build_box_after_indeed\relax}
2468
2469% \def\strc_floats_build_box_after_indeed
2470%   {\global\setbox\floatbox\hpack
2471%      {\edef\m_width{\floatframedparameter\c!width}%
2472%       \ifx\m_width\v!fit
2473%         \let\m_width\floatwidth
2474%       \orelse\ifx\m_width\v!broad
2475%         \let\m_width\v!fit
2476%       \fi
2477%       \letfloatframedparameter\c!strut\v!no
2478%       \letfloatframedparameter\c!width\m_width
2479%       \inheritedfloatframedframed
2480%         {\box\floatbox}}}
2481
2482\def\strc_floats_build_box_after_indeed
2483  {\global\setbox\floatbox\hpack
2484     {\edef\m_width{\floatframedparameter\c!width}%
2485      \ifx\m_width\v!fit
2486        \letfloatframedparameter\c!width\floatwidth
2487      \orelse\ifx\m_width\v!broad
2488        \letfloatframedparameter\c!width\v!fit
2489      \else
2490        \letfloatframedparameter\c!width\m_width % expanded, not really needed
2491      \fi
2492      \letfloatframedparameter\c!strut\v!no
2493      \inheritedfloatframedframed
2494        {\box\floatbox}}}
2495
2496% special purpose: used in floatcombinations
2497%
2498% todo : keep float content and caption separated in local
2499
2500\newbox\b_strc_floats_separate_content
2501\newbox\b_strc_floats_separate_caption
2502
2503\def\strc_floats_build_box_separate_set
2504  {\c_floats_adapt_to_caption_width\conditionaltrue
2505   \c_floats_store_minimal_package\conditionaltrue}
2506
2507% \def\strc_floats_build_box_separate_make
2508%   {\offinterlineskip
2509%    \vpack to \onepoint{\box\b_strc_floats_content}\break
2510%    \vpack to \onepoint{\box\b_strc_floats_caption}}
2511
2512%D Remark for \LMTX: we don't want to migrate inserts here so we unpack
2513%D (could be a flag). When migrated, the inserts end up in the vertical
2514%D list and we no longer have just a box (but inserts and lines again).
2515
2516\def\strc_floats_build_box_separate_make
2517  {\savebox\??localfloatstack{\the\numexpr\c_strc_localfloats_n+1\relax:a}{\box\b_strc_floats_content}%
2518   \savebox\??localfloatstack{\the\numexpr\c_strc_localfloats_n+1\relax:b}{\box\b_strc_floats_caption}}
2519
2520\protected\def\strc_floats_build_box_separate_split#1%
2521  {\global\setbox\b_strc_floats_separate_content\vpack{\foundbox\??localfloatstack{\number#1:a}}%
2522   \global\setbox\b_strc_floats_separate_caption\tpack{\foundbox\??localfloatstack{\number#1:b}}}
2523
2524% \def\strc_floats_build_box_step#1%
2525%   {\doifdefined{\??floatbuilder#1}{\def\floatcaptionarrangement{#1}\quitcommalist}}
2526
2527\def\strc_floats_build_box_step#1%
2528  {\ifcsname\??floatbuilder#1\endcsname
2529     \def\floatcaptionarrangement{#1}% \let\floatcaptionarrangement\commalistelement
2530     \quitcommalist
2531   \fi}
2532
2533\def\strc_floats_locate_text_float
2534  {\let\next\strc_floats_align_caption
2535   \processallactionsinset[\floatcaptionparameter\c!location]
2536     [ \v!left=>\let\next\strc_floats_relocate_caption_left,
2537      \v!right=>\let\next\strc_floats_relocate_caption_right,
2538      \v!inner=>\doifelserightpagefloat{\let\next\strc_floats_relocate_caption_left }{\let\next\strc_floats_relocate_caption_right},
2539      \v!outer=>\doifelserightpagefloat{\let\next\strc_floats_relocate_caption_right}{\let\next\strc_floats_relocate_caption_left }]%
2540   \next}
2541
2542\installfloatboxbuilder \v!none         \strc_floats_build_box_default
2543\installfloatboxbuilder \s!default      \strc_floats_build_box_default
2544\installfloatboxbuilder \v!high         \strc_floats_build_box_high
2545\installfloatboxbuilder \v!low          \strc_floats_build_box_low
2546\installfloatboxbuilder \v!middle       \strc_floats_build_box_middle
2547
2548\installfloatboxbuilder \v!rightmargin  \strc_floats_build_box_side % added 2016-08-23
2549\installfloatboxbuilder \v!leftmargin   \strc_floats_build_box_side % added 2016-08-23
2550\installfloatboxbuilder \v!innermargin  \strc_floats_build_box_side % added 2016-08-23
2551\installfloatboxbuilder \v!outermargin  \strc_floats_build_box_side % added 2016-08-23
2552
2553\installfloatboxbuilder \v!left         \strc_floats_build_box_side
2554\installfloatboxbuilder \v!right        \strc_floats_build_box_side
2555\installfloatboxbuilder \v!inner        \strc_floats_build_box_side % added 2016-08-23
2556\installfloatboxbuilder \v!outer        \strc_floats_build_box_side % added 2016-08-23
2557
2558\installfloatboxbuilder \v!lefthanging  \strc_floats_build_box_side % added 2016-08-23
2559\installfloatboxbuilder \v!righthanging \strc_floats_build_box_side % added 2016-08-23
2560\installfloatboxbuilder \v!hang         \strc_floats_build_box_side % added 2016-08-23
2561
2562\installfloatboxbuilder \v!top          \strc_floats_build_box_top
2563\installfloatboxbuilder \v!bottom       \strc_floats_build_box_bottom
2564
2565% \setuplayout[grid=yes] \showgrid \setupcaptions[style=smallbodyfont,location=grid,inbetween=]
2566%
2567% \starttext
2568%     test \placefigure{}                 {\externalfigure[cow.pdf][frame=on,grid=yes]}   test \page
2569%     test \placefigure{\input zapf\relax}{\externalfigure[cow.pdf][frame=on,grid=yes]}   test \page
2570%     test \placefigure{}                 {\externalfigure[cow.pdf][frame=on,grid=depth]} test \page
2571%     test \placefigure{\input zapf\relax}{\externalfigure[cow.pdf][frame=on,grid=depth]} test \page
2572% \stoptext
2573
2574% This might move to page-flt:
2575
2576\newif\ifpostponecolumnfloats \postponecolumnfloatsfalse % don't change
2577
2578\setnewconstant\postcenterfloatmethod\plusone
2579
2580\permanent\def\postcenterfloatbox#1%
2581  {\scratchdimen
2582     \ifcase\postcenterfloatmethod
2583       #1% \wd\floatbox
2584     \orelse\ifinsidecolumns
2585       \ifpostponecolumnfloats\makeupwidth\else#1\fi
2586     \orelse\ifdim#1>\hsize
2587       \hsize
2588     \else
2589       \wd\floatbox
2590     \fi
2591   \global\setbox\floatbox\hbox to \scratchdimen
2592   % {\hfill\box\floatbox\hfill}} % geen \hss, gaat mis in kolommen !
2593   % {\hss  \box\floatbox\hss  }} % wel \hss, anders mis in colset
2594     {\ifconditional\c_page_floats_center_box_global
2595        \donetrue
2596      \orelse\ifconditional\c_page_floats_center_box_local
2597        \donetrue
2598      \else
2599        \donefalse
2600      \fi
2601      \ifdim\scratchdimen>\effectivehsize
2602        \donefalse
2603      \fi
2604      \hss\ifdone\hskip\effectiveleftskip\fi
2605      \box\floatbox
2606      \ifdone\hskip\effectiverightskip\fi\hss}}
2607
2608\def\strc_floats_set_paragraph_variant
2609  {\bgroup
2610   \forgetall
2611   \postponenotes
2612   \dontcomplain
2613   \setbox\b_strc_floats_content\vbox{\borderedfloatbox}% \vpack >?
2614  %\page_backgrounds_add_local_to_box\b_strc_floats_content
2615   \ifnofloatcaption
2616     \global\setbox\floatbox\vpack{\box\b_strc_floats_content}%
2617   \else
2618     \strc_floats_check_caption_content
2619     \strc_floats_prepare_side_caption
2620     \strc_floats_apply_caption_command
2621    %\moveboxontogrid\b_strc_floats_caption{\floatcaptionparameter\c!grid}\d_strc_floats_caption_height
2622    %\page_backgrounds_add_local_to_box\b_strc_floats_caption
2623     \strc_floats_build_side_box
2624   \fi
2625   \egroup}
2626
2627\def\strc_floats_prepare_side_caption
2628  {\dostarttagged\t!floatcaption\empty
2629   \edef\p_strc_floats_caption_width{\floatcaptionparameter\c!width}%
2630   \edef\p_strc_floats_caption_align{\floatcaptionparameter\c!align}%
2631   \ifx\p_strc_floats_caption_width\v!max
2632     \strc_floats_prepare_side_caption_max
2633   \orelse\ifx\p_strc_floats_caption_width\v!fit
2634     \strc_floats_prepare_side_caption_fit
2635   \else
2636     \strc_floats_prepare_side_caption_width
2637   \fi
2638   \dostoptagged}
2639
2640% these could be \??floatpreparesidecaption
2641
2642% \setupfloat[figure][location=left]
2643% \setupcaption[figure][width=max]
2644%
2645% \placefigure{my figure caption my figure caption}{\framed[width=4cm,height=1cm]{}} \input tufte
2646% \placefigure{my figure caption}                  {\framed[width=4cm,height=1cm]{}} \input tufte
2647
2648\def\strc_floats_prepare_side_caption_max
2649  {\setbox\b_strc_floats_caption\vbox
2650     {\strc_floats_caption_set_align
2651      \hsize\wd\b_strc_floats_content
2652      \strc_floats_make_complete_caption}}
2653
2654\def\strc_floats_prepare_side_caption_fit % or center when smaller
2655  {\ifdim\wd\b_strc_floats_caption>\wd\b_strc_floats_content\relax
2656     \setbox\b_strc_floats_caption\vbox
2657       {\forgetall % needed?
2658        \strc_floats_caption_set_align
2659        \hsize\wd\b_strc_floats_content
2660        \strc_floats_make_complete_caption}%
2661   \else
2662     % maybe we should listen to the align option here (now side floats need the max option
2663     \setbox\b_strc_floats_caption\hpack to \wd\b_strc_floats_content
2664       {\hss\hbox{\strc_floats_make_complete_caption}\hss}%
2665   \fi}
2666
2667\def\strc_floats_prepare_side_caption_width
2668  {\setbox\b_strc_floats_caption\vbox
2669     {\strc_floats_caption_set_align
2670      \hsize\p_strc_floats_caption_width % \wd\b_strc_floats_content
2671      \strc_floats_make_complete_caption}}
2672
2673% % maybe (but then also prepare_page that way):
2674%
2675% \installcorenamespace{floatpreparesidecaption}
2676%
2677% \def\strc_floats_prepare_side_caption
2678%   {\dostarttagged\t!floatcaption\empty
2679%    \edef\p_strc_floats_caption_width{\floatcaptionparameter\c!width}%
2680%    \edef\p_strc_floats_caption_align{\floatcaptionparameter\c!align}%
2681%    \expandnamespacemacro\??floatpreparesidecaption\p_strc_floats_caption_width\s!unknown
2682%    \dostoptagged}
2683%
2684% \defcsname\??floatpreparesidecaption\v!max\endcsname
2685%   {\setbox\b_strc_floats_caption\vbox
2686%      {\strc_floats_caption_set_align
2687%       \hsize\wd\b_strc_floats_content
2688%       \strc_floats_make_complete_caption}}
2689%
2690% \defcsname\??floatpreparesidecaption\v!fit\endcsname
2691%   {\ifdim\wd\b_strc_floats_caption>\wd\b_strc_floats_content\relax
2692%      \setbox\b_strc_floats_caption\vbox
2693%        {\forgetall % needed?
2694%         \hsize\wd\b_strc_floats_content
2695%         \strc_floats_make_complete_caption}%
2696%    \else
2697%      \setbox\b_strc_floats_caption\hbox to \wd\b_strc_floats_content
2698%        {\hss\hbox{\strc_floats_make_complete_caption}\hss}%
2699%    \fi}
2700%
2701% \defcsname\??floatpreparesidecaption\s!unknown\endcsname
2702%   {\setbox\b_strc_floats_caption\vbox
2703%      {\strc_floats_caption_set_align
2704%       \hsize\p_strc_floats_caption_width % \wd\b_strc_floats_content
2705%       \strc_floats_make_complete_caption}}
2706
2707\def\strc_floats_locate_side_float#1%
2708  {\begingroup
2709   \alignstrutmode\zerocount
2710   \hsize\d_strc_float_temp_width \forgetall
2711   \alignedline{\floatparameter\c!location}\v!middle{#1}%
2712   \endgroup}
2713
2714\def\strc_floats_build_side_box
2715  {\let\strc_floats_align_content\relax
2716   \let\strc_floats_align_caption\relax
2717   \strc_floats_build_box}
2718
2719\def\strc_floats_set_box % todo : \global\setbox, currently messy
2720  {\ifvisible
2721     \par
2722     \edef\floatcaptiondirectives{\floatparameter\c!location,\floatcaptionparameter\c!location}%
2723     \strc_floats_set_caption_criteria
2724     \ifconditional\c_strc_floats_par_float
2725       \strc_floats_set_paragraph_variant
2726     \else
2727       \strc_floats_set_page_variant
2728     \fi
2729     \strc_floats_set_local_dimensions
2730     \global\advanceby\totalnoffloats\plusone
2731     \ifconditional\c_floats_store_minimal_package \else
2732       \setbox\floatbox\hpack{\strc_float_save_data\box\floatbox}% still needed? we will do renumbering differently
2733     \fi
2734     \global\floatheight\htdp\floatbox
2735     \global\floatwidth\wd\floatbox
2736     \ifconditional\c_floats_store_minimal_package \else
2737       \ifinset\v!margin\floatlocation\else % gaat namelijk nog fout
2738         \setbox\floatbox\vpack
2739           {\parindent\zeropoint
2740            \box\floatbox}%
2741       \fi
2742     \fi
2743     \wd\floatbox\floatwidth
2744     \ifdim\dimexpr\floatheight+\lineheight\relax<\textheight \else
2745       \global\floatheight\dimexpr\textheight-\lineheight\relax
2746       \ht\floatbox\floatheight
2747       \dp\floatbox\zeropoint
2748       \showmessage\m!floatblocks{10}{\the\totalnoffloats}%
2749     \fi
2750   \fi}
2751
2752% \def\dooutput{\sidefloatoutput} % redefinition of \dooutput
2753
2754\definefloat
2755  [\v!figure]
2756  [\v!figures]
2757
2758\definefloat
2759  [\v!table]
2760  [\v!tables]
2761
2762\setupfloat
2763  [\v!table]
2764  [\c!frame=\v!off]
2765
2766\definefloat
2767  [\v!intermezzo]
2768  [\v!intermezzi]
2769
2770\definefloat
2771  [\v!graphic]
2772  [\v!graphics]
2773
2774% float strategy, replaces some of the above macros
2775
2776\installcorenamespace{floatmethods}
2777
2778\mutable\lettonothing\floatmethod        % set by lua
2779\mutable\lettonothing\floatlabel         % set by lua
2780\mutable\lettonothing\floatcolumn        % set by lua
2781\mutable\lettonothing\floatrow           % set by lua
2782\mutable\lettonothing\floatspecification
2783\mutable\lettonothing\forcedfloatmethod  % set by lua and floatcombinations
2784
2785\permanent\protected\def\setfloatmethodvariables#1% \floatmethod \floatlabel \floatrow \floatcolumn
2786  {\clf_analysefloatmethod{#1}} % move definition to lua end
2787
2788\permanent\protected\def\somesomewherefloat[#1]%
2789  {\page_floats_save_somewhere_float\s!somewhere{#1}}
2790
2791\def\strc_floats_get_box
2792  {\ifvisible
2793     \ifcsname\??floatmethods\currentoutputroutine:\floatmethod\endcsname \else
2794       \let\floatmethod\floatlocationdefault
2795       \ifcsname\??floatmethods\currentoutputroutine:\floatmethod\endcsname \else
2796         \let\floatmethod\v!here
2797       \fi
2798     \fi
2799     \ifempty\forcedfloatmethod \else
2800       \let\floatmethod\forcedfloatmethod
2801     \fi
2802     \let\askedfloatmethod\floatmethod
2803     \ifexporting \ifx\askedfloatmethod\v!here \else
2804       \showmessage\m!floatblocks{15}{\askedfloatmethod,\v!here}%
2805       \let\floatlocation\v!here
2806     \fi \fi
2807     % [] will go
2808     \edef\floatlocationmethod{\floatmethod,\floatlocation}%
2809     \csname\??floatmethods\currentoutputroutine:\floatmethod\endcsname
2810   \fi}
2811
2812\installcorenamespace{floatsettings}
2813
2814\permanent\protected\def\installfloatmethod#1#2#3% routine keyword handler
2815  {\defcsname\??floatmethods#1:#2\endcsname{#3}}
2816
2817\permanent\protected\def\handlefloatmethod#1%
2818  {\csname\??floatmethods\currentoutputroutine:#1\endcsname}
2819
2820% \protected\def\installfloatmethod#1#2#3% routine keyword handler
2821%   {\ifcsname\??floatsettings#1:#2\endcsname \else
2822%      \expandafter\newtoks\csname\??floatsettings#1:#2\endcsname
2823%    \fi
2824%    \defcsname\??floatmethods#1:#2\endcsname{#3}}
2825%
2826% \protected\def\startfloatmethodsettings#1#2 #3\stopfloatmethodsettings
2827%   {\csname\??floatsettings#1:#2\endcsname\expandafter{\the\csname\??floatsettings#1:#2\endcsname#3}}
2828%
2829% \let\stopfloatmethodsettings\relax
2830%
2831% \protected\def\applyfloatmethodsettings#1#2{\the\??floatsettings#1:#2\endcsname}
2832
2833\definesystemconstant{tblr}
2834\definesystemconstant{lrtb}
2835\definesystemconstant{tbrl}
2836\definesystemconstant{rltb}
2837\definesystemconstant{btlr}
2838\definesystemconstant{lrbt}
2839\definesystemconstant{btrl}
2840\definesystemconstant{rlbt}
2841\definesystemconstant{fxtb}
2842\definesystemconstant{fxbt}
2843\definesystemconstant{fixd}
2844
2845% can move to page-one:
2846
2847\installfloatmethod \s!singlecolumn \v!here        \page_one_place_float_here
2848\installfloatmethod \s!singlecolumn \v!force       \page_one_place_float_force
2849\installfloatmethod \s!singlecolumn \v!left        \page_one_place_float_left
2850\installfloatmethod \s!singlecolumn \v!right       \page_one_place_float_right
2851\installfloatmethod \s!singlecolumn \v!text        \page_one_place_float_text
2852\installfloatmethod \s!singlecolumn \v!top         \page_one_place_float_top
2853\installfloatmethod \s!singlecolumn \v!bottom      \page_one_place_float_bottom
2854\installfloatmethod \s!singlecolumn \v!auto        \page_one_place_float_auto
2855\installfloatmethod \s!singlecolumn \v!margin      \page_one_place_float_margin
2856\installfloatmethod \s!singlecolumn \v!opposite    \page_one_place_float_face
2857\installfloatmethod \s!singlecolumn \v!page        \page_one_place_float_page
2858\installfloatmethod \s!singlecolumn \v!leftpage    \page_one_place_float_leftpage
2859\installfloatmethod \s!singlecolumn \v!rightpage   \page_one_place_float_rightpage
2860\installfloatmethod \s!singlecolumn \v!inmargin    \page_one_place_float_inmargin
2861\installfloatmethod \s!singlecolumn \v!inleft      \page_one_place_float_leftmargin
2862\installfloatmethod \s!singlecolumn \v!inright     \page_one_place_float_rightmargin
2863\installfloatmethod \s!singlecolumn \v!leftmargin  \page_one_place_float_leftmargin
2864\installfloatmethod \s!singlecolumn \v!rightmargin \page_one_place_float_rightmargin
2865\installfloatmethod \s!singlecolumn \v!leftedge    \page_one_place_float_leftedge
2866\installfloatmethod \s!singlecolumn \v!rightedge   \page_one_place_float_rightedge
2867\installfloatmethod \s!singlecolumn \v!somewhere   \page_one_place_float_somewhere
2868\installfloatmethod \s!singlecolumn \v!backspace   \page_one_place_float_backspace
2869\installfloatmethod \s!singlecolumn \v!cutspace    \page_one_place_float_cutspace
2870\installfloatmethod \s!singlecolumn \s!tblr        \page_one_place_float_top
2871\installfloatmethod \s!singlecolumn \s!lrtb        \page_one_place_float_top
2872\installfloatmethod \s!singlecolumn \s!tbrl        \page_one_place_float_top
2873\installfloatmethod \s!singlecolumn \s!fxtb        \page_one_place_float_top
2874\installfloatmethod \s!singlecolumn \s!rltb        \page_one_place_float_top
2875\installfloatmethod \s!singlecolumn \s!btlr        \page_one_place_float_bottom
2876\installfloatmethod \s!singlecolumn \s!lrbt        \page_one_place_float_bottom
2877\installfloatmethod \s!singlecolumn \s!btrl        \page_one_place_float_bottom
2878\installfloatmethod \s!singlecolumn \s!rlbt        \page_one_place_float_bottom
2879\installfloatmethod \s!singlecolumn \s!fxbt        \page_one_place_float_bottom
2880\installfloatmethod \s!singlecolumn \s!fixd        \page_one_place_float_force
2881
2882%D Local floats:
2883
2884\installcorenamespace{localfloats}
2885\installcorenamespace{localfloatstack}
2886
2887\installsetuponlycommandhandler \??localfloats {localfloats}
2888
2889\setuplocalfloats
2890  [%\c!before=\blank,
2891   %\c!after=\blank,
2892   \c!inbetween=\blank]
2893
2894\initializeboxstack\??localfloatstack
2895
2896%newcount  \c_strc_localfloats_n  \aliased\let \noflocalfloats\c_strc_localfloats_n
2897\newinteger\c_strc_localfloats_n  \aliasinteger\noflocalfloats\c_strc_localfloats_n
2898
2899\permanent\protected\def\resetlocalfloats
2900  {\global\c_strc_localfloats_n\zerocount
2901   \initializeboxstack\??localfloatstack}
2902
2903\permanent\protected\def\somelocalfloat
2904  {\global\advanceby\c_strc_localfloats_n\plusone
2905   \savebox\??localfloatstack{\the\c_strc_localfloats_n}{\box\floatbox}}
2906
2907\permanent\protected\def\getlocalfloats
2908  {\dorecurse\c_strc_localfloats_n
2909     {\ifnum\recurselevel=\plusone % 1\relax
2910        \directlocalfloatsparameter\c!before
2911      \else
2912        \directlocalfloatsparameter\c!inbetween
2913      \fi
2914      \dontleavehmode\hpack{\foundbox\??localfloatstack\recurselevel}% \restorebox...
2915      \ifnum\recurselevel=\c_strc_localfloats_n\relax
2916        \directlocalfloatsparameter\c!after
2917      \fi}}
2918
2919\permanent\protected\def\flushlocalfloats
2920  {\getlocalfloats
2921   \resetlocalfloats}
2922
2923% \protected\def\getlocalfloat#1%
2924%   {\normalexpanded{\foundbox{\??localfloatstack}{\number#1}}}% \vbox{\restorebox...}
2925
2926\permanent\protected\def\getlocalfloat#1%
2927  {\foundbox\??localfloatstack{\number#1}} % \vbox{\restorebox...}
2928
2929\permanent\protected\def\forcelocalfloats
2930  {\let\forcedfloatmethod\v!local}
2931
2932\installfloatmethod \s!singlecolumn \v!local \somelocalfloat
2933\installfloatmethod \s!multicolumn  \v!local \somelocalfloat
2934\installfloatmethod \s!mixedcolumn  \v!local \somelocalfloat
2935\installfloatmethod \s!columnset    \v!local \somelocalfloat
2936
2937\protect \endinput
2938