33 lines
715 B
Vue
33 lines
715 B
Vue
|
|
<template>
|
||
|
|
<code ref="codeBlock" :class="languageClass">{{ code }}</code>
|
||
|
|
</template>
|
||
|
|
|
||
|
|
<script setup lang="ts">
|
||
|
|
import { ref, onMounted, watch, nextTick } from 'vue'
|
||
|
|
import hljs from 'highlight.js'
|
||
|
|
|
||
|
|
const props = defineProps<{
|
||
|
|
code: string
|
||
|
|
language: string
|
||
|
|
}>()
|
||
|
|
|
||
|
|
const codeBlock = ref<HTMLElement | null>(null)
|
||
|
|
|
||
|
|
const languageClass = `language-${props.language || 'plaintext'}`
|
||
|
|
|
||
|
|
const highlight = () => {
|
||
|
|
if (codeBlock.value) {
|
||
|
|
// Reset internal state if needed, though highlighting overwrites innerHTML
|
||
|
|
delete codeBlock.value.dataset.highlighted
|
||
|
|
hljs.highlightElement(codeBlock.value)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
onMounted(() => {
|
||
|
|
highlight()
|
||
|
|
})
|
||
|
|
|
||
|
|
watch(() => props.code, () => {
|
||
|
|
nextTick(highlight)
|
||
|
|
})
|
||
|
|
</script>
|