30. object Ijp extends LpxPlugIn {
private val leafThreffective = Seq('ijHuang, 'ijLi, 'ijMinimum, …
private val spotThreffective = Seq('ijRenyiEntropy, 'ijYen, …
private val leafThrSyms =
leafThreffective ++ (plg.threshold.Common.ijSymbols.toSet -- leaf…
}
private val spotThrSyms = {
spotThreffective ++ (plg.threshold.Common.ijSymbols.toSet -- spot…
}
private val mode = arg("kaMode", Seq('measure, 'setParam))
private val sep1 = arg("-- phase1 --")
private val shrink = arg("shrink", 4)
private val leafDenoise = arg("leafDenoise", 2.0)
private val leafThr = arg("leafThr", leafThrSyms)
private val spotDenoise = arg("spotDenoise", 1.0)
private val spotThr = arg("spotThr", spotThrSyms)
private val genStk = arg("genStk", false)
private val sep2 = arg("-- phase2 --")
private val leafMinArea = arg("leafMinAreaInOrg", 500000d)
private val spotCircularity = arg("spotCircularity", 0.6)
private val sep3 = arg("----")
private val continuePlugIn = arg("continuePlugIn", true)
31. // R G B
private val colorLeaf = new java.awt.Color(128, 128, 128)
private val colorSpot = new java.awt.Color(255, 255, 255)
private val colorLeafId = new java.awt.Color( 0, 198, 255)
private val colorSpotId = new java.awt.Color( 0, 255, 0)
private val colorImageJForeground = new java.awt.Color(255, 255, 255)
private val fontLeaf = new java.awt.Font("Serif", java.…
private val fontSpot = new java.awt.Font("Serif", java.…
def config(argStr: String): Option[() => Any] = {
def rec() {
val imp = IJ.getImage
input(mode)
mode.getSym match {
case 'measure => measure(imp)
case 'setParam => {
if (setParam()) rec()
}
}
}
rec()
None
}
32. private def measure(imp: Imp) {
if (ImgC.is(imp)) {
phase1(imp)
} else {
phase2()
}
}
private def phase1(impOrg: Imp) {
def bandpass(ip: Ip, loSd: Double, hiSd: Double): Ip = {
new plg.band_pass.DiffOfGaussian(loSd, hiSd)(ip)
}
def bandpassMin0(ip: Ip, loSd: Double, hiSd: Double): Ip = {
plg.band_pass.Min0(bandpass(ip, loSd, hiSd))
}
def to8bit(ip: Ip): Ip = plg.filter2d.ToByteType.SliScale(ip)
def toThrStk(ip: Ip): Ist = new plg.filter2d.ToStkByThrFromByte(A…
def showAndSetCurSlice(ist: Ist, title: String, z: Int) {
val impShow = new Imp(WindowManager.makeUniqueName(title), ist)
impShow.setDisplayRange(0, 255, 7)
impShow.updateAndDraw
impShow.setSlice(z + 1)
impShow.show
}
33. require(ImgC.is(impOrg), "ImgC.is")
require(impOrg.getStackSize == 1, "getStackSize == 1")
require(shrink() >= 1, "shrink >= 1")
ij.gui.Toolbar.setForegroundColor(colorImageJForeground)
impOrg.setTitle(WindowManager.makeUniqueName("org"))
val ipOrg = impOrg.getProcessor.rotateRight
impOrg.setProcessor(ipOrg)
ipOrg.setInterpolationMethod(Ip.BILINEAR)
val ipShrink = ipOrg.resize((ipOrg.getWidth / shrink().toFloat).r…
val (ipCieL, ipCieA, ipCieB_notUsed) =
new Rgb2ColorSpace(false).procSli(ipShrink, 'CIELAB2_speedy)
val (numX, numY) = UtilImg.dim(ipCieL)
val bpHiMax = numX.min(numY)
// leaf: CIEL*
val ipLeaf = to8bit(bandpassMin0(plg.filter_pt.MathOpMultiply(-1)…
val thrLeaf = new IjThresholder(leafThr.getSym).getThr(ipLeaf).get()
if (genStk()) {
val istLeaf = toThrStk(ipLeaf)
showAndSetCurSlice(istLeaf, "leaf", thrLeaf)
} else {
val imp = UtilImg.show(ipLeaf, f"leaf_${thrLeaf}")
IJ.setThreshold(imp, thrLeaf, 255) }
34. // spot: CIEa*
val ipSpot = to8bit(bandpass(ipCieA, spotDenoise(), bpHiMax))
val thrSpot = new IjThresholder(spotThr.getSym).getThr(ipSpot).get()
if (genStk()) {
val istSpot = toThrStk(ipSpot)
showAndSetCurSlice(istSpot, "spot", thrSpot)
} else {
val imp = UtilImg.show(ipSpot, f"spot_${thrSpot}")
IJ.setThreshold(imp, thrSpot, 255)
}
}
// use leafMinArea(), spotCircularity()
private def phase2() {
def getIpOfTitle(title: String): Ip = {
val titles = UtilIj.getAllImageTitles()
val hits = titles.filter(_.startsWith(title))
LpxExc.assert(hits.size == 1, f"Image '$' is not …
val ip = WindowManager.getImage(hits.head).getProcessor
LpxExc.assert(Img8.isBinary(ip), f"Image '$' must be …
ip
}
35. def drawString(ipTgt: Ip, s: String, font: Font, color: Color, …
ipTgt.setColor(color)
ipTgt.setFont(font)
val width = ipTgt.getStringWidth(s)
ipTgt.drawString(s, x - width, y)
}
ij.gui.Toolbar.setForegroundColor(colorImageJForeground)
val ipLeaf = getIpOfTitle("leaf")
val ipSpot = getIpOfTitle("spot")
LpxExc.assert(UtilImg.sameDim(ipLeaf, ipSpot), "dimension mismatch")
val leafMinAreaInShrinked = (leafMinArea() / (shrink() * shrink()))…
val leafBlobs = {
PixGrp.filterOutSmall(PixGrp.getBlobs(ipLeaf), leafMinAreaInShr…
}
val spotBlobs = {
val ipSpotInLeaf = Img8.dupRet(ipSpot, false) { ipSpotInLeaf =>
for (i <- 0 until ipSpot.getPixelCount if ipLeaf.get(i) == 0) {
ipSpotInLeaf.set(i, 0)
}
}
PixGrp.getBlobs(ipSpotInLeaf).filter(_.getCircularity >=
spotCircularity()) }
36. UtilIj.writeln(f"#shrink;?t${shrink()}")
UtilIj.writeln(f"# areaAdjustFactor;?t${shrink() * shrink()}")
UtilIj.writeln(f"#leafDenoise;?t${leafDenoise()}")
UtilIj.writeln(f"#leafThr;?t${leafThr.getSym.name}")
UtilIj.writeln(f"#spotDenoise;?t${spotDenoise()}")
UtilIj.writeln(f"#spotThr;?t${spotThr.getSym.name}")
UtilIj.writeln(f"#leafMinAreaInOrg;?t${leafMinArea()}")
UtilIj.writeln(f"# leafMinAreaInShrinked;?t${leafMinAreaInShrinked}"
UtilIj.writeln(f"#spotCircularity;?t${spotCircularity()}?n")
for ((leafBlob, leafIdx) <- leafBlobs.zipWithIndex) {
for (polRoi <- leafBlob.toPolygonRoi(true, true)) {
plg.roi_util.Painter.drawByRoiInSitu(ipDebug, colorLeaf, polRoi)
val awtRectangle = polRoi.getFloatPolygon.getBounds
ipDebug.setColor(colorLeafId)
val x = awtRectangle.x
val y = awtRectangle.y + awtRectangle.height / 2
drawString(ipDebug, f"${leafIdx}", fontLeaf, colorLeafId, x, y)
}
val leafXySet = leafBlob.toXys.toSet
val assocBlobs = spotBlobs.filter { spotBlob =>
val (centroidX, centroidY) = spotBlob.getCentroid
leafXySet.contains((centroidX.round.toInt, centroidY.round.…
} sortBy(- _.size)
37. for ((blob, blobIdx) <- assocBlobs.zipWithIndex) {
blob.drawToIpByColor(ipDebug, colorSpot)
val x = blob.xsMin - 3
val y = (blob.ysMin + blob.ysMax) / 2 + 10
drawString(ipDebug, f"${blobIdx}", fontSpot, colorSpotId, x, y)
}
UtilIj.writeln(f"leafIdx;?t$leafIdx")
UtilIj.writeln(f"leafArea;?t${leafBlob.size * shrink() * shrink(…
UtilIj.writeln(f"spotNum;?t${assocBlobs.size}")
val spotTotalArea = assocBlobs.map(_.size).sum
UtilIj.writeln(f"spotTotalArea;?t${spotTotalArea * shrink() * shr…
for ((spotBlob, spotIdx) <- assocBlobs.zipWithIndex) {
UtilIj.writeln(f" spotArea;?t${leafIdx}-${spotIdx};?t" +
f"${spotBlob.size * shrink() * shrink()}")
}
UtilIj.writeln("")
}
null
}