import macros, karax, vdom from strutils import startsWith, toLowerAscii const StmtContext = ["kout", "inc", "echo", "dec", "!"] proc getName(n: NimNode): string = case n.kind of nnkIdent: result = $n.ident of nnkAccQuoted: result = "" for i in 0.. 0: result[L-1] = tcall2(result[L-1], tmpContext) of nnkStmtList, nnkStmtListExpr, nnkWhenStmt, nnkIfStmt, nnkCaseStmt, nnkTryStmt, nnkFinally: # recurse for every child: result = copyNimNode(n) for x in n: result.add tcall2(x, tmpContext) of nnkVarSection, nnkLetSection, nnkConstSection: result = n of nnkCallKinds: let op = getName(n[0]) if isTag(op): let tmp = genSym(nskLet, "tmp") result = newTree( if tmpContext == nil: nnkStmtListExpr else: nnkStmtList, newLetStmt(tmp, newCall(bindSym"tree", newDotExpr(bindSym"VNodeKind", n[0])))) for i in 1 ..< n.len: # named parameters are transformed into attributes or events: let x = n[i] if x.kind == nnkExprEqExpr: let key = getName x[0] if key.startsWith("on"): result.add newCall(!("set" & key), tmp, x[1]) elif key == "id" or key == "class" or key == "value": result.add newDotAsgn(tmp, key, x[1]) else: result.add newCall(bindSym"setAttr", tmp, newLit(key), x[1]) elif x.kind == nnkIdent: result.add newCall(x, tmp) else: result.add tcall2(x, tmp) if tmpContext == nil: result.add tmp else: result.add newCall(bindSym"add", tmpContext, tmp) elif tmpContext != nil and op notin StmtContext: result = newCall(bindSym"add", tmpContext, n) elif op == "!" and n.len == 2: result = n[1] else: result = n else: result = n macro buildHtml*(tag, children: untyped): VNode = expectKind children, nnkDo var call: NimNode if tag.kind in nnkCallKinds: call = tag else: call = newCall(tag) call.add body(children) result = tcall2(call, nil) when defined(debugKaraxDsl): echo repr result macro buildHtml*(children: untyped): VNode = expectKind children, nnkDo result = tcall2(body(children), nil) when defined(debugKaraxDsl): echo repr result