Grammalecte  Changes On Branch e20095be9731edfd

Changes In Branch FixWebext Through [e20095be97] Excluding Merge-Ins

This is equivalent to a diff from a6d823b2a6 to e20095be97

2017-10-28
07:56
[fx] button will disappear only when closing manually the menu check-in: 46027d61ee user: olr tags: fx, FixWebext
07:54
[fx] CSS: line-height doesn’t look OK on Firefox check-in: e20095be97 user: olr tags: fx, FixWebext
07:52
[fx] code cleaning check-in: e605c5e3ec user: olr tags: fx, FixWebext
00:16
Ajout de MutationObserver, ajout dans le css et isolation du xNode du menu (tester uniquement sur Chrome check-in: c422898599 user: IllusionPerdu tags: fx, FixWebext
2017-10-27
21:46
[fr] phonet_simil: handicap/handicape check-in: 00a95e2427 user: olr tags: trunk, fr
20:41
[fx] use a debug profile for Firefox check-in: a6d823b2a6 user: olr tags: trunk, fx
19:32
[fx][bug] retrieving text content from node check-in: e1ac68ef1a user: olr tags: trunk, fx

Modified gc_lang/fr/webext/content_scripts/init.js from [08d2b10057] to [669d7f6b5e].

47
48
49
50
51
52
53


54
55
56
57
58
59
60
    oTFPanel: null,
    oLxgPanel: null,
    oGCPanel: null,

    oMessageBox: null,

    xRightClickedNode: null,



    listenRightClick: function () {
        // Node where a right click is done
        // Bug report: https://bugzilla.mozilla.org/show_bug.cgi?id=1325814
        document.addEventListener('contextmenu', function (xEvent) {
            this.xRightClickedNode = xEvent.target;
        }.bind(this), true);







>
>







47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
    oTFPanel: null,
    oLxgPanel: null,
    oGCPanel: null,

    oMessageBox: null,

    xRightClickedNode: null,

    xObserver: null,

    listenRightClick: function () {
        // Node where a right click is done
        // Bug report: https://bugzilla.mozilla.org/show_bug.cgi?id=1325814
        document.addEventListener('contextmenu', function (xEvent) {
            this.xRightClickedNode = xEvent.target;
        }.bind(this), true);
87
88
89
90
91
92
93



























94
95
96
97
98
99
100
                for (let xNode of document.querySelectorAll("[contenteditable]")) {
                    this.lMenu.push(new GrammalecteMenu(this.nMenu, xNode));
                    this.nMenu += 1;
                }
            }
        }
    },




























    rescanPage: function () {
        if (this.oTFPanel !== null) { this.oTFPanel.hide(); }
        if (this.oLxgPanel !== null) { this.oLxgPanel.hide(); }
        if (this.oGCPanel !== null) { this.oGCPanel.hide(); }
        for (let oMenu of this.lMenu) {
            oMenu.deleteNodes();







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
                for (let xNode of document.querySelectorAll("[contenteditable]")) {
                    this.lMenu.push(new GrammalecteMenu(this.nMenu, xNode));
                    this.nMenu += 1;
                }
            }
        }
    },

    observePage: function () {
        /*
            When a textarea is added via jascript we add the menu :)
        */
        this.xObserver = new MutationObserver(function (mutations) {
            mutations.forEach(function (mutation) {
                for (let i = 0;  i < mutation.addedNodes.length;  i++){
                    if (mutation.addedNodes[i].getElementsByTagName) {
                        if (mutation.addedNodes[i].tagName == "TEXTAREA") {
                            oGrammalecte.lMenu.push(new GrammalecteMenu(oGrammalecte.nMenu, mutation.addedNodes[i]));
                            oGrammalecte.nMenu += 1;
                        } else {
                            for (let xNode of mutation.addedNodes[i].getElementsByTagName("textarea")) {
                                oGrammalecte.lMenu.push(new GrammalecteMenu(oGrammalecte.nMenu, xNode));
                                oGrammalecte.nMenu += 1;
                            }
                        }
                    }
                }
            });
        });
        this.xObserver.observe(document.body, {
            childList: true,
            subtree: true
        });
    },

    rescanPage: function () {
        if (this.oTFPanel !== null) { this.oTFPanel.hide(); }
        if (this.oLxgPanel !== null) { this.oLxgPanel.hide(); }
        if (this.oGCPanel !== null) { this.oGCPanel.hide(); }
        for (let oMenu of this.lMenu) {
            oMenu.deleteNodes();
294
295
296
297
298
299
300



/*
    Start
*/
oGrammalecte.listenRightClick();
oGrammalecte.createMenus();








>
323
324
325
326
327
328
329
330


/*
    Start
*/
oGrammalecte.listenRightClick();
oGrammalecte.createMenus();
oGrammalecte.observePage();

Modified gc_lang/fr/webext/content_scripts/menu.css from [2b784470a7] to [17932b4c0d].

1
2
3
4
5
6
7
8
9
10

11
12
13
14
15
16
17
18
19
20
21
/*
    CSS
    Button and menu for Grammalecte
*/

/*
    Button
*/
.grammalecte_menu_main_button {
    position: absolute;

    display: none;
    margin: -8px 0 0 -8px;
    width: 8px;
    height: 8px;
    background-color: hsla(210, 80%, 80%, .5);
    border: 4px solid hsla(210, 80%, 60%, .5);
    border-top: 4px solid hsla(210, 100%, 40%, .7);
    border-bottom: 4px solid hsla(210, 100%, 40%, .7);
    border-radius: 50%;
    text-align: center;
    cursor: pointer;










>


|
|







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
/*
    CSS
    Button and menu for Grammalecte
*/

/*
    Button
*/
.grammalecte_menu_main_button {
    position: absolute;
    box-sizing: border-box;
    display: none;
    margin: -8px 0 0 -8px;
    width: 16px;
    height: 16px;
    background-color: hsla(210, 80%, 80%, .5);
    border: 4px solid hsla(210, 80%, 60%, .5);
    border-top: 4px solid hsla(210, 100%, 40%, .7);
    border-bottom: 4px solid hsla(210, 100%, 40%, .7);
    border-radius: 50%;
    text-align: center;
    cursor: pointer;
59
60
61
62
63
64
65

66
67
68
69
70
71
72
    margin-left: -10px;
    border-radius: 5px;
    border: 3px solid hsl(210, 50%, 30%);
    box-shadow: 0px 0px 2px hsla(210, 10%, 10%, .5);
    background-color: hsl(210, 50%, 30%);
    font-family: "Trebuchet MS", "Fira Sans", "Liberation Sans", sans-serif;
    z-index: 2147483640; /* maximum is 2147483647: https://stackoverflow.com/questions/491052/minimum-and-maximum-value-of-z-index */

}

.grammalecte_menu_close_button {
    float: right;
    margin: 2px 2px 0 0;
    padding: 1px 5px;
    border-radius: 2px;







>







60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
    margin-left: -10px;
    border-radius: 5px;
    border: 3px solid hsl(210, 50%, 30%);
    box-shadow: 0px 0px 2px hsla(210, 10%, 10%, .5);
    background-color: hsl(210, 50%, 30%);
    font-family: "Trebuchet MS", "Fira Sans", "Liberation Sans", sans-serif;
    z-index: 2147483640; /* maximum is 2147483647: https://stackoverflow.com/questions/491052/minimum-and-maximum-value-of-z-index */
    text-align: left;
}

.grammalecte_menu_close_button {
    float: right;
    margin: 2px 2px 0 0;
    padding: 1px 5px;
    border-radius: 2px;

Modified gc_lang/fr/webext/content_scripts/menu.js from [2428c12fef] to [6f7cefd29a].

1
2
3
4
5
6
7
8

9
10
11
12
13









14
15
16
17
18
19
20

21
22
23
24
25
26
27
28
29
30
31




32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
// JavaScript

"use strict";


class GrammalecteMenu {

    constructor (nMenu, xNode) {

        this.sMenuId = "grammalecte_menu" + nMenu;
        this.xButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_main_button", textContent: " "});
        this.xButton.onclick = () => { this.switchMenu(); };
        this.xButton.style.zIndex = (xNode.style.zIndex.search(/^[0-9]+$/) !== -1) ? (parseInt(xNode.style.zIndex) + 1).toString() : xNode.style.zIndex;
        this.xMenu = this._createMenu(xNode);









        this._insertAfter(this.xButton, xNode);
        this._insertAfter(this.xMenu, xNode);
        this._createListenersOnReferenceNode(xNode);
    }

    _insertAfter (xNewNode, xReferenceNode) {
        xReferenceNode.parentNode.insertBefore(xNewNode, xReferenceNode.nextSibling);

    }

    _createListenersOnReferenceNode (xNode) {
        xNode.addEventListener('focus', (e) => {
            this.xButton.style.display = "block";
        });
        xNode.addEventListener('blur', (e) => {
            window.setTimeout(() => {this.xButton.style.display = "none";}, 300);
        });
    }





    _createMenu (xNode) {
        try {
            let xMenu = oGrammalecte.createNode("div", {id: this.sMenuId, className: "grammalecte_menu"});
            let xCloseButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_close_button", textContent: "×"} );
            xCloseButton.onclick = () => { this.switchMenu(); }
            xMenu.appendChild(xCloseButton);
            xMenu.appendChild(oGrammalecte.createNode("div", {className: "grammalecte_menu_header", textContent: "GRAMMALECTE"}));
            // Text formatter
            if (xNode.tagName == "TEXTAREA") {
                let xTFButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item", textContent: "Formateur de texte"});
                xTFButton.onclick = () => {
                    this.switchMenu();
                    oGrammalecte.createTFPanel();
                    oGrammalecte.oTFPanel.start(xNode);
                    oGrammalecte.oTFPanel.show();
                };
                xMenu.appendChild(xTFButton);
            }
            // lexicographe
            let xLxgButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item", textContent: "Lexicographe"});
            xLxgButton.onclick = () => {
                this.switchMenu();
                let sText = (xNode.tagName == "TEXTAREA") ? xNode.value : xNode.innerText;
                oGrammalecte.startLxgPanel();
                xGrammalectePort.postMessage({
                    sCommand: "getListOfTokens",
                    dParam: {sText: sText},
                    dInfo: {sTextAreaId: xNode.id}
                });
            };
            xMenu.appendChild(xLxgButton);
            // Grammar checker
            let xGCButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item", textContent: "Correction grammaticale"});
            xGCButton.onclick = () => {
                this.switchMenu();
                let sText = (xNode.tagName == "TEXTAREA") ? xNode.value : xNode.innerText;
                oGrammalecte.startGCPanel(xNode);
                xGrammalectePort.postMessage({
                    sCommand: "parseAndSpellcheck",
                    dParam: {sText: sText, sCountry: "FR", bDebug: false, bContext: false},
                    dInfo: {sTextAreaId: xNode.id}
                });
            };
            xMenu.appendChild(xGCButton);
            // Conjugation tool
            let xConjButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item_block", textContent: "Conjugueur"});
            let xConjButtonTab = oGrammalecte.createNode("div", {className: "grammalecte_menu_button", textContent: "Onglet"});
            xConjButtonTab.onclick = () => {








>




|
>
>
>
>
>
>
>
>
>
|
|
|


|

>


|
|


|




>
>
>
>
|







|




|








<



|
|







<
|


|
|







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68

69
70
71
72
73
74
75
76
77
78
79
80

81
82
83
84
85
86
87
88
89
90
91
92
// JavaScript

"use strict";


class GrammalecteMenu {

    constructor (nMenu, xNode) {
        this.xNode = xNode;
        this.sMenuId = "grammalecte_menu" + nMenu;
        this.xButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_main_button", textContent: " "});
        this.xButton.onclick = () => { this.switchMenu(); };
        this.xButton.style.zIndex = (xNode.style.zIndex.search(/^[0-9]+$/) !== -1) ? (parseInt(xNode.style.zIndex) + 1).toString() : xNode.style.zIndex;
        this.xMenu = this._createMenu();

        let xStyle = window.getComputedStyle(this.xNode);
        let nMarginTop = -1 * (8 + parseInt(xStyle.marginBottom.replace('px', ''), 10));

        let xNodeInsertAfter = this.xNode;
        if (document.location.host == "twitter.com" && this.xNode.classList.contains('rich-editor')) {
            xNodeInsertAfter = this.xNode.parentNode;
        }

        this._insertAfter(this.xButton, xNodeInsertAfter, nMarginTop);
        this._insertAfter(this.xMenu, xNodeInsertAfter, nMarginTop + 8);
        this._createListeners();
    }

    _insertAfter (xNewNode, xReferenceNode, nMarginTop) {
        xReferenceNode.parentNode.insertBefore(xNewNode, xReferenceNode.nextSibling);
        xNewNode.style.marginTop = nMarginTop + "px";
    }

    _createListeners () {
        this.xNode.addEventListener('focus', (e) => {
            this.xButton.style.display = "block";
        });
        this.xNode.addEventListener('blur', (e) => {
            window.setTimeout(() => {this.xButton.style.display = "none";}, 300);
        });
    }

    _getText () {
        return (this.xNode.tagName == "TEXTAREA") ? this.xNode.value : this.xNode.innerText;
    }

    _createMenu () {
        try {
            let xMenu = oGrammalecte.createNode("div", {id: this.sMenuId, className: "grammalecte_menu"});
            let xCloseButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_close_button", textContent: "×"} );
            xCloseButton.onclick = () => { this.switchMenu(); }
            xMenu.appendChild(xCloseButton);
            xMenu.appendChild(oGrammalecte.createNode("div", {className: "grammalecte_menu_header", textContent: "GRAMMALECTE"}));
            // Text formatter
            if (this.xNode.tagName == "TEXTAREA") {
                let xTFButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item", textContent: "Formateur de texte"});
                xTFButton.onclick = () => {
                    this.switchMenu();
                    oGrammalecte.createTFPanel();
                    oGrammalecte.oTFPanel.start(this.xNode);
                    oGrammalecte.oTFPanel.show();
                };
                xMenu.appendChild(xTFButton);
            }
            // lexicographe
            let xLxgButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item", textContent: "Lexicographe"});
            xLxgButton.onclick = () => {
                this.switchMenu();

                oGrammalecte.startLxgPanel();
                xGrammalectePort.postMessage({
                    sCommand: "getListOfTokens",
                    dParam: {sText: this._getText()},
                    dInfo: {sTextAreaId: this.xNode.id}
                });
            };
            xMenu.appendChild(xLxgButton);
            // Grammar checker
            let xGCButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item", textContent: "Correction grammaticale"});
            xGCButton.onclick = () => {
                this.switchMenu();

                oGrammalecte.startGCPanel(this.xNode);
                xGrammalectePort.postMessage({
                    sCommand: "parseAndSpellcheck",
                    dParam: {sText: this._getText(), sCountry: "FR", bDebug: false, bContext: false},
                    dInfo: {sTextAreaId: this.xNode.id}
                });
            };
            xMenu.appendChild(xGCButton);
            // Conjugation tool
            let xConjButton = oGrammalecte.createNode("div", {className: "grammalecte_menu_item_block", textContent: "Conjugueur"});
            let xConjButtonTab = oGrammalecte.createNode("div", {className: "grammalecte_menu_button", textContent: "Onglet"});
            xConjButtonTab.onclick = () => {