index.js 10.8 KB
Newer Older
1
// Object which stores all the user selected/entered values
2
let inputObj = {
3
4
    textChoice: 'manual',           // choice of text entry initially set as manual. Can have values manual, calculated
    text: '',                       // User entered text in case of manual  
5
    numberOfCharacters: '',         // number of characters in text. Either from user entered text or user entered number
6
7
    schoolLevel: '',                // Value of school level selected from dropdown
    category: ''                    // Value of category selected from dropdown
8
};
9

10
11

// function handleTextRadioClick: responsible for showing or hiding text input / text length input based on selected option
12
function handleTextRadioClick() {
13
14
    let textChoice = document.querySelector('input[name="text-input-option"]:checked').value;
    inputObj.textChoice = textChoice;
15
16
17
18
19
20
21
22
    if (textChoice === 'manual') {
        let value = removeSpecialCharacters(inputObj.text);
        let characters = value.length;
        setCharacterLength(characters);
    } else {
        let value = document.getElementById("inputTextCharacters").value;
        setCharacterLength(value);
    }
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38

    // show or hide validation messages
    if (inputObj.textChoice === 'manual' && inputObj.text === '') {
        //document.getElementById('textarea-validation').style.display = 'block';
    } else {
        document.getElementById('textarea-validation').style.display = 'none';
    }

    if (inputObj.textChoice === 'calculated' &&
        (inputObj.numberOfCharacters === '' || inputObj.numberOfCharacters === 0)) {

        //document.getElementById('textCharacters-validation').style.display = 'block';
    } else {
        document.getElementById('textCharacters-validation').style.display = 'none';
    }

39
40
41
42
    toggleElement('character-calculation-wrapper');
    toggleElement('manual-character-input');
}

43
44
45

// function toggleElement: hides/shows the html element based on current visibility. 
// accepts value of id attribute of element as parameter
46
function toggleElement(id) {
47
48
49
    let element = document.getElementById(id);
    if (element.style.display === "none") {
        element.style.display = "block";
50
    } else {
51
        element.style.display = "none";
52
53
54
    }
}

55
56

// function handleTextAreaChange: captures the changes as user enters the text and gets the length
57
// and sets number of characters to property numberOfCharacters on inputObj
58
59
function handleTextAreaChange() {
    let value = document.getElementById("manual-text-entry").value;
60
    inputObj.text = value;
61
62
    value = removeSpecialCharacters(value);
    let characters = value.length;
63
    setCharacterLength(characters);
64
65
66
67
68
69
70
71
    document.getElementById("calculatedTextCharacters").setAttribute('value', characters);
}

// function removeSpecialCharacters: removes punctuation marks and other special characters
// but allows numbers and alphabets along with language specific characters German: äöüÄÖÜß and French: ùûüÿàâæéèêëïîôœÙÛÜŸÀÂÆÉÈÊËÏÎÔŒ
function removeSpecialCharacters(str) {
    return str.replace(/(?!\w|||||||||||\ÿ|||||||||||||||||||||||||\Œ)./g, '')  // regex to remove special characters 
        .replace(/^(\s*)([\W\w]*)(\b\s*$)/g, '$2');   // regex to trim the string to remove any whitespace at the beginning or the end
72
73
}

74
75

// function handleCharacterInputChange: captures changes in number of characters input field
76
// and sets number of characters to property numberOfCharacters on inputObj
77
78
79
80
81
function handleCharacterInputChange() {
    let value = document.getElementById("inputTextCharacters").value;
    setCharacterLength(value);
}

82
// function setCharacterLength: sets number of characters to property numberOfCharacters on inputObj
83
function setCharacterLength(characters) {
84
85
86
87
88
    if (characters === '') {
        inputObj.numberOfCharacters = 0;
    } else {
        inputObj.numberOfCharacters = parseInt(characters);
    }
89
90
91
}


92
93
94
// function isFormValid: checks for mandatory input fields and validates te form 
// returns true if all values are filled else returns false
// also shows error messages for respective inputs fields
95
function isFormValid() {
96
97
98
99
100
101
102
103
    let invalidFields = 0;
    if (inputObj.textChoice === 'manual' && inputObj.text === '') {
        invalidFields++;
        document.getElementById('textarea-validation').style.display = 'block';
    } else {
        document.getElementById('textarea-validation').style.display = 'none';
    }

104
    if (inputObj.textChoice === 'calculated' &&
105
        (inputObj.numberOfCharacters === '' || inputObj.numberOfCharacters === 0)) {
106

107
108
109
110
111
112
        invalidFields++;
        document.getElementById('textCharacters-validation').style.display = 'block';
    } else {
        document.getElementById('textCharacters-validation').style.display = 'none';
    }

113
    if (inputObj.schoolLevel === '' || inputObj.schoolLevel === 0) {
114
        invalidFields++;
115
        document.getElementById('schoolLevel-validation').style.display = 'block';
116
    } else {
117
        document.getElementById('schoolLevel-validation').style.display = 'none';
118
119
    }

Ratnadeep Rajendra Kharade's avatar
Ratnadeep Rajendra Kharade committed
120
    if (inputObj.category === '' || inputObj.category === 0) {
121
        invalidFields++;
122
        document.getElementById('category-validation').style.display = 'block';
123
    } else {
124
        document.getElementById('category-validation').style.display = 'none';
125
    }
126

127
128
129
130
131
132
133
    if ((inputObj.numberOfCharacters < 100 && (inputObj.schoolLevel === '1' || inputObj.schoolLevel === '2'))) {
        invalidFields++;
        document.getElementById('min-count-validation').style.display = 'block';
    } else {
        document.getElementById('min-count-validation').style.display = 'none';
    }

134
    return invalidFields < 1
135
136
}

