2017-06-15 77 views
0

問題是根據它們的top CSS屬性對根節點的所有子div進行排序。如何通過Scala.js中的屬性值對子節點進行排序?

這裏是我的代碼:

val elements = global.document.getElementById("root").childNodes.asInstanceOf[dom.NodeList] 

val clones = (for (i <- (0 to (elements.length - 1)) if (elements(i).isInstanceOf[dom.raw.HTMLDivElement])) yield { 
    val clone = elements(i).cloneNode(true) 
    val style = clone.attributes.getNamedItem("style").value 
    val parts = style.split("top: ") 
    val parts2 = parts(1).split("px") 
    val px = parts2(0).toDouble 
    Tuple2[dom.Node, Double](clone, px) 
}).toList 

val sorted = clones.sortWith((a, b) => a._2 > b._2) 

global.document.getElementById("root").innerHTML = "" 

for (e <- sorted) { 
    global.document.getElementById("root").appendChild(e._1) 
} 

我是新來Scala.js,並花了相當的努力,想出這個解決方案。它編譯和似乎工作,但我不知道它是多麼合法。

例如,我只能以非常複雜的方式獲取節點的top屬性。另外我懷疑,要刪除所有子節點global.document.getElementById("root").innerHTML = ""是一種後門方式。我不確定這種排序是否可以在不創建克隆的情況下完成。我歡迎任何有待改進的建議,我希望有些初學者可能會發現這些代碼甚至有用。

回答

1

各種建議,一些關於Scala和一些底層瀏覽器環境:

首先,jQuery的(actual JavaScript library)(Scala.js facade)是你的朋友。試圖用原始DOM做任何事情都是一件痛苦的事情,除了最簡單的玩具應用之外,我不推薦它。 (這個有沒有關係Scala.js,頭腦 - 這是在瀏覽器中工作的只是現實,是所有真正的JavaScript以及。)

使用jQuery,得到的元素就是:

val elements = $("root").children 

其次,基本上沒有人在Scala中使用索引循環 - 這是合法的,但非常罕見。相反,你直接在for中獲取每個元素。您可以將價值分配直接放在自己的位置,保持yield條款的清晰。

jQuery讓你直接獲得CSS屬性。 (雖然我認爲你仍然必須解析出「px」。)再說一次,如果你嘗試使用原始DOM函數,一切都會更加困難。

而且它很難拼出Tuple2 - 你只需要使用parens作爲元組。全部放在一起,它看起來東西這樣的:

for { 
    element <- elements 
    if (element.isInstanceOf[dom.raw.HTMLDivElement]) 
    clone = element.clone() 
    top = clone.css("top") 
    px = top.dropRight(2).toDouble 
} 
    yield (clone, px) 

介意,我還沒有真正嘗試了上面的代碼 - 也有可能是一些錯誤 - 但是這更像是地道的斯卡拉。 js + jQuery代碼看起來很像,而且值得考慮作爲一個起點。

+0

感謝您提出這些建議。我實際上知道Scala.js.有一個jQuery擴展,但是我根本無法導入這個擴展:https://github.com/scala-js/scala-js-jquery,我得到了所有關於它的神祕錯誤信息捆綁。 D3.js擴展程序很容易導入,並且可以作爲魅力使用,目前我用它來進行選擇。我將不勝感激任何關於如何導入jQuery的幫助(一個完整的工作示例可能)。使用客戶端和服務器(+共享代碼)編譯在一起的集成項目使事情進一步複雜化:https://github.com/vmunier/play-with-scalajs-example。 – sbtpr

+0

那麼,使用vmunier的庫是非常符合沼澤標準的 - 我自己使用它。我建議使用較新的jquery-facade(上面鏈接)而不是舊的scala-js-jquery。但我不知道捆綁錯誤來自哪裏 - 這有點奇怪。我將很快出發,但我建議將它放在scala-js/scala-js Gitter頻道(這是Scala.js社區的核心),併發布您看到的錯誤 - 那裏的人可能會有幫助。 –

+0

另外,萬一它不明顯:請記住,它不是任何類型的jQuery *擴展*,它只是一個門面。您仍然需要在您的Scala.js代碼之前包含jQuery本身。 Scala.js外觀(無論使用scala-js-jquery還是jquery-facade)只是告訴Scala代碼如何*使用* jQuery。 –

相關問題