Open giannissc opened 1 year ago
Currently elements cannot break away from their local scope. If columns
is activated globally in the document, subsequent elements cannot break from their column parent to use the full width of the page.
A separate issue is that if an element (e.g. image) doesn't fit into the remaining space it will move to the next page/column leaving a blank space behind it.
These two issues, while separate, must be tackled together as there are complex interactions between them.
To solve the first issue I propose that we introduce a scope
argument to all the layout methods. Scope can either be global
(relative to page) or local
(relative to parent [existing behavior]).
To solve the second issue I propose a new layout element #wrap
or #float
(no strong preference but for the rest of this post I will be using #wrap
). #wrap
is the counterpart to #place
. Unlike place however, it can participate in the flow.
The function signatures would be:
#place(scope, alignment, dx, dy, body)
#wrap(scope, [alignment], dx, dy, body)
alignment
:
[]
: [alignment]
:[alignment, alignment, ...]
[, alignment, ...]
Algorithm for #wrap
elements:
#wrap
element's dimensions and check if the element can fit to existing page/column (other #wrap
elements might already populate the page)#wrap
element at correct position in current page/column based on its alignment
policy. Relayout all other content (except other #wrap
elements) in current page/column.#wrap
element at correct position in the next page/column based on its alignment
policy. Keep adding content to current page until it is filled.In case 2 or more #wrap
elements are placed in the same position in a page/column fallback arguments
can be used to decide its position:
alignment
- [alignment1, alignment1]
: place it to the next available spot (e.g. if 2 #wrap
elements request the top position then place the first #wrap
element at the top and the second #wrap
below it.)alignment
- [alignment1, alignment2]
: Place the 2nd #wrap
to the position indicated by alignment2
. Assuming there are no more conflicts the content is laid out again in the available space. If there is another conflict move to the next page and repeat (alignment1 -> alignment2
). For example if the first #wrap
request the top position then the second can request in the fallback the bottom.alignment
- [alignment]
: no fallback value is provided, move to the next page and repeat (alignment
)alignment
- []
: no primary alignment value is provided, try to fit #wrap
into existing page/column. Otherwise move to the top of next page/column. If there is a conflict move to an empty space belowalignment
- [, alignment]
: Try to place to current page/column at current position. If it doesn't fit or there is some other conflict use secondary alignment
. If there are more conflicts move to the top of next page and repeatDoes this seem reasonable? @laurmaedje, @reknih
Also is this the best place to discuss or do you prefer discord?
I am also willing to contribute code to get this out sooner! 🙂
Not allowing text to wrap around other elements can result in the following issue:
Simple allowing content to break the column rules and layout based on page will also have the same issue:
#wrap(scope: local, alignment: [])
- Default#wrap(scope: global, alignment: [])
#wrap(scope: global, alignment: [center+horizon])
#wrap(scope: global, alignment: [top, top])
#wrap(scope: global, alignment: [top, bottom])
This is great. In fact, it'd be ideal.
Do you think the primary and secondary alignments are both necessary? @Andonome
This is the most important missing feature to make typst as powerful as LaTeX.
Do you think the primary and secondary alignments are both necessary? @Andonome
I wouldn't say 'necessary', but I've found a great deal of flexibility in having both 'top' and 'bottom' options.
This page looks fine, as-is, but the two elements float apart when more text is added, which matches the general format of pictures-at-bottom, and tables-on-top.
I've not found tables in the centre work very often.
Of course if anyone wants to get really fancy, automatic wrapping around a PNGs filled parts would be punk-as-all-heck.
This is the most important missing feature to make typst as powerful as LaTeX.
LaTeX doesn't have this ability. There is no reliable text wrapping in a multicols environment. It's a big factor which stops it having reliable output - every compile, every page needs to be checked, images moved, et c.
Edit: I see I've received some silent naysayers downvoting this comment.
If anyone wants to put their code where their mouth is, check out my main project, and get any 3 images (of your choosing) to float, using any macro you please.
@Andonome I think is wrap is to be implemented it should be implemented with all these usecases in mind. Another usecase that comes to mind is that you have a central circular figure and that text should wrap around it as well. You examples are genuinely useful. Thanks!
In you table and figure example would you want to force text to move to the next page or would it be ok for it to render in-between the two elements?
@Andonome I think is wrap is to be implemented it should be implemented with all these usecases in mind. Another usecase that comes to mind is that you have a central circular figure and that text should wrap around it as well. You examples are genuinely useful. Thanks!
Would a showcase be useful? I've had a bunch of ugly results with difficult elements.
In you table and figure example would you want to force text to move to the next page or would it be ok for it to render in-between the two elements?
It depends on the results. Either could be fine, but what's sorely lacking is the ability to return to the last page for a do-over. LaTeX can't correct previous pages, so you can get these ugly dangling single-lines of text.
I've given headers a bunch of \needspace{
commands to stop them going at the end of a page, but that's left this dangling, when the next couple of \paragraph
statements (with Journeys) could have fit between these two images fine.
Of course here it's blocked by the General Tempo Chart, so that should have been moved to after the next paragraph.
In a lot of cases, it's far more important to say 'place this element somewhere before the next subsection' than making a statement about the position.
Here's another table that could have been better placed by floating anywhere else after the \subsection{Encounters}
.
I don't know if there's a non-intensive way to have typst go through a bunch of options involving multiple pages, but maybe there could be a second processing option where the user understands it'll take extra time to process, but the results will make sense. Atm a full LaTeX process can take 20 minutes - that's quite doable for big pushes, but less okay when the results need fiddled with before publishing a new version.
I have update the proposal based on your previous comments and from conversations in Discord. Here is the updated proposal if you want to have a look @Andonome :
Multi-column Float Proposal.pdf
I haven't thought thoroughly about your latest comment just yet but do you think that the proposal here covers those usecases
Ok I just had another look and your usecase in incredibly useful! I might need to tweak the scope
argument with other options such as paragraph
, section
, etc. for more fine-grained control!
It depends on the results. Either could be fine, but what's sorely lacking is the ability to return to the last page for a do-over. LaTeX can't correct previous pages, so you can get these ugly dangling single-lines of text.
I am not sure I fully understand this point. Is this something that the algorithm is lacking or is it something that the existing Latex API cannot express. If it is the latter I will make a note on the algorithm implementation portion of the proposal otherwise I will make a note on the motivation and API section as an additional user intent
Proposal v3: Multi-column Float Proposal-3.pdf
Proposal v4: Multi-column Float Proposal-4.pdf
Proposal v4: Multi-column Float Proposal-4.pdf
This all looks fantastic.
In 1.6:
Giving an option to disable horizontal wrapping would alleviate the issue.
It might be better to disable this by default. Nobody wants to see 2-words crawling down the side of a table. The table should be centred automatically.
In fact in general, the default being 'typst chooses' is always good. Take for example the first example table. It's clearly best presented image-wide, but that won't always be obvious until the page has processed. If the floating default behaviour was for typst to choose how it floats (and only request the user states if it should be in the same section or page as something else) then it'd really help in producing unattended document production.
I can suggest reading the Lillypond essay about problems of automated music engraving. I believe, a lot of ideas are common to any complex layout system and potentially can be applied to typst as well.
tldr: Music notation is much more complicated than one can imagine. Naive approach to notation layout based on the hierarchy of containers (page→staff→lines→notes etc) simply does not work. Once in a while you will face some quirky notation like multi-staff slurs or beams, and things will get complicated. In the end, this will result in a lot of ad-hoc code, or the result will not be visually pleasing. Lillypond uses completely different approach to layout.
I just wanted to add my +1 here.
I'm trying to write up a whitepaper in IEEE format and floating tables / figures are not possible AFAIK.
It would be lovely to see this feature implemented.
+1. As far as I can tell, this is the only missing feature stopping me completing a nearly perfect template for my usual research journal (and then hassling the editors about it). Having figures and tables spanning two columns is a must.
Just thought I'd add some god-tier image floating challenges.
The ideal command here would be something like #image[ columns = 2, image.png]
.
I don't how much of a 'badness' rating typst has under the hood, but perhaps an image could be covered when needed, as above.
Clearly only available for .png or something with transparency, but automatic text-wrapping would be the bees' knees.
+1 need this as well @onefact!
Also needing this for conference/journal submissions. E.g. summary tables, larger figures (a la small-multiples), etc.
Any updates on this? I need a way to span a table over two columns for a research paper.
@danaugrs Unfortunately, there has been no progress on this lately.
This is my use case I would very much like to be able to reproduce in Typst: to wrap text around a textbox. In LaTeX I used packages wrapstuff
and tcolorbox
for this, see result:
The LaTeX code to achieve this effect looks like this; top = 5
is the number of lines of the paragraph where mybox
is supposed to appear.
\begin{wrapstuff}[top=5, width=0.4\linewidth]
\begin{mybox}[title=LektĂĽre-Empfehlung]
Gundersen (2021, pp. 31-49) gibt in seiner (online verfügbaren) Dissertation einen informativen und zugleich prägnanten Überblick über die Anfänge und Geschichte von DBR in der Bildungsforschung. Auch in den einführenden Büchern von Bakker (2018) sowie McKenney und Reeves (2019) wird auf die Entwicklung von DBR eingegangen. Dort finden sich auch Erläuterungen zu Varianten und Hinweise auf erste Meta-Studien.
\end{mybox}
\end{wrapstuff}
\textbf{Seit wann gibt es DBR im Bildungskontext?} Anfang der 1990er Jahre haben die Bildungsforscher Ann Brown (1992) und Allan Collins (1992) sogenannte Designexperimente kreiert. Sie waren unzufrieden mit Laborexperimenten und wollten besser verstehen, wie Lernen im Kontext funktioniert. Dazu verlegten sie ihre Forschung vom kontrollierten Labor ins reale Klassenzimmer. Klassenzimmer ist hier wörtlich zu nehmen, denn im Blick war vor allem die Schule. Das Ziel, sowohl praktische als auch theoretische Relevanz zu erreichen, ist in DBR kennzeichnend geblieben. Bereits diese frühen Designexperimente waren interventionistisch, iterativ und kollaborativ angelegt, und man arbeitete tendenziell mit kleinen Fallzahlen. Designexperimente gelten als die Anfänge von DBR.
\textbf{Wie hat sich DBR weiter entwickelt?} Ende der 1990er Jahre und um 2000 stieg das Interesse an Designexperimenten. Es entwickelten sich Varianten unter verschiedenen Bezeichnungen wie Developmental Research oder Formative Research. Einige Autoren begannen, zwischen Validierungs- und Entwicklungsstudien zu unterscheiden und als eigenständige Studientypen zu postulieren. Durchgesetzt hat sich diese Trennung allerdings nicht, was auch einem der Kernmerkmale -- der doppelten Zielsetzung für Wissenschaft und Praxis -- widerspräche. Dennoch sind die Arbeiten aus dieser Zeit einflussreich und markieren wichtige Suchbewegungen, die in DBR nach wie vor diskutiert werden: Dazu gehört etwa die Frage, wie man in DBR zu theoretischen Erkenntnissen gelangt und auf welche Weise Verallgemeinerungen möglich sind. In den 2000er Jahren sind zahlreiche methodologische Beiträge zu DBR in englischer Sprache erschienen. Das, was wir als gemeinsame Merkmale von DBR zusammengestellt haben, wurde in dieser Zeit erarbeitet. Seit 2010 werden zunehmend mehr DBR-Studien veröffentlicht; auch erste systematische Übersichtsarbeiten erscheinen. Begleitet wurden und werden diese Aktivitäten durch Kritik vor allem aus der Perspektive der empirischen (pädagogisch-psychologisch ausgerichteten) Bildungsforschung: Legt man deren Routinen und Qualitätsstandards an, erscheinen sowohl die empirischen als auch die theoretischen Prozesse und Ergebnisse von DBR oft unbefriedigend.
With mybox
being defined as
\newtcolorbox{mybox}[1][]{
enhanced,
boxsep=0pt,
boxrule=0pt,
toprule=3pt,
code={\vspace{-2ex}\footnotesize\singlespacing\fontfamily{cmss}\selectfont},
#1}
Is this feature being considered for version 1.0 of Typst?
Is this feature being considered for version 1.0 of Typst?
Definitely. But note that 1.0 is still a ways off.
We need this feature Typst Devs :cry:
A solution in the meantime: https://github.com/ntjess/wrap-it PR is here: https://github.com/typst/packages/pull/357
It handles the common cases (think of it like a less-finicky version of wrapfig
), but there are still some fundamental limitations that can't be solved in typst
I'm impressed by your solution Nathan! Great work!
A solution in the meantime: https://github.com/ntjess/wrap-it PR is here: typst/packages#357
It handles the common cases (think of it like a less-finicky version of
wrapfig
), but there are still some fundamental limitations that can't be solved in typst
This looks pretty neat. Does anyone know whether it's possible to position a table spanning the width of the page in typical Typst 2-column layout with this package?
A solution in the meantime: https://github.com/ntjess/wrap-it PR is here: typst/packages#357 It handles the common cases (think of it like a less-finicky version of
wrapfig
), but there are still some fundamental limitations that can't be solved in typstThis looks pretty neat. Does anyone know whether it's possible to position a table spanning the width of the page in typical Typst 2-column layout with this package?
Doesn't seem like it's possible - at least I wasn't able to. Maybe @ntjess knows a workaround?
Im not sure if it was already discussed elsewhere but I believe that the ability to place multicolumn floats should be a feature of columns
(reflowing the text as needed) instead of a temporary break of the columns
element.
i encountered the same issue whilst using the charged-iee template, i wasn't able to put a figure containing a large / wide image at the top, spanning the two columns :thinking:
having this feature or a workaround would be really great :innocent:
Any idea when this feature will be added?
@Vivdaddy We plan to take a closer look at this for 0.12, but I can't make any promises.
It seems like spanning a figure across all columns should be relatively straightforward to implement and it would fix 90% of all multi-column issues. Specially if the figure is at the top or bottom of a page. It would be as if a page with such a figure were a little shorter and the page break happened a bit before or after the actual page break in order to make space for the figure. I know that if this feature were implemented it would prevent me from temporarily switching back to LaTeX, and it seems a lot of people are also anxiously waiting for this (over 100 users if we go by GitHub reactions, but I suspect there are many more). Please let us know when you have updates! :heart:
It seems like spanning a figure across all columns should be relatively straightforward to implement and it would fix 90% of all multi-column issues. Specially if the figure is at the top or bottom of a page. It would be as if a page with such a figure were a little shorter and the page break happened a bit before or after the actual page break in order to make space for the figure. I know that if this feature were implemented it would prevent me from temporarily switching back to LaTeX, and it seems a lot of people are also anxiously waiting for this (over 100 users if we go by GitHub reactions, but I suspect there are many more). Please let us know when you have updates! :heart:
I suspect that if it was straightforward the issue wouldn't still be open.
I suspect that if it was straightforward the issue wouldn't still be open.
This issue is about arbitrary multi-column float elements, which is a complex problem, specially if it involves arbitrary-shape text wrapping as in the last image in this comment. My objective was to point out that there is a subset of this problem space i.e. spanning an element across all columns of a page, specially at the top or bottom of a page (with no arbitrary-shape text wrapping), which is simpler to implement, and would solve the majority of use cases. I think any attempt at a solution should first focus on this.
@laurmaedje Any progress on this feature request? :)
I believe that the lack of support for multi-column figures and tables is the main limitation to using Typst for writing manuscripts for scientific journals.
is the main limitation
It depends on the field - almost nothing I submit to (in biology) uses multi-column layouts, but I need line numbers (happily that's being worked on #352 )
I believe that the lack of support for multi-column figures and tables is the main limitation to using Typst for writing manuscripts for scientific journals.
Definitely true for informatics and computer sciences where the IEEE format is quite common. Some stuff is just to large to fit in a single half-page column meaningfullly.
I think the ideal solution, from a user's perspective, would involve adding a single parameter, tentatively called colspan
, to non-breakable block elements, which would specify how many columns that element should span. Specifying a colspan
of more columns than exist in the current context would result in an error. I think such a parameter, coupled with the existing usage of placement: "auto" | "top" | "bottom"
, would provide complete freedom to place multi-column blocks anywhere as desired.
I'm not a mod, but I think that there are now enough "This feature is stopping me from using Typst"/"This feature is missing for XYZ support" comments in this issue. The Devs are aware of this issue, and it is as-of-now the third most upvoted issue. So instead of adding more comments of the same, I'd suggest using the emoticons to express your support for this feature. (And the selfish remark: Then people that have subscribed to this issue will not get spammed with non-progress messages)
Supersedes: #137.
I want to be able to break the column rules for figures and tables to the full size of the page and I want to be able to float these elements. I believe these two must be tackled together as you can see in the motivating examples