varabyte / kobweb-intellij-plugin Goto Github PK
View Code? Open in Web Editor NEWAn official IntelliJ IDE plugin to include Kobweb-specific enhancements and understanding to your project
License: Apache License 2.0
An official IntelliJ IDE plugin to include Kobweb-specific enhancements and understanding to your project
License: Apache License 2.0
See the important note in this section: https://github.com/varabyte/kobweb?tab=readme-ov-file#componentstyle
In other words, detect this case:
private val SomeStyle by ComponenStyle
then put a warning on the "private" keyword and add two actions the user can take
@Suppress("PRIVATE_COMPONENT_STYLE")
private val SomeCustomStyle by ComponentStyle { /* ... */ }
@InitSilk
fun registerPrivateStyle(ctx: InitSilkContext) {
ctx.theme.registerComponentStyle(SomeCustomStyle)
}
Once set, they should be able to issue kobweb commands from the IDE via UI.
The plugin currently still uses the default template icon
For example, if you have something like this:
and you click on the red square, it brings up a color picker. Right now, we're ignoring the request to update the color if the user picks one.
The code to handle this would go in KobwebColorProvider::setColorTo
, which is currently stubbed.
We're not always in a situation where we can change the color, but we might try to update things when we can. It could be pretty cool to write val x = Color.rgb(0, 0, 0)
and then use the color picker to figure out the correct value we want.
We should support all the Kobweb color functions, specifically here: https://github.com/varabyte/kobweb/blob/14e9ccffb889907cb3ee9d94a0c3e90c3d33db74/frontend/kobweb-compose/src/jsMain/kotlin/com/varabyte/kobweb/compose/ui/graphics/Color.kt#L221
For example, ctx.router.navigateTo("a/b/c/mispeled")
, or Link("stale-route-that-got-removed-but-I-forgot-about-this-link")
These would allow you to add modules to an existing project, which is something you can't currently accomplish with kobweb create
Live templates autocomplete code AND, if relevant, prompt users to fill out variable names before the completion is considered done.
We'll use VAR to represent things that should be filled out by the user and "$" to represent the cursor position when done.
For now we'll collect everything here because there probably aren't that many Kobweb concepts but we could break this up into multiple bugs if that's better.
Actual live template shortcut names are open for debate!
val VAR by ComponentStyle {
base { Modifier.$ }
}
val VAR by ComponentStyle.base {
Modifier.$
}
@Page
@Composable
fun VAR() {
$
}
val worker = rememberWorker {
VAR { output ->
$
}
}
@InitSilk
fun VAR(ctx: InitSilkContext) {
$
}
@InitKobweb
fun VAR(ctx: InitKobwebContext) {
$
}
@Api
fun VAR(ctx: ApiContext) {
$
}
@InitApi
fun VAR(ctx: InitApiContext) {
$
}
val VAR = object : ApiStream {
override suspend fun onTextReceived(ctx: TextReceivedContext) {
$
}
}
val VAR = ApiStream { ctx ->
$
}
A common mistake, especially for beginners but not necessarily:
val SomeStyle by ComponentStyle {
Modifier.size(...)
}
This compiles but does nothing. It should be:
val SomeStyle by ComponentStyle {
base { Modifier.size(...) }
}
or
val SomeStyle by ComponentStyle.base {
Modifier.size(...)
}
The devil is probably in the details here, but like #2 , we could support taking some html snipping and generating Kobweb code for it.
Caution
This sounds very complicated and is probably not worth prioritizing for a while!
See also: https://plugins.jetbrains.com/plugin/12205-html-to-kotlinx-html
// pages/SomeSlug.kt
@Page("some-slug")
☝️ Should be @Page
// pages/someRoute
@file:PackageMapping("some-route")
☝️ File should be deleted.
// pages/SomeSlug.kt
@Page("{some-slug}")
☝️ Should be @Page("{}")
// pages/someRoute
@file:PackageMapping("{some-route}")
☝️ Should be @file:PackageMapping("{}")
See also: https://opletter.github.io/css2kobweb/
Instead of having people open a website, it could be nice to just have the ability to paste / convert CSS code inside of the IDE plugin.
This will require a bunch of tagging in Kobweb with links to the source mozilla sites, but it might be nice to open a playground within your IDE to those CSS properties.
/**
* ...
* @see <a href="https://mozilla.com/...">...</a>
*/
fun Modifier.font(...)
results in an action which opens a floating web page inside your IDE that goes to the linked mozilla page. (Basically, search every header doc for each function call and search for a mozilla link in there)
We could support opening the page both with a quick action but ALSO with a gutter action too. That could be a really nice experience for bridging Kotlin and CSS.
Specifically, com.varabyte.kobweb.compose.ui.graphics.Color.Rgb
and com.varabyte.kobweb.compose.ui.graphics.Color.Hsl
types.
The driving idea here is, if I have my cursor on a Silk Button
, can I quickly surface all relevant styles, variants, and stylevars? (Basically, the plugin would need to analyze its code and find all nested symbols which are one of those things, which it can share in a popup somewhere, probably in the quickdoc window)
A sidebar tool which shows all Silk widgets, and clicking on one will let users create code where the cursor is.
Caution
This sounds very difficult and we may not want to prioritize early on.
// Before
val worker = remember { SomeWorker() }
// After
val worker = rememberWorker { SomeWorker() }
Also offer to automatically migrate the method call.
This might not be necessary since users can run kobweb create app
(or app/empty
) themselves.
// Valid
val SomeStyle by ComponentStyle { ... }
// Invalid
class Sneaky {
val SomeStyle by ComponentStyle { ... }
}
More?
Like the Android Studio preview, which lets you see code rendered without having to actually run your application, especially with the help of @Preview
annotations.
Caution
This is VERY DIFFICULT and should probably not be prioritized for a while.
See also: https://developer.android.com/jetpack/compose/tooling/previews
Probably some way to ask the current file context something like this:
enum class KobwebModuleType {
APPLICATION,
LIBRARY,
WORKER;
}
// WORKER modules don't have access to the UI so many Kobweb actions / inspections are not relevant there
fun KobwebModuleType.isFramework() = this == APPLICATION || this == LIBRARY
fun Module.findKobwebType(): KobwebModuleType() = { /* how do we do this? */ }
// Later, say in UnusedInspectionSuppressor
someContext.module.findKobwebType()?.isFramework() ?: return // Early abort
// Before
Widget(Modifier.styleA().styleB().styleC().attrA())
// After
val SomeStyle by ComponentStyle.base(extraModifiers = { Modifier.attrA() }) {
Modifer.styleA().styleB().styleC()
}
Widget(SomeStyle.toModifier())
An action to convert between this:
val SomeStyle by ComponentStyle {
base { Modifier.size(...) }
}
and this:
val SomeStyle by ComponentStyle.base {
Modifier.size(...)
}
The action would show up if you put your cursor on the "base" word and hit alt-enter.
Note that the context action should NOT show up for this case:
val SomeStyle by ComponentStyle {
base { Modifier.size(...) }
hover { Modifier.whatever() }
}
Can we discover those versions from the project's Gradle model? Worst case, we can parse libs.versions.toml
directly, but that's more fragile. What if a user isn't using version catalogs?
It is important to figure this out soon, so that new code that goes in will see a precedent that they should be using tests.
Warn if a user is using an attribute modifer within a component style (and offer assistance to extract it to the extraModifiers parameter)
// Before
val SomeStyle by ComponentStyle.base {
Modifier.id("id").size(...)
^^
"id" is an attribute modifier and not valid inside a ComponentStyle, which can only reference style modifiers
}
// After refactoring
val SomeStyle by ComponentStyle.base(extraModifiers = { Modifier.id("id") }) {
Modifier.size(...)
}
Also support alt base syntax:
// Before
val SomeStyle by ComponentStyle {
base { Modifier.id("id") }
}
// After refactoring
val SomeStyle by ComponentStyle(extraModifiers = { Modifier.id("id") }) {
base { Modifier.size(...) }
}
For attribute modifiers that AREN'T in the base block, do NOT offer to refactor. Just show the warning.
val SomeStyle by ComponentStyle {
hover { Modifier.id("id").size(...) }
^^
}
// Third party library
val SomeStyle by CssStyle
// App
fun initSilk(ctx) {
ctx.modifyStyle(SomeStyle) {
...
}
}
Div(SomeStyle.toModifier(...))
Putting the cursor on "SomeStyle" and navigating should offer you a popup both to the main SomeStyle declaration and also the modifyStyle line.
This is apparently a feature provided by AS?
// Before
Modifier.a().b().c()
// After
Modifier
.a()
.b()
.c()
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.