137
138

// function showFeedbackForm: displays feedback form when calculation is done
139
function showFeedbackForm() {
140
141
    let element = document.getElementById('feedback-form');
    element.style.display = "block";
142
}
143

144

145
146
147
// function schoolLevelChangeEvent: listens for change in school level dropdown
// and sets selected value to property schoolLevel on inputObj
function schoolLevelChangeEvent(event) {
148
    inputObj.schoolLevel = event.target.value;
149
150
}

151
152
153
// function categoryChangeEvent: listens for change in category dropdown
// and sets selected value to property category on inputObj
function categoryChangeEvent(event) {
154
    inputObj.category = event.target.value;
155
}
156
157
158
159
160
161
162
163
164
165
166


// function calculateReadingTime: This function is responsible for calculating reading time
// reading time can be calculated if all inputs are valid
function calculateReadingTime() {

    if (isFormValid()) {

        //variable x which holds final reading time in minutes
        let x = 0;

167
        // logic or algorithm for calculating reading time goes here
168
        // inputObj.numberOfCharacters has number of characters (number data type)
169
170
        // inputObj.schoolLevel has level of school (string data type)
        // inputObj.category has category of reader (string data type)
171

172

173
        // example calculation
174
175
176
        //x = (inputObj.numberOfCharacters * inputObj.schoolLevel * inputObj.category);

        let combination = inputObj.schoolLevel + '' + inputObj.category;
177

178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
        let C = inputObj.numberOfCharacters;

        switch (combination) {
            case '11':
                x = (0.7165 * C) + (172.8332 * 0.690) - 125.9143;
                break;
            case '12':
                x = (0.3463 * C) + (185.4177 * 0.249) - 62.0577;
                break;
            case '13':
                x = (0.4967 * C) + (223.3422 * 0.386) - 101.3559;
                break;
            case '14':
                x = (0.6489 * C) + (195.7637 * 0.528) - 120.8358;
                break;
            case '15':
                x = (0.7165 * C) + (172.8332 * 0.690) - 125.9143;
                break;
            case '21':
                x = (0.5007 * C) + (703.686 * 0.505) - 358.5641;
                break;
            case '22':
                x = (0.3135 * C) + (902.8845 * 0.30) - 285.855;
                break;
            case '23':
                x = (0.3396 * C) + (956.5228 * 0.329) - 326.4739;
                break;
            case '24':
                x = (0.3797 * C) + (857.5144 * 0.378) - 328.6899;
                break;
            case '25':
                x = (0.5007 * C) + (703.686 * 0.505) - 358.5641;
                break;
            case '31':
                x = (0.3524 * C) + (563.8412 * 0.42) - 196.8003;
                break;
            case '32':
                x = (0.1941 * C) + (671.9616 * 0.204) - 131.0749;
                break;
            case '33':
                x = (0.2432 * C) + (712.2978 * 0.263) - 177.29;
                break;
            case '34':
                x = (0.2965 * C) + (628.5916 * 0.34) - 189.2485;
                break;
            case '35':
                x = (0.3524 * C) + (563.8412 * 0.42) - 196.8003;
                break;
            case '41':
                x = (0.3445 * C) + (1315.1448 * 0.357) - 459.0464;
                break;
            case '42':
230
                x = (0.2003 * C) + (1421.0975 * 0.206) - 290.0477;
231
232
233
234
235
236
237
238
239
240
241
242
243
244
                break;
            case '43':
                x = (0.2289 * C) + (1389.9964 * 0.24) - 325.0492;
                break;
            case '44':
                x = (0.2842 * C) + (1471.1005 * 0.298) - 431.9652;
                break;
            case '45':
                x = (0.3445 * C) + (1315.1448 * 0.357) - 459.0464;
                break;
            default:
                x = 'error';
                break;
        }
245

246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
        // get modulo division of x for rounding off till 30 seconds
        let xMod60 = x % 60;
        if (xMod60 <= 15) {
            roundOff = 0;
        }
        if (xMod60 > 15 && xMod60 <= 30) {
            roundOff = 30;
        }
        if (xMod60 > 30 && xMod60 <= 45) {
            roundOff = 30;
        }
        if (xMod60 > 45) {
            roundOff = 60;
        }

        // subtract mod seconds and add rounded off seconds
        let roundedOffSeconds = x - xMod60 + roundOff;

        // get formatted time in hh:mm:ss format
        let formattedTime = getFormattedTime(roundedOffSeconds)

        // set time value to html element
268
        var s = document.getElementById('reading-time-element');
269
        s.innerHTML = formattedTime;
270
271
272
273
274
        // display html element which shows time
        let element = document.getElementById('calculate-time-element');
        element.style.display = "block";
    }
}
275

276
// function getFormattedTime
277
278
279
280
281
282
283
284
285
286
287
288
289
// accepts seconds value and returns in hh:mm:ss format
function getFormattedTime(totalSeconds) {
    let hours = Math.floor(totalSeconds / 3600);
    totalSeconds %= 3600;
    let minutes = Math.floor(totalSeconds / 60);
    let seconds = totalSeconds % 60;

    minutes = String(minutes).padStart(2, "0");
    hours = String(hours).padStart(2, "0");
    seconds = String(seconds).padStart(2, "0");

    return hours + ":" + minutes + ":" + seconds;
}