diff options
Diffstat (limited to 'core/src/main/kotlin/renderers/DefaultRenderer.kt')
-rw-r--r-- | core/src/main/kotlin/renderers/DefaultRenderer.kt | 71 |
1 files changed, 47 insertions, 24 deletions
diff --git a/core/src/main/kotlin/renderers/DefaultRenderer.kt b/core/src/main/kotlin/renderers/DefaultRenderer.kt index 5e3eadbe..606eea54 100644 --- a/core/src/main/kotlin/renderers/DefaultRenderer.kt +++ b/core/src/main/kotlin/renderers/DefaultRenderer.kt @@ -5,55 +5,62 @@ import org.jetbrains.dokka.pages.* import org.jetbrains.dokka.plugability.DokkaContext import org.jetbrains.dokka.plugability.single import org.jetbrains.dokka.resolvers.LocationProvider +import org.jetbrains.dokka.transformers.pages.PageNodeTransformer abstract class DefaultRenderer<T>( protected val outputWriter: OutputWriter, protected val context: DokkaContext ) : Renderer { + private val extension = context.single(CoreExtensions.fileExtension) + protected lateinit var locationProvider: LocationProvider private set + protected open val preprocessors: Iterable<PageNodeTransformer> = emptyList() + protected abstract fun T.buildHeader(level: Int, content: T.() -> Unit) protected abstract fun T.buildLink(address: String, content: T.() -> Unit) - protected abstract fun T.buildList(node: ContentList, pageContext: PageNode) + protected abstract fun T.buildList(node: ContentList, pageContext: ContentPage) protected abstract fun T.buildNewLine() - protected abstract fun T.buildResource(node: ContentEmbeddedResource, pageContext: PageNode) - protected abstract fun T.buildTable(node: ContentTable, pageContext: PageNode) + protected abstract fun T.buildResource(node: ContentEmbeddedResource, pageContext: ContentPage) + protected abstract fun T.buildTable(node: ContentTable, pageContext: ContentPage) protected abstract fun T.buildText(textNode: ContentText) protected abstract fun T.buildNavigation(page: PageNode) - protected abstract fun buildPage(page: PageNode, content: (T, PageNode) -> Unit): String + protected abstract fun buildPage(page: ContentPage, content: (T, ContentPage) -> Unit): String protected abstract fun buildError(node: ContentNode) - protected open fun T.buildGroup(node: ContentGroup, pageContext: PageNode){ + protected open fun T.buildGroup(node: ContentGroup, pageContext: ContentPage) { node.children.forEach { it.build(this, pageContext) } } - protected open fun T.buildLinkText(nodes: List<ContentNode>, pageContext: PageNode) { + protected open fun T.buildLinkText(nodes: List<ContentNode>, pageContext: ContentPage) { nodes.forEach { it.build(this, pageContext) } } - protected open fun T.buildCode(code: List<ContentNode>, language: String, pageContext: PageNode) { + protected open fun T.buildCode(code: List<ContentNode>, language: String, pageContext: ContentPage) { code.forEach { it.build(this, pageContext) } } - protected open fun T.buildHeader(node: ContentHeader, pageContext: PageNode) { + protected open fun T.buildHeader(node: ContentHeader, pageContext: ContentPage) { buildHeader(node.level) { node.children.forEach { it.build(this, pageContext) } } } - protected open fun ContentNode.build(builder: T, pageContext: PageNode) = builder.buildContentNode(this, pageContext) + protected open fun ContentNode.build(builder: T, pageContext: ContentPage) = + builder.buildContentNode(this, pageContext) - protected open fun T.buildContentNode(node: ContentNode, pageContext: PageNode) { + protected open fun T.buildContentNode(node: ContentNode, pageContext: ContentPage) { when (node) { is ContentText -> buildText(node) is ContentHeader -> buildHeader(node, pageContext) is ContentCode -> buildCode(node.children, node.language, pageContext) is ContentDRILink -> buildLink( - locationProvider.resolve(node.address, node.platforms.toList(), pageContext)) { + locationProvider.resolve(node.address, node.platforms.toList(), pageContext) + ) { buildLinkText(node.children, pageContext) } - is ContentResolvedLink -> buildLink(node.address) {buildLinkText(node.children, pageContext)} + is ContentResolvedLink -> buildLink(node.address) { buildLinkText(node.children, pageContext) } is ContentEmbeddedResource -> buildResource(node, pageContext) is ContentList -> buildList(node, pageContext) is ContentTable -> buildTable(node, pageContext) @@ -62,22 +69,34 @@ abstract class DefaultRenderer<T>( } } - protected open fun buildPageContent(context: T, page: PageNode) { + protected open fun buildPageContent(context: T, page: ContentPage) { context.buildNavigation(page) page.content.build(context, page) } - protected open fun renderPage(page: PageNode) = - outputWriter.write(locationProvider.resolve(page), buildPage(page, ::buildPageContent), "") + protected open fun renderPage(page: PageNode) { + val path by lazy { locationProvider.resolve(page, skipExtension = true) } + when (page) { + is ContentPage -> outputWriter.write(path, buildPage(page) { c, p -> buildPageContent(c, p) }, extension) + is RendererSpecificPage -> when (val strategy = page.strategy) { + is RenderingStrategy.Copy -> outputWriter.writeResources(strategy.from, path) + is RenderingStrategy.Write -> outputWriter.write(path, strategy.text, "") + is RenderingStrategy.Callback -> outputWriter.write(path, strategy.instructions(this, page)) + RenderingStrategy.DoNothing -> Unit + } + else -> throw AssertionError( + "Page ${page.name} cannot be rendered by renderer as it is not renderer specific nor contains content" + ) + } + } protected open fun renderPages(root: PageNode) { renderPage(root) root.children.forEach { renderPages(it) } } - protected open fun buildSupportFiles() {} - - protected open fun renderPackageList(root: PageNode) = + // reimplement this as preprocessor + protected open fun renderPackageList(root: ContentPage) = getPackageNamesAndPlatforms(root) .keys .joinToString("\n") @@ -93,12 +112,16 @@ abstract class DefaultRenderer<T>( emptyMap() } - override fun render(root: PageNode) { - locationProvider = context.single(CoreExtensions.locationProviderFactory).getLocationProvider(root as ModulePageNode) - renderPackageList(root) - buildSupportFiles() - renderPages(root) + override fun render(root: RootPageNode) { + val newRoot = preprocessors.fold(root) { acc, t -> t(acc) } + + locationProvider = + context.single(CoreExtensions.locationProviderFactory).getLocationProvider(newRoot) + + root.children<ModulePageNode>().forEach { renderPackageList(it) } + + renderPages(newRoot) } } -fun PageNode.platforms() = this.content.platforms.toList()
\ No newline at end of file +fun ContentPage.platforms() = this.content.platforms.toList()
\ No newline at end of file |