zacharied / anki-content-injector

Anki add-on to "overlay" HTML/CSS/JS content on cards at review-time
3 stars 2 forks source link

Expanding {{Field}}s in _global.html #1

Open khonkhortisan opened 5 years ago

khonkhortisan commented 5 years ago

{{Tags}}, or {{info::Id}} from Additional Card Fields (Fork for 2.1) https://ankiweb.net/shared/info/744725736 don't expand after injection. It would be nice to be able to use this for adding the subject on a card based on tags, or as a seed for randomizing multiple choice questions in javascript without having it randomize differently on the front versus the back side.

zacharied commented 5 years ago

I'll dig around the Anki code later to try to figure out where it substitutes the {{Field}}s. We currently use the prepareQA hook to inject, so we don't very much choice as to when it gets called. I can look into monkey-patching the page render method to try to inject the content earlier. Edit 1 The relevant code is in anki/template/template.py. Looks like the substitution is first performed at anki/collection.py:579. Edit 2 We have to get the content injected before template.render() is called (see anki/template/template.py:55).

Incidentally, I did something similar to your randomization problem using Cookie monster. You can just store a randomly generated number in a cookie in the question and then retrieve it in the answer.

khonkhortisan commented 5 years ago

Another option would be to manually call the substitution on the content while injecting it

I confused myself with a series of hacks

inject+="<script>"
inject+="var mw_reviewer_state='"+str(mw.reviewer.state)+"';"
inject+="var mw_reviewer_card__note_tags='"+" ".join(mw.reviewer.card._note.tags)+"';"
inject+="</script>"
<div id="tags" align=right style="font-size:8px;color:grey;position:absolute;bottom:0;right:0;z-index:-1;">{{Tags}}</div>
document.getElementById("tags").innerHTML=mw_reviewer_card__note_tags;
⋮
alert("tags: "+document.getElementById('tags').innerHTML);
khonkhortisan commented 2 years ago

I ran into this again with

<svg width="100%" height="100%" data-jdenticon-value="{{info-Id:}}" style="position:absolute;left:0;top:0;z-index:-1"></svg>
<script src="https://cdn.jsdelivr.net/npm/jdenticon@3.1.1/dist/jdenticon.min.js" async
        integrity="sha384-l0/0sn63N3mskDgRYJZA6Mogihu0VY3CusdLMiwpJ9LFPklOARUcOiWEIGGmFELx"
        crossorigin="anonymous">
</script>