From 6c66b7c72013f8e335d93b28e743101883f30bb9 Mon Sep 17 00:00:00 2001 From: Mistivia Date: Tue, 4 Nov 2025 22:34:33 +0800 Subject: add scroll to log line --- irclog/search/index.html | 18 ++++- irclog/search/search.js | 112 ------------------------------ irclog/search/search1.js | 119 ++++++++++++++++++++++++++++++++ irclog/view/index.html | 2 +- irclog/view/view1.js | 151 ---------------------------------------- irclog/view/view4.js | 174 +++++++++++++++++++++++++++++++++++++++++++++++ 6 files changed, 311 insertions(+), 265 deletions(-) delete mode 100644 irclog/search/search.js create mode 100644 irclog/search/search1.js delete mode 100644 irclog/view/view1.js create mode 100644 irclog/view/view4.js diff --git a/irclog/search/index.html b/irclog/search/index.html index 066b30d..a31414b 100644 --- a/irclog/search/index.html +++ b/irclog/search/index.html @@ -45,6 +45,22 @@ color: blue; text-decoration: underline; } + .logline { + color: black; + text-decoration: none; + } + .logline:link { + color: black; + text-decoration: none; + } + .logline:hover { + color: black; + text-decoration: underline; + } + .logline:visited { + color: black; + text-decoration: none; + } @@ -57,6 +73,6 @@
- + diff --git a/irclog/search/search.js b/irclog/search/search.js deleted file mode 100644 index 9a574d6..0000000 --- a/irclog/search/search.js +++ /dev/null @@ -1,112 +0,0 @@ -const logContainer = document.getElementById('log-container'); -const queryInput = document.getElementById('query'); - -const queryString = window.location.search; -const urlParams = new URLSearchParams(queryString); -let query = urlParams.get('q'); -if (query === null) { - query = ''; -} else { - queryInput.value = query.trim(); -} - -logContainer.innerHTML = ''; - -function escapeHtml(unsafe) { - if (!unsafe) return ''; - return unsafe - .replace(/&/g, "&") - .replace(//g, ">") - .replace(/"/g, """) - .replace(/'/g, "'"); -} - -function ircAction(text) { - const regex = - /^(\[[^\]]+\])(\s*<)([^>]+)(>:\s*)(\u0001ACTION\s+)([^\u0001]+)(\u0001)(.*)$/gm; - const replacement = '$1 * $3 $6$8'; - return text.replace(regex, replacement); -} - -function linkify(text) { - const urlRegex = /(\b(https?):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig; - return text.replace(urlRegex, function(url) { - return `${url}`; - }); -} - -function aggrLog(data) { - const logsByDate = {}; - const lines = data.trim().split('\n'); - - lines.forEach(line => { - const match = line.match(/^\.\/(\d{4}\/\d{2}-\d{2})\.txt:(.*)/); - if (match) { - const fullDate = match[1].replace('/', '-'); - const logContent = match[2].trim(); - if (!logsByDate[fullDate]) { - logsByDate[fullDate] = []; - } - logsByDate[fullDate].push(logContent); - } - }); - const dates = Object.keys(logsByDate); - const sortedDates = dates.sort().reverse(); - let ret = ''; - sortedDates.forEach(date => { - year = date.substring(0, 4); - month = date.substring(5, 7); - day = date.substring(8, 10); - url = '../view/?chan=main&y=' + year + '&m=' + month + '&d=' + day; - ret = ret + '\n=== ' + date + ' ===' + '\n'; - logsByDate[date].forEach(log => { - ret = ret + log + '\n'; - }); - }); - return ret; -} - -function logProcess(text) { - text = ircAction(text); - text = escapeHtml(text); - text = aggrLog(text); - text = linkify(text); - return text; -} - -function loadLog() { - if (query === '') return; - let targetUrl = 'https://raye.mistivia.com/cgi-bin/irclogsearch/?' + encodeURIComponent(query); - fetch(targetUrl) - .then(response => { - if (!response.ok) { - throw new Error(`HTTP Error: ${response.status} ${response.statusText} for hash: ${urlHash}`); - } - return response.text(); - }) - .then(text => { - logContainer.innerHTML = `
${logProcess(text.trim())}
`; - }) - .catch(error => { - console.error('Fetch error:', error); - logContainer.innerHTML = ''; - }); -} - -loadLog(); - -function search() { - query = queryInput.value.trim(); - window.history.replaceState(null, '', window.location.origin + window.location.pathname + '?q=' + encodeURIComponent(query)); - loadLog(); -} - -function handleEnter(event) { - if (event.key === 'Enter' || event.keyCode === 13) { - event.preventDefault(); - search(); - } -} - -queryInput.addEventListener('keyup', handleEnter); \ No newline at end of file diff --git a/irclog/search/search1.js b/irclog/search/search1.js new file mode 100644 index 0000000..cf59f90 --- /dev/null +++ b/irclog/search/search1.js @@ -0,0 +1,119 @@ +const logContainer = document.getElementById('log-container'); +const queryInput = document.getElementById('query'); + +const queryString = window.location.search; +const urlParams = new URLSearchParams(queryString); +let query = urlParams.get('q'); +if (query === null) { + query = ''; +} else { + queryInput.value = query.trim(); +} + +logContainer.innerHTML = ''; + +function escapeHtml(unsafe) { + if (!unsafe) return ''; + return unsafe + .replace(/&/g, "&") + .replace(//g, ">") + .replace(/"/g, """) + .replace(/'/g, "'"); +} + +function ircAction(text) { + const regex = + /^(\[[^\]]+\])(\s*<)([^>]+)(>:\s*)(\u0001ACTION\s+)([^\u0001]+)(\u0001)(.*)$/gm; + const replacement = '$1 * $3 $6$8'; + return text.replace(regex, replacement); +} + +function linkify(text) { + const urlRegex = /(\b(https?):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig; + return text.replace(urlRegex, function(url) { + return `${url}`; + }); +} + +function aggrLog(data) { + const logsByDate = {}; + const lines = data.trim().split('\n'); + + lines.forEach(line => { + const match = line.match(/^\.\/(\d{4}\/\d{2}-\d{2})\.txt:(.*)/); + if (match) { + const fullDate = match[1].replace('/', '-'); + const logContent = match[2].trim(); + if (!logsByDate[fullDate]) { + logsByDate[fullDate] = []; + } + logsByDate[fullDate].push(logContent); + } + }); + const dates = Object.keys(logsByDate); + const sortedDates = dates.sort().reverse(); + let ret = ''; + sortedDates.forEach(date => { + year = date.substring(0, 4); + month = date.substring(5, 7); + day = date.substring(8, 10); + url = '../view/?chan=main&y=' + year + '&m=' + month + '&d=' + day; + ret = ret + '\n=== ' + date + ' ===' + '\n'; + logsByDate[date].forEach(log => { + let time = log.substring(1,9); + let logurl = url + '#' + time; + ret = ret + '' + log + '\n'; + }); + }); + return ret; +} + +function logProcess(text) { + text = ircAction(text); + text = escapeHtml(text); + text = aggrLog(text); + text = linkify(text); + return text; +} + +function loadLog() { + if (query === '') return; + let targetUrl = 'https://raye.mistivia.com/cgi-bin/irclogsearch/?' + encodeURIComponent(query); + fetch(targetUrl) + .then(response => { + if (!response.ok) { + throw new Error(`HTTP Error: ${response.status} ${response.statusText} for hash: ${urlHash}`); + } + return response.text(); + }) + .then(text => { + try { + logContainer.innerHTML = `
${logProcess(text.trim())}
`; + } catch (e) { + console.log(e); + } + + }) + .catch(error => { + console.error('Fetch error:', error); + logContainer.innerHTML = ''; + }); +} + +loadLog(); + +function search() { + query = queryInput.value.trim(); + window.history.replaceState(null, '', window.location.origin + window.location.pathname + '?q=' + encodeURIComponent(query)); + loadLog(); +} + +function handleEnter(event) { + if (event.key === 'Enter' || event.keyCode === 13) { + event.preventDefault(); + search(); + } +} + +queryInput.addEventListener('keyup', handleEnter); \ No newline at end of file diff --git a/irclog/view/index.html b/irclog/view/index.html index 3041286..490e9c3 100644 --- a/irclog/view/index.html +++ b/irclog/view/index.html @@ -57,6 +57,6 @@
- + diff --git a/irclog/view/view1.js b/irclog/view/view1.js deleted file mode 100644 index 567ec23..0000000 --- a/irclog/view/view1.js +++ /dev/null @@ -1,151 +0,0 @@ -const logContainer = document.getElementById('log-container'); -const dateInput = document.getElementById('log-date'); - -const queryString = window.location.search; -const urlParams = new URLSearchParams(queryString); -let chan = urlParams.get('chan'); -let year = urlParams.get('y'); -let month = urlParams.get('m'); -let day = urlParams.get('d'); - -if (chan === 'main') { - document.getElementById('searchlink').style.visibility = 'visible'; -} - -function getDate(year, month, day) { - try { - year = parseInt(year, 10); - month = parseInt(month, 10); - day = parseInt(day, 10); - if (isNaN(year) || isNaN(month) || isNaN(day)) { - throw new Error("date is NaN"); - } - return new Date(year, month - 1, day); - } catch (e) { - console.log(e); - const now = new Date(); - const y = now.toLocaleString('en-US', { timeZone: 'Asia/Shanghai', year: 'numeric' }); - const m = now.toLocaleString('en-US', { timeZone: 'Asia/Shanghai', month: 'numeric' }); - const d = now.toLocaleString('en-US', { timeZone: 'Asia/Shanghai', day: 'numeric' }); - return getDate(y, m, d); - } -} - -function formatDate(date) { - const year = date.getFullYear(); - const month = String(date.getMonth() + 1).padStart(2, '0'); - const day = String(date.getDate()).padStart(2, '0'); - return `${year}-${month}-${day}`; -} - -function setDateState(date) { - year = date.getFullYear(); - month = String(date.getMonth() + 1).padStart(2, '0'); - day = String(date.getDate()).padStart(2, '0'); - dateInput.value = formatDate(getDate(year, month, day)); - window.history.replaceState(null, '', window.location.origin + window.location.pathname + - '?chan=' + chan + - '&y=' + year + - '&m=' + month + - '&d=' + day); -} - -setDateState(getDate(year, month, day)); - -logContainer.innerHTML = ''; - -function escapeHtml(unsafe) { - if (!unsafe) return ''; - return unsafe - .replace(/&/g, "&") - .replace(//g, ">") - .replace(/"/g, """) - .replace(/'/g, "'"); -} - -function ircAction(text) { - const regex = - /^(\[[^\]]+\])(\s*<)([^>]+)(>:\s*)(\u0001ACTION\s+)([^\u0001]+)(\u0001)(.*)$/gm; - const replacement = '$1 * $3 $6$8'; - return text.replace(regex, replacement); -} - -function linkify(text) { - const urlRegex = /(\b(https?):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig; - return text.replace(urlRegex, function(url) { - return `${url}`; - }); -} - -function logProcess(text) { - text = ircAction(text); - text = escapeHtml(text); - text = linkify(text); - return text; -} - -function loadLog() { - let targetUrl = 'https://raye.mistivia.com/irclog/%23' + chan + '/' + year + '/' + month + '-' + day + '.txt'; - fetch(targetUrl) - .then(response => { - if (!response.ok) { - throw new Error(`HTTP Error: ${response.status} ${response.statusText} for hash: ${urlHash}`); - } - return response.text(); - }) - .then(text => { - logContainer.innerHTML = `
${logProcess(text)}
`; - }) - .catch(error => { - console.error('Fetch error:', error); - logContainer.innerHTML = ''; - }); -} - -loadLog(); - -function onDateChange() { - var dateInput = this; - var dateValue = dateInput.value; - - if (dateValue && chan) { - var dateParts = dateValue.split('-'); - var year = dateParts[0]; - var month = dateParts[1]; - var day = dateParts[2]; - let date = getDate(year, month, day); - setDateState(date); - loadLog(); - } -} - -document.getElementById("log-date").addEventListener('change', onDateChange, false); - -function changeDate(days) { - let currentDate = getDate(year, month, day); - const currentDay = currentDate.getDate(); - currentDate.setDate(currentDay + days); - setDateState(currentDate); - dateInput.dispatchEvent(new Event('change')); -} - -function setPreviousDay() { - changeDate(-1); - window.scrollTo(0, 0); -} - -function setNextDay() { - changeDate(1); - window.scrollTo(0, 0); -} - -function setToday() { - let date = getDate('', '', ''); - setDateState(date); - dateInput.dispatchEvent(new Event('change')); -} - -function gotosearch() { - window.open('../search/', '_blank'); -} \ No newline at end of file diff --git a/irclog/view/view4.js b/irclog/view/view4.js new file mode 100644 index 0000000..1863f64 --- /dev/null +++ b/irclog/view/view4.js @@ -0,0 +1,174 @@ +const logContainer = document.getElementById('log-container'); +const dateInput = document.getElementById('log-date'); + +const queryString = window.location.search; +const urlParams = new URLSearchParams(queryString); +let chan = urlParams.get('chan'); +let year = urlParams.get('y'); +let month = urlParams.get('m'); +let day = urlParams.get('d'); +let hashtag = window.location.hash.substring(1); + +if (chan === 'main') { + document.getElementById('searchlink').style.visibility = 'visible'; +} + +function getDate(year, month, day) { + try { + year = parseInt(year, 10); + month = parseInt(month, 10); + day = parseInt(day, 10); + if (isNaN(year) || isNaN(month) || isNaN(day)) { + throw new Error("date is NaN"); + } + return new Date(year, month - 1, day); + } catch (e) { + console.log(e); + const now = new Date(); + const y = now.toLocaleString('en-US', { timeZone: 'Asia/Shanghai', year: 'numeric' }); + const m = now.toLocaleString('en-US', { timeZone: 'Asia/Shanghai', month: 'numeric' }); + const d = now.toLocaleString('en-US', { timeZone: 'Asia/Shanghai', day: 'numeric' }); + return getDate(y, m, d); + } +} + +function formatDate(date) { + const year = date.getFullYear(); + const month = String(date.getMonth() + 1).padStart(2, '0'); + const day = String(date.getDate()).padStart(2, '0'); + return `${year}-${month}-${day}`; +} + +function setDateState(date) { + year = date.getFullYear(); + month = String(date.getMonth() + 1).padStart(2, '0'); + day = String(date.getDate()).padStart(2, '0'); + dateInput.value = formatDate(getDate(year, month, day)); + window.history.replaceState(null, '', window.location.origin + window.location.pathname + + '?chan=' + chan + + '&y=' + year + + '&m=' + month + + '&d=' + day); +} + +setDateState(getDate(year, month, day)); + +logContainer.innerHTML = ''; + +function escapeHtml(unsafe) { + if (!unsafe) return ''; + return unsafe + .replace(/&/g, "&") + .replace(//g, ">") + .replace(/"/g, """) + .replace(/'/g, "'"); +} + +function ircAction(text) { + const regex = + /^(\[[^\]]+\])(\s*<)([^>]+)(>:\s*)(\u0001ACTION\s+)([^\u0001]+)(\u0001)(.*)$/gm; + const replacement = '$1 * $3 $6$8'; + return text.replace(regex, replacement); +} + +function linkify(text) { + const urlRegex = /(\b(https?):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig; + return text.replace(urlRegex, function(url) { + return `${url}`; + }); +} + +function insertTag(text) { + let res = ''; + let lines = text.split('\n'); + let scrollToInserted = false; + for (let line of lines) { + let time = line.substring(1, 9); + if (!scrollToInserted && time == hashtag && time !== '') { + res += ''; + scrollToInserted = true; + res += '' + line + '\n'; + } else { + res += line + '\n'; + } + } + return res; +} + +function logProcess(text) { + text = ircAction(text); + text = escapeHtml(text); + text = linkify(text); + text = insertTag(text); + return text; +} + +function loadLog() { + let targetUrl = 'https://raye.mistivia.com/irclog/%23' + chan + '/' + year + '/' + month + '-' + day + '.txt'; + fetch(targetUrl) + .then(response => { + if (!response.ok) { + throw new Error(`HTTP Error: ${response.status} ${response.statusText} for hash: ${urlHash}`); + } + return response.text(); + }) + .then(text => { + logContainer.innerHTML = `
${logProcess(text)}
`; + let scrollTo = document.getElementById('scrollTo'); + if (scrollTo) { + scrollTo.scrollIntoView(); + } + }) + .catch(error => { + console.error('Fetch error:', error); + logContainer.innerHTML = ''; + }); +} + +loadLog(); + +function onDateChange() { + var dateInput = this; + var dateValue = dateInput.value; + + if (dateValue && chan) { + var dateParts = dateValue.split('-'); + var year = dateParts[0]; + var month = dateParts[1]; + var day = dateParts[2]; + let date = getDate(year, month, day); + setDateState(date); + loadLog(); + } +} + +document.getElementById("log-date").addEventListener('change', onDateChange, false); + +function changeDate(days) { + let currentDate = getDate(year, month, day); + const currentDay = currentDate.getDate(); + currentDate.setDate(currentDay + days); + setDateState(currentDate); + dateInput.dispatchEvent(new Event('change')); +} + +function setPreviousDay() { + changeDate(-1); + window.scrollTo(0, 0); +} + +function setNextDay() { + changeDate(1); + window.scrollTo(0, 0); +} + +function setToday() { + let date = getDate('', '', ''); + setDateState(date); + dateInput.dispatchEvent(new Event('change')); +} + +function gotosearch() { + window.open('../search/', '_blank'); +} \ No newline at end of file -- cgit v1.0