Created attachment 127428 [details] A testing document Content of a counter is not inserted. For example, here I attached a simple html. Upon opening in a browser, you'd see every heading is enumerated. However, you won't see enumeration at all upon opening the same file in `lowriter`
I confirm. https://www.w3.org/TR/CSS21/generate.html#counters Arch Linux 64-bit, KDE Plasma 5 Version: 5.3.0.0.alpha0+ Build ID: ff2a399b61f34f7920e594e8cbb6c19045b24956 CPU Threads: 8; OS Version: Linux 4.7; UI Render: default; Locale: fi-FI (fi_FI.UTF-8); Calc: group Built on October 7th 2016
I took an attempt to fix this, but at this point I think I gotta move on — at least for now. I think it's worth to put my findings here in case anybody want to try fixing this — or may be if I try returning here at some point. • calc's html import has a newer CSS parser, which ideally should be used. I was told on IRC that writer's html filter is very-very old — peoples are actually surprised there is a CSS parser. • the filter probably supports only CSS1 version. It is made so explicit that "CSS1" infix is everywhere — even in filenames! You can though just ignore it, and add newer features. • the filter code is mediocre — a bunch of global variables, unused variables, over-engineering with abstractions — it's hard to explore. • Before taking on CSS counters you need to add support for ":before" and ":after" selectors and "content:" function. • Full CSS rule (i.e. selector plus body) being parsed at ParseRule() • Parsing selectors (the part before "{") happens at ParseSelector(), and its only influence to the outside world through returned value; which is passed to SelectorParsed(), and afterwards gets deleted. Now, here's an important and cool twist which guaranteed to grant you many hours of confusion: inside CSS1Parser::ParseRule() you see a call to SelectorParsed() which takes the returned value. You go to definition, and what you see: bool CSS1Parser::SelectorParsed( CSS1Selector* /* pSelector */, bool /*bFirst*/ ) { // delete selector return true; } It's one of many functions in html filter which is there just for lols, but this is not the twist. You gonna ask yourself: if value from ParseSelector() just gets deleted, how could it influence the final behavior?? You'd start re-exploring the code hoping to find another global variable, but there is nothing. Follow the rabbit: under the Code World there is a Wonderland Of Machine Code! Fire up gdb, put breakpoint to SelectorParsed() call, and make just one little step — and you'll find there's a SvxCSS1Parser::SelectorParsed()! It has the actual code, and to my shame I don't know why it even works. It might have something to do with functions being declared as "virtual", but "class SvxCSS1Parser" is a child of CSS1Parser, and the code is executed inside the parent, and SelectorParsed() doesn't called through a pointer, rather as a local function. I guess it might be because it implicitly get called through "this" pointer… Interestingly though, etags navigates to the correct definition (as opposed to semantic). • `SwCSS1Parser::StyleParsed()` is where selectors and their styles meet each other. They're stored through `InsertClass()` into a std::map `m_Classes` for further processing. What's left, is to find where it loops over text elements (i.e. headings, paragraphs, etc), compares to selector, and applies stuff from CSS body. But I really tired, I spent much more time than it seems from the above. I've got more notes locally too, but don't think they're really relevant.
I am going to try writing a new filter for writer, so may be after this is done, I could try top-down approach to html filter, being armed with the knowledge of the code components higher the stack.