我正在将quilljs与我的clojurescript应用程序集成在一起。我将其包含在我的project.cljs文件中,如下所示:[cljsjs/quill "1.3.5-0"]
。
编译器正在缩小某些方法并导致错误:
function xA(a, b) {
var c = t(a).getSelection(!0)
, d = c.index
, e = c.length
, h = Quill.import("delta");
c = function(b, c, d, e) {
return function(b) {
return t(a).updateContents((new e).rf(c).delete(d).nf({
image: b
}))
}
}(c, d, e, h);
return b.c ? b.c(c) : b.call(null, c)
}
这是错误:Uncaught TypeError: (intermediate value).rf is not a function
clojurescript代码如下:
(defn file-recieve-handler [this cb]
(let [range (.getSelection @this true)
index (.-index range)
length (.-length range)
delta (.import js/Quill "delta")]
(cb (fn [url]
(.updateContents @this
(.insert
(.delete
(.retain (new delta) index)
length)
#js {:image url}))))))
retain
方法和insert
方法越来越小-事实并非如此。 (删除不是出于某种原因,我猜那是因为它是javascript中的关键字。)
我找到了quilljs的externs文件: https://github.com/cljsjs/packages/blob/master/quill/resources/cljsjs/quill/common/quill.ext.js
是否有必要补充extern文件或以其他方式编写代码,以便在为编译器打开高级编译时不会缩小这两种方法?
在某些情况下,以下是完整文件。它基于此https://github.com/benhowell/reagent-quill/blob/master/quill.cljs
(ns quill.core
(:require
[reagent.core :as r]))
(defn quill-toolbar [id]
[:div {:id (str "quill-toolbar-" id)}
[:span {:class "ql-formats"}
[:select {:class "ql-header"}
[:option {:value "1"}]
[:option {:value "2"}]
[:option {:value "3"}]
[:option {:value "4"}]
[:option {:value "5"}]
[:option]]]
[:span {:class "ql-formats"}
[:select {:class "ql-font"}
[:option]
[:option {:value "serif"}]
[:option {:value "monospace"}]]]
[:span {:class "ql-formats"}
[:select {:class "ql-size"}
[:option {:value "small"}]
[:option]
[:option {:value "large"}]
[:option {:value "huge"}]]]
[:span {:class "ql-formats"}
[:button {:class "ql-bold"}]
[:button {:class "ql-italic"}]
[:button {:class "ql-underline"}]
[:button {:class "ql-strike"}]
[:button {:class "ql-blockquote"}]]
[:span {:class "ql-formats"}
[:select {:class "ql-align"}]]
[:span {:class "ql-formats"}
[:button {:class "ql-script" :value "sub"}]
[:button {:class "ql-script" :value "super"}]]
[:span {:class "ql-formats"}
[:button {:class "ql-indent" :value "-1"}]
[:button {:class "ql-indent" :value "+1"}]]
[:span {:class "ql-formats"}
[:button {:class "ql-image"}] ]
[:span {:class "ql-formats"}
[:select {:class "ql-color"}]
[:select {:class "ql-background"}]]
[:span {:class "ql-formats"}
[:button {:class "ql-clean"}]]])
(defn file-recieve-handler [this cb]
(let [range (.getSelection @this true)
index (.-index range)
length (.-length range)
delta (.import js/Quill "delta")]
(cb (fn [url]
(.updateContents @this
(.insert
(.delete
(.retain (new delta) index)
length)
#js {:image url}))))))
(defn editor [{:keys [id value selection on-change image-handler]}]
(let [this (r/atom nil)
get-value #(aget @this "container" "firstChild" "innerHTML")
string-id (if (keyword? id) (name id) id) ]
(r/create-class
{:component-did-mount
(fn [component]
(reset! this
(js/Quill.
(aget (.-children (r/dom-node component)) 1)
#js {:modules #js {:toolbar (aget (.-children (r/dom-node component)) 0)}
:theme "snow"
:scrollingContainer (str "quill-wrapper-" string-id)
:placeholder "Compose an epic..."}))
(.on @this "text-change"
(fn [delta old-delta source]
(on-change source (get-value))))
; FYI this is another area I had trouble. I got around it using
; get and set in the goog.object
(let [toolbar (.getModule @this "toolbar")
handlers (goog.object/get toolbar "handlers")]
(goog.object/set handlers "image" #(file-recieve-handler this image-handler)))
(if (= selection nil)
(.setSelection @this nil)
(.setSelection @this (first selection) (second selection) "api")))
:component-will-receive-props
(fn [component next-props]
(if
(or
(not= (:value (second next-props)) (get-value))
(not= (:id (r/props component)) (:id (second next-props))))
(do
(if (= selection nil)
(.setSelection @this nil)
(.setSelection @this (first selection) (second selection) "api"))
(.pasteHTML @this (:value (second next-props))))))
:display-name (str "quill-editor-" string-id)
:reagent-render
(fn []
[:div {:id (str "quill-wrapper-" string-id) :class "quill-wrapper"}
[quill-toolbar string-id]
[:div {:id (str "quill-editor-" string-id)
:class "quill-editor"
:dangerouslySetInnerHTML {:__html value}}]])})))
(defn display-area [{:keys [id content]}]
(let [this (r/atom nil)]
(r/create-class
{:component-did-mount
(fn [component]
(reset! this (js/Quill. (r/dom-node component)
#js {:theme "snow"
:modules #js {:toolbar false}
:placeholder ""}))
(.disable @this))
:component-will-receive-props
(fn [component next-props]
(.pasteHTML @this (:content (second next-props))))
:display-name (str "quill-display-area-" id)
:reagent-render
(fn []
[:div {:id (str "quill-display-area-" id)
:class "quill-display-area"
:dangerouslySetInnerHTML {:__html content}}])})))
答案 0 :(得分:1)
您可以打开外部推断警告,编译器会告诉您可能重命名的内容。
;; in the actual ns
(set! *warn-on-infer* true)
;; in the build config compiler options
:infer-externs true
请参见https://clojurescript.org/guides/externs#externs-inference
要帮助调试重命名问题,可以在编译器选项中打开:pseudo-names true
。这样可以更轻松地找出要重命名的方法,并且可能需要^js
typehint或手动externs。
答案 1 :(得分:0)
我使用了@ thomas-heller建议的类型提示,它起作用了。我将原始功能分为两个独立的功能。此处被重写:
(defn add-image [^js/Quill quill ^js/Quill.imports.delta delta index length url]
(.updateContents quill
(.insert
(.delete
(.retain delta index)
length)
#js {:image url})))
;https://github.com/quilljs/quill/pull/995/files#diff-6dafc0fe6b5e9aed0859eef541e68372
(defn file-recieve-handler [^js/Quill quill cb]
(let [range (.getSelection quill true)
index (.-index range)
length (.-length range)
delta (new (.-delta (.-imports js/Quill)))]
(cb (fn [url]
(add-image quill delta index length url)))))