Binding 在Lift中将Scala绑定到HTML

Binding 在Lift中将Scala绑定到HTML,binding,lift,Binding,Lift,我已经开始玩升降机了。我想创建一个基本应用程序,它通过输入字段从用户处获取输入,对该输入执行db搜索,并获取db搜索的结果,创建一个对象列表,然后绑定到一些html代码 我只需要关于绑定部分的帮助,但首先需要一些背景信息 我有一个列表[节点]: case类节点(aname:String,adata:String){..} 我要将此html绑定到: <div class="lift:helloWorld.displayNodes"> <div>

我已经开始玩升降机了。我想创建一个基本应用程序,它通过输入字段从用户处获取输入,对该输入执行db搜索,并获取db搜索的结果,创建一个对象列表,然后绑定到一些html代码

我只需要关于绑定部分的帮助,但首先需要一些背景信息

我有一个列表[节点]:
case类节点(aname:String,adata:String){..}

我要将此html绑定到:

<div class="lift:helloWorld.displayNodes">
    <div>
            <div><li><B>Node:</B></li></div>
                <div>Name: <node:name></node:name></div>
                <div>Data: <node:data></node:data></div>
                <BR>
        </div>
</div>
现在问题是:
如何绑定而不在html中指定希望html代码调用的方法。我的意思是我想删除这一行:
,因为我不想在填充列表之前调用它。因此,基本上,我希望scala代码调用html并绑定到它,而不是html“调用”scala代码,但只有在它拥有数据之后。如何做到这一点


PS-我查看了cookbook.liftweb.net,但他们没有我需要的示例。

我不确定您的系统是如何设置的,但通常对于服务器推送,您希望使用Comet actor。下面的代码应该让您开始使用该路径,因为它将执行初始渲染,然后允许您根据消息事件向页面发送部分更新。因此,在这种情况下,它将响应加载列表时应发送的事件
pushList
。你可以阅读更多关于演员的内容

HTML文件

<div data-lift="comet?type=HelloWorldActor">
   <span id="nodes"></span> 
</div>

演员

case class HelloWorldActor() extends CometActor {
  //Handle any messages received
  override def lowPriority: PartialFunction[Any, Unit] = {
    case "pushList" => 
      partialUpdate {
        JsCmds.SetHtml("nodes", displayNodes.apply(listTemplate))
      }
  }

  //Look up the template from templates-hidden/list.html or if that does not exist
  //use the default NodeSeq specified
  def listTemplate = Templates.apply("templates-hidden" :: "list" :: Nil) openOr
    <div>
       <div><li><B>Node:</B></li></div>
       <div>Name: <span name="name"></span></div>
       <div>Data: <span name="data"></span></div>
       <BR>
    </div>

  //Load the list, and then on completion send the actor the message to push the list
  //This could also happen from outside the actor, you'd send the message in a similar 
  //fashion from wherever it happens
  def loadList() = {
    //load the data in your list and on complete
    this ! "pushList"
  }

  //The CSS Selector to output the node
  def displayNodes = {
    "*" #> nodeList.map { node =>
      "@name" #> node.name &
      "@data" #> node.data
    }
  }

  //Initial CSS Transformation
  override def render = {
    //Your initial CSS transformation
  }
}
case类HelloWorldActor()扩展了CometActor{
//处理收到的任何消息
覆盖def低优先级:部分功能[任何,单元]={
案例“推送列表”=>
部分更新{
JsCmds.SetHtml(“节点”,displayNodes.apply(listTemplate))
}
}
//从templates hidden/list.html中查找模板,或者如果该模板不存在的话
//使用指定的默认NodeSeq
def listmetplate=Templates.apply(“隐藏的模板”::“列表”::Nil)openOr
  • 节点:
  • 姓名: 数据:
    //加载列表,然后在完成时向参与者发送消息以推送列表 //这也可能发生在演员之外,你可以用类似的方式发送信息 //来自任何地方的时尚 def loadList()={ //在列表中加载数据,并在完成时加载 这是“推送名单” } //用于输出节点的CSS选择器 def displayNodes={ “*”#>nodeList.map{node=> “@name”#>node.name& “@data”#>node.data } } //初始CSS转换 覆盖def呈现={ //您最初的CSS转换 } }
    您将看到是什么实际设置了页面上的HTML。它只是一个JavaScript命令,在html元素上查找给定的id,然后用指定的
    NodeSeq
    替换它。如果您不打算使用Comet,可以使用该命令作为任何返回
    JsCmd
    的提升组件的响应


    我还提取了输出节点的HTML,以便于说明。
    Templates
    对象包含一种使用设计器友好模板的机制,该模板可以被查找并重复使用,这样做就不会丢失任何东西。但是,如果您想继续在一个文件中使用HTML,您可以在初始的
    呈现中捕获元素,比如:
    “#节点”#>{ns=>listmlate=ns;PassThru}
    (当然,在将
    listmlate
    更改为
    var
    之后)。

    我建议使用
    SHtml.idmemorize
    通过这种方式,您最初可以拥有一个带有输入但没有结果的页面。在用户输入数据并且服务器得到数据库数据后,您可以通过查询
    outer.setHtml


    这比设置一个
    CometActor
    更便宜、更容易,但只有当用户提出要求时,才能得到结果。因此,这样服务器将无法自行将某些更新推送到浏览器。

    JsCmds.SetHtml链接非常棒!我要用记忆或接线
    case class HelloWorldActor() extends CometActor {
      //Handle any messages received
      override def lowPriority: PartialFunction[Any, Unit] = {
        case "pushList" => 
          partialUpdate {
            JsCmds.SetHtml("nodes", displayNodes.apply(listTemplate))
          }
      }
    
      //Look up the template from templates-hidden/list.html or if that does not exist
      //use the default NodeSeq specified
      def listTemplate = Templates.apply("templates-hidden" :: "list" :: Nil) openOr
        <div>
           <div><li><B>Node:</B></li></div>
           <div>Name: <span name="name"></span></div>
           <div>Data: <span name="data"></span></div>
           <BR>
        </div>
    
      //Load the list, and then on completion send the actor the message to push the list
      //This could also happen from outside the actor, you'd send the message in a similar 
      //fashion from wherever it happens
      def loadList() = {
        //load the data in your list and on complete
        this ! "pushList"
      }
    
      //The CSS Selector to output the node
      def displayNodes = {
        "*" #> nodeList.map { node =>
          "@name" #> node.name &
          "@data" #> node.data
        }
      }
    
      //Initial CSS Transformation
      override def render = {
        //Your initial CSS transformation
      }
    }