Search code examples
mysqlnode.jsiframetinymceinnerhtml

Why does this Javascript function rewrite the innerHTML of one div but not the other?


I'm using NodeJS to query a MySQL database for a single entry of a journal, but the results aren't going to both of the assigned divs. I have an iFrame in my center column, dedicated to two divs (one hidden at any given time). One div is a read-only page for the journal entry, and the other one contains a TinyMCE rich-text editor. I have buttons in left column to switch between the views.

The rich-text editor loads properly on initial load of page, but doesn't update as I navigate with the calendar; the read-only innerHTML does update properly as I navigate. calDt[] is an array that holds dates. calDt[0] is the active date, while calDt[1] holds a dummy date used for navigating the calendar without changing the entry.

app.js:

    app.get('/getdata/:dateday', (req, res) => {
        let sql = `SELECT entry FROM main where dateID ='${req.params.dateday}'`
        let query = db.query(sql, (err, results) => {
            if(err) {
                throw err 
            }
            res.send(JSON.stringify(results));
        })
    })

middle-left.ejs

   <button style= "height:22px"; type="button" onclick="readDivHere()">Lock</button>
   <button style= "height:22px"; type="button" onclick="editDivHere()">Edit</button></div>

    <script> // the Lock button brings us back to the completed entry in the middle stuff
        function readDivHere() {
        document.getElementById('frame1').contentWindow.readDivHere();
        document.getElementById('frame1').scrolling = "yes";
    }
    </script>

    <script> // the Edit button will bring tinymce rich-text editor to the middle stuff
        function editDivHere() {
        document.getElementById('frame1').contentWindow.editDivHere();
        document.getElementById('frame1').scrolling = "no";
    }
    </script>

middle-center.ejs

<iframe id="frame1" class="entryon" src="" frameborder="0px"></iframe>
<script>
    document.getElementById("frame1").src = "iframe";
</script>

iframe.ejs


    <div id="readDiv" class="here" style="display: block; background: white; padding-top: 0px; padding-left: 10px; padding-right: 8px; min-height: 810px; width: 967px;"><%- include ('entry'); %></div>
    <div id="editDiv" class="here" style="display: none; padding: 0px;" ><%- include ('editPage'); %></div>


    <script> //function that switches from rich-text editor back to real entry
        function readDivHere() { // here we run a function to update text of read-only entry
        document.getElementById("readDiv").style.display="block";
        document.getElementById("editDiv").style.display="none";
        }
    </script>
    <script> //function that switches from read-only entry to rich-text editor
        function editDivHere() {
        document.getElementById("readDiv").style.display="none";
        document.getElementById("editDiv").style.display="block";
        }
    </script>

entry.ejs

<div id="readOnlyEntry"></div>

<script>
        // load the active entry into the middle column for proper reading
        function loadEntry(p) {
                var x = parent.calDt[1].getFullYear();
                var y = parent.calDt[1].getMonth();
                y = y + 1;
                if (y < 10) {
                    y = "0" + y;
                };
                if (p < 10) {
                    p = "0" + p;
                }
                var newDate = x + "" + y + "" + p;     // p is a date formatted like 20210808
                var xhttp = new XMLHttpRequest();
                xhttp.onreadystatechange = function() {
                    const text = this.responseText;
                    const obj = JSON.parse(text);
                    document.getElementById("readOnlyEntry").innerHTML = obj[0].entry;
                    document.getElementById("richTextEd").innerHTML = obj[0].entry; // doesn't work!
                }
            xhttp.open("GET", "../getdata/" + newDate, true);
            xhttp.send();
        }
</script> 
    
<script>
    // rich-text editor populates correctly on load
    loadEntry(parent.calDt[0].getDate());
</script>

editPage.ejs

<%- include ('tinymce'); %>

<form method="POST" action="../result" enctype="multipart/form-data">
        <textarea name="content" id="richTextEd">Here's the default text.</textarea>
</form>

calendar-clicker.ejs

var p = x.innerHTML; // get the value of the calendar cell text (i.e. day of the month)
p = p.match(/\>(.*)\</)[1];
var d = calDt[1].getFullYear(); // what year is the calendar referencing?
var q = calDt[1].getMonth();  // what month is the calendar referencing? 
q = q + 1; // compensate for javascript's weird month offset
calDt[0] = new Date(q + "/" + p + "/" + d); // assign a new global date variable
calDt[1] = calDt[0]; // temporarily reset navigation date to active date
document.getElementById('frame1').contentWindow.loadEntry(p);

Does the failure have to do with assigning the innerHTML to a different .ejs? If I put the form into the same div as the read-only entry, the form still fails to update as I navigate.


Solution

  • Solved it. In entry.ejs, I replaced...

    document.getElementById("richTextEd").innerHTML = obj[0].entry;
    

    with

    tinymce.get("richTextEd").setContent(obj[0].entry);
    

    https://www.tiny.cloud/blog/how-to-get-content-and-set-content-in-tinymce/