diff --git a/client/rivescript_macros.go b/client/rivescript_macros.go index 0233dd1..012e7b9 100644 --- a/client/rivescript_macros.go +++ b/client/rivescript_macros.go @@ -157,4 +157,27 @@ func (h *BotHandlers) setObjectMacros() { } return "" }) + + // Send a public chat message to a channel name. + h.rs.SetSubroutine("ban", func(rs *rivescript.RiveScript, args []string) string { + if len(args) >= 1 { + var ( + username = args[0] + duration = "24" + ) + if len(args) > 1 { + duration = args[1] + } + + log.Error("Macro: /ban %s %s", username, duration) + h.client.Send(messages.Message{ + Action: messages.ActionMessage, + Channel: "barertc-debug", + Message: fmt.Sprintf("/ban %s %s", username, duration), + }) + } else { + return "[ban: invalid number of parameters]" + } + return "" + }) } diff --git a/src/components/VideoFeed.vue b/src/components/VideoFeed.vue index 339a20c..9dc7abe 100644 --- a/src/components/VideoFeed.vue +++ b/src/components/VideoFeed.vue @@ -147,16 +147,47 @@ export default { // Mutation Observer to detect if the watermark is tampered with by the viewer. initWatermarkObserver() { const $container = this.$refs.videoContainer, + $layer = this.$refs.watermarkLayer, $watermark = this.$refs.watermarkImage, $smallImage = this.$refs.watermarkSmallImage; if (!$container || !$watermark || !$smallImage) return; + // Helper function to check CSS properties that may hide the element visually without deleting it from the page. + const isInvisible = (elem) => { + let style = window.getComputedStyle(elem); + return style.display === "none" || style.visibility === "hidden" || parseFloat(style.opacity) < 0.02; + }; + const isImageMissing = (elem) => { + try { + let src = elem.src; + if (src.indexOf("data:image/svg") !== 0) { + return true; + } + } catch (e) { + console.error("isImageMissing", elem, e); + } + return false; + } + this.observer = new MutationObserver(() => { - const stillPresent = $container.contains($watermark) && $container.contains($smallImage); + const stillPresent = $container.contains($layer) && $container.contains($watermark) && $container.contains($smallImage); if (!stillPresent) { this.onWatermarkRemoved(); } + + // Check for CSS hacking: this looks at the computed style, so only check if the top-level VideoFeed is not hidden. + try { + if ($container.style.display !== "none") { + if (isInvisible($watermark) || isInvisible($smallImage) || isInvisible($layer)) { + this.onWatermarkRemoved(); + } else if (isImageMissing($watermark) || isImageMissing($smallImage)) { + this.onWatermarkRemoved(); + } + } + } catch(e) { + console.error("checking container:", e); + } }); this.observer.observe($container, { @@ -185,7 +216,7 @@ export default { :muted="localVideo"> -