我正在尝试使用Amazon Rekognition在图像中检测到的文本周围绘制框。
这是一个精简的JavaFX应用程序,可以做到这一点:
object TextRekognizeGui extends JFXApp {
lazy val rekognition: Option[AmazonRekognition] =
RekogClient.get(config.AwsConfig.rekogEndpoint, config.AwsConfig.region)
private val config = MainConfig.loadConfig()
stage = new PrimaryStage {
scene = new Scene {
var imgFile: Option[File] = None
content = new HBox {
val imgFile: ObjectProperty[Option[File]] = ObjectProperty(None)
val img: ObjectProperty[Option[Image]] = ObjectProperty(None)
val lines: ObjectProperty[Seq[TextDetection]] = ObjectProperty(Seq.empty)
// These two print statements are always executed when we press the appropriate button.
img.onChange((_, _, newValue) => println("New image"))
lines.onChange((_, _, newValue) => println(s"${newValue.length} new text detections"))
children = Seq(
new VBox {
children = Seq(
new OpenButton(img, imgFile, lines, stage),
new RekogButton(img, imgFile, lines, rekognition)
)
},
new ResultPane(675, 425, img, lines))
}
}
}
stage.show
}
class ResultPane(width: Double, height: Double, img: ObjectProperty[Option[Image]],
textDetections: ObjectProperty[Seq[TextDetection]]) extends AnchorPane { private val emptyPane: Node = Rectangle(0, 0, width, height)
// This print statement, and the one below, are often not executed even when their dependencies change.
private val backdrop = Bindings.createObjectBinding[Node](
() => {println("new backdrop"); img.value.map(new MainImageView(_)).getOrElse(emptyPane)},
img
)
private val outlines = Bindings.createObjectBinding[Seq[Node]](
() => {println("new outlines"); textDetections.value map getTextOutline},
textDetections
)
在我看来,这就像我遵循ScalaFX文档的directions创建自定义绑定一样。当我单击“ RekogButton”时,我希望看到“新文本检测”消息以及“新轮廓”消息,但是更多的时候我只会看到“新文本检测”消息。
在程序的整个生命周期中,行为似乎是相同的,但仅在某些运行中才表现出来。 img
-> background
绑定也会发生相同的问题,但这种情况很少出现。
为什么属性更改时有时无法调用绑定?
修改1 JavaFX将与绑定关联的侦听器存储为weak reference,这意味着它们仍然可以被垃圾回收,除非另一个对象持有对它们的强引用或软引用。因此,如果垃圾收集器恰好在应用初始化和绘制轮廓之间运行,看来我的应用失败了。
这很奇怪,因为我似乎对绑定有很强的引用-结果窗格中值“ outlines”的“ delegate”字段。进一步研究。