Browse Source

Do not highlight usernames inside links (#366)

sweet!

* Do not highlight usernames  inside words

Fixes #156

* Do not search on separate words

* Add accuracy options to markjs
master
Matt Steele 10 months ago
committed by GitHub
parent
commit
aeb221b32f
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 29714 additions and 19 deletions
  1. +2
    -0
      build/.gitignore
  2. +5
    -0
      build/javascript/package-lock.json
  3. +4
    -2
      build/javascript/package.json
  4. +41
    -15
      webroot/js/components/chat/chat-message-view.js
  5. +2
    -1
      webroot/js/web_modules/@videojs/http-streaming/dist/videojs-http-streaming.min.js
  6. +25
    -0
      webroot/js/web_modules/common/_commonjsHelpers-37fa8da4.js
  7. +29619
    -0
      webroot/js/web_modules/common/core-440932cf.js
  8. +1
    -0
      webroot/js/web_modules/import-map.json
  9. +13
    -0
      webroot/js/web_modules/markjs/dist/mark.es6.min.js
  10. +2
    -1
      webroot/js/web_modules/videojs/core.js

+ 2
- 0
build/.gitignore View File

@ -0,0 +1,2 @@
node_modules
web_modules

+ 5
- 0
build/javascript/package-lock.json View File

@ -1467,6 +1467,11 @@
"global": "^4.3.2"
}
},
"mark.js": {
"version": "8.11.1",
"resolved": "https://registry.npmjs.org/mark.js/-/mark.js-8.11.1.tgz",
"integrity": "sha1-GA8fnr74sOY45BZq1S24eb6y/8U="
},
"mdn-data": {
"version": "2.0.4",
"resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.4.tgz",


+ 4
- 2
build/javascript/package.json View File

@ -6,12 +6,13 @@
"dependencies": {
"@joeattardi/emoji-button": "^4.5.0",
"@justinribeiro/lite-youtube": "^0.9.1",
"@videojs/http-streaming": "2.3.0",
"@videojs/themes": "^1.0.1",
"htm": "^3.0.4",
"mark.js": "^8.11.1",
"preact": "^10.5.7",
"tailwindcss": "^1.9.6",
"video.js": "7.10.2",
"@videojs/http-streaming": "2.3.0"
"video.js": "7.10.2"
},
"devDependencies": {
"cssnano": "^4.1.10",
@ -27,6 +28,7 @@
"@justinribeiro/lite-youtube",
"htm",
"preact",
"mark.js/dist/mark.es6.min.js",
"tailwindcss/dist/tailwind.min.css"
],
"alias": {


+ 41
- 15
webroot/js/components/chat/chat-message-view.js View File

@ -1,5 +1,6 @@
import { h, Component } from '/js/web_modules/preact.js';
import htm from '/js/web_modules/htm.js';
import Mark from '/js/web_modules/markjs/dist/mark.es6.min.js';
const html = htm.bind(h);
import {
@ -10,11 +11,27 @@ import { convertToText } from '../../utils/chat.js';
import { SOCKET_MESSAGE_TYPES } from '../../utils/websocket.js';
export default class ChatMessageView extends Component {
render() {
async componentDidUpdate(prevProps) {
const { message, username } = this.props;
const { author, body, timestamp } = message;
if (prevProps.message === message && this.state.formattedMessage) {
return;
}
const { body } = message;
const formattedMessage = formatMessageText(body, username);
const formattedMessage = await formatMessageText(body, username);
this.setState({
formattedMessage
});
}
render() {
const { message } = this.props;
const { author, timestamp } = message;
const { formattedMessage } = this.state;
if (!formattedMessage) {
return;
}
const formattedTimestamp = formatTimestamp(timestamp);
const isSystemMessage = message.type === SOCKET_MESSAGE_TYPES.SYSTEM;
@ -60,21 +77,30 @@ function getChatMessageClassString() {
return 'message flex flex-row items-start p-3 m-3 rounded-lg shadow-s text-sm';
}
export function formatMessageText(message, username) {
let formattedText = highlightUsername(message, username);
formattedText = getMessageWithEmbeds(formattedText);
return convertToMarkup(formattedText);
export async function formatMessageText(message, username) {
let formattedText = getMessageWithEmbeds(message);
formattedText = convertToMarkup(formattedText);
return await highlightUsername(formattedText, username);
}
function highlightUsername(message, username) {
const pattern = new RegExp(
'@?' + username.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&'),
'gi'
);
return message.replace(
pattern,
'<span class="highlighted px-1 rounded font-bold bg-orange-500">$&</span>'
);
// https://github.com/julmot/mark.js/issues/115
const node = document.createElement('span');
node.innerHTML = message;
return new Promise(res => {
new Mark(node).mark(username, {
element: 'span',
className: 'highlighted px-1 rounded font-bold bg-orange-500',
separateWordSearch: false,
accuracy: {
value: 'exactly',
limiters: [",", ".", "'", '?', '@'],
},
done() {
res(node.innerHTML);
}
});
});
}
function getMessageWithEmbeds(message) {


+ 2
- 1
webroot/js/web_modules/@videojs/http-streaming/dist/videojs-http-streaming.min.js View File

@ -1,4 +1,5 @@
import { c as createCommonjsModule, g as getDefaultExportFromCjs, d as document_1, w as window_1, a as core, b as commonjsGlobal } from '../../../common/core-b8f2ee39.js';
import { c as createCommonjsModule, g as getDefaultExportFromCjs, a as commonjsGlobal } from '../../../common/_commonjsHelpers-37fa8da4.js';
import { d as document_1, w as window_1, c as core } from '../../../common/core-440932cf.js';
//[4] NameStartChar ::= ":" | [A-Z] | "_" | [a-z] | [#xC0-#xD6] | [#xD8-#xF6] | [#xF8-#x2FF] | [#x370-#x37D] | [#x37F-#x1FFF] | [#x200C-#x200D] | [#x2070-#x218F] | [#x2C00-#x2FEF] | [#x3001-#xD7FF] | [#xF900-#xFDCF] | [#xFDF0-#xFFFD] | [#x10000-#xEFFFF]
//[4a] NameChar ::= NameStartChar | "-" | "." | [0-9] | #xB7 | [#x0300-#x036F] | [#x203F-#x2040]


+ 25
- 0
webroot/js/web_modules/common/_commonjsHelpers-37fa8da4.js View File

@ -0,0 +1,25 @@
var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
function getDefaultExportFromCjs (x) {
return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x;
}
function createCommonjsModule(fn, basedir, module) {
return module = {
path: basedir,
exports: {},
require: function (path, base) {
return commonjsRequire(path, (base === undefined || base === null) ? module.path : base);
}
}, fn(module, module.exports), module.exports;
}
function getDefaultExportFromNamespaceIfNotNamed (n) {
return n && Object.prototype.hasOwnProperty.call(n, 'default') && Object.keys(n).length === 1 ? n['default'] : n;
}
function commonjsRequire () {
throw new Error('Dynamic requires are not currently supported by @rollup/plugin-commonjs');
}
export { commonjsGlobal as a, getDefaultExportFromNamespaceIfNotNamed as b, createCommonjsModule as c, getDefaultExportFromCjs as g };

+ 29619
- 0
webroot/js/web_modules/common/core-440932cf.js
File diff suppressed because it is too large
View File


+ 1
- 0
webroot/js/web_modules/import-map.json View File

@ -5,6 +5,7 @@
"@videojs/http-streaming/dist/videojs-http-streaming.min.js": "./@videojs/http-streaming/dist/videojs-http-streaming.min.js",
"@videojs/themes/fantasy/index.css": "./@videojs/themes/fantasy/index.css",
"htm": "./htm.js",
"mark.js/dist/mark.es6.min.js": "./markjs/dist/mark.es6.min.js",
"preact": "./preact.js",
"tailwindcss/dist/tailwind.min.css": "./tailwindcss/dist/tailwind.min.css",
"video.js": "./video.js/core.js",


+ 13
- 0
webroot/js/web_modules/markjs/dist/mark.es6.min.js
File diff suppressed because it is too large
View File


+ 2
- 1
webroot/js/web_modules/videojs/core.js View File

@ -1 +1,2 @@
export { a as default } from '../common/core-b8f2ee39.js';
import '../common/_commonjsHelpers-37fa8da4.js';
export { c as default } from '../common/core-440932cf.js';

Loading…
Cancel
Save