Forum How do I...?

Cannot access document.styleSheets

rathje
Hi,

I would like to modify the stylesheet via JavaScript (to set a counter-reset), but document.styleSheets is undefined when running Prince.

Log.info("document.styleSheets: " + document.styleSheets) 


gives

prince: document.styleSheets: undefined


I have tried embedded and and linked styles.

Any ideas?
mikeday
Sorry, you will need to modify the DOM directly by adding/removing elements and text nodes, the styleSheets collection is not yet supported.
rathje
Thanks, that was damn quick.

But it seems that tampering with the dom doesn't update Prince's styles knowledge - at least not when called via prince-script.

This does work:

var style = document.createElement('style'),
         script = document.getElementsByTagName('script')[0],
            styles = 'footer { page: footer; counter-reset: page 666; }';
            script.parentNode.insertBefore(style, script);
            style.innerHTML = styles;


This does not work:

 Prince.addScriptFunc("resetPageToMainStartPage", function() {
            var style = document.createElement('style'),
            script = document.getElementsByTagName('script')[0],
            styles = 'footer { page: footer; counter-reset: page 666; }';
            script.parentNode.insertBefore(style, script);
            style.innerHTML = styles;
        });


with

footer::before {
		content: prince-script(resetPageToMainStartPage);
}


Edited by rathje

mikeday
Right, prince-script() functions cannot update the DOM. Or they can, but it's too late, and it won't affect the document typesetting which is already ongoing. What is it you want to do? There may be another way to do it.
rathje

Yup, there might be another way. I even think I saw it here in the forum weeks ago, but I cannot find it anymore.

My Problem:
- front matter pages are displayed roman, from say I to IX
- for the main matter the page counter is reset to 1 (say 1 to 99),
- for the back matter I have to resume the front matter counter, starting with X in this example.

Thus, I need to save the value of the front matter page counter somewhere.
(I have tried things like "counter-reset: oldpage counter(page)". Since this didn't work I tried the Javascript approach above.)

Best,
Dirk
mikeday
Tricky! You could use JavaScript to capture the last page of the front matter and the last page of the main matter, then do the subtraction for the back matter, like this:
<html>
<head>
<style>
@page front {
    @bottom { content: prince-script(frontpage, counter(page)) }
}

@page main {
    @bottom { content: prince-script(mainpage, counter(page)) }
}

@page back {
    @bottom { content: prince-script(backpage, counter(page)) }
}

.front { page: front }
.main { page: main; counter-reset: page 1 }
.back { page: back }
</style>
<script>
var lastmainpage = 0, lastfrontpage = 0;

Prince.addScriptFunc("frontpage", function(pagenum) {
    pagenum = Number(pagenum);
    if (pagenum > lastfrontpage) lastfrontpage = pagenum;
    return pagenum;
});

Prince.addScriptFunc("mainpage", function(pagenum) {
    pagenum = Number(pagenum);
    if (pagenum > lastmainpage) lastmainpage = pagenum;
    return pagenum;
});

Prince.addScriptFunc("backpage", function(pagenum) {
    pagenum = Number(pagenum);
    return pagenum - lastmainpage + lastfrontpage;
});
</script>
</head>
<body>

<div class="front">
Front matter
</div>

<div class="main">
Main matter
<div style="page-break-before: always"></div>
Main matter
<div style="page-break-before: always"></div>
Main matter
</div>

<div class="back">
Back matter
</div>

</body>
</html>

I'm not super proud of this solution, though. Also it is tricky to get the Roman numerals in this approach, unless you implement it yourself in JavaScript, which is a little tedious.

Edit: also because we are not actually changing the page counter, cross-references into the back matter will not be correct unless you also use prince-script() for them too.

Edited by mikeday

rathje

Even if you are not super proud of this: I am super grateful.

For the roman numerals I found this: http://stackoverflow.com/questions/9083037/convert-a-number-into-a-roman-numeral-in-javascript

****

What about a feature request to allow prince-script() in the counter-reset-property? Then, the old counter could be saved via one prince-script() call, and resumed by a second.

Best,
Dirk
mikeday
Yes, that would be handy. I will add this to the roadmap.