All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.simiacryptus.mindseye.art.examples.TiledTexture.scala Maven / Gradle / Ivy

The newest version!
/*
 * Copyright (c) 2020 by Andrew Charneski.
 *
 * The author licenses this file to you under the
 * Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance
 * with the License.  You may obtain a copy
 * of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */

package com.simiacryptus.mindseye.art.examples

import java.net.URI

import com.simiacryptus.mindseye.art.models.VGG19
import com.simiacryptus.mindseye.art.ops._
import com.simiacryptus.mindseye.art.util.ArtSetup.{ec2client, s3client}
import com.simiacryptus.mindseye.art.util.ImageArtUtil._
import com.simiacryptus.mindseye.art.util.{BasicOptimizer, _}
import com.simiacryptus.mindseye.lang.Tensor
import com.simiacryptus.mindseye.layers.java.{ImgTileAssemblyLayer, AffineImgViewLayer}
import com.simiacryptus.notebook.NotebookOutput
import com.simiacryptus.ref.wrappers.RefAtomicReference
import com.simiacryptus.sparkbook.NotebookRunner.withMonitoredJpg
import com.simiacryptus.sparkbook._
import com.simiacryptus.sparkbook.util.Java8Util._
import com.simiacryptus.sparkbook.util.LocalRunner

object TiledTexture extends TiledTexture with LocalRunner[Object] with NotebookRunner[Object] {
  override val styleUrl: String = "file:///C:/Users/andre/Pictures/texture_sources/the-starry-night.jpg"
}

class TiledTexture extends ArtSetup[Object] {

  val styleUrl = "upload:Style"
  val initUrl: String = "50 + noise * 0.5"
  val s3bucket: String = "test.deepartist.org"
  val minResolution = 120
  val maxResolution = 400
  val magnification = Array(3.0)
  val rowsAndCols = 2
  val steps = 2
  val aspectRatio = 1.0
  val min_padding = 64
  val max_padding = 256
  val border_factor = 1.0

  override def indexStr = "201"

  override def description = 
Creates a simple tiled texture based on a style using:
  1. Random plasma initialization
  2. Standard VGG19 layers
  3. Operators constraining and enhancing style
  4. Progressive resolution increase
  5. View layer to enforce tiling
.toString.trim override def inputTimeoutSeconds = 3600 override def postConfigure(log: NotebookOutput) = { log.eval[() => Null](() => { () => { implicit val implicitLog = log // First, basic configuration so we publish to our s3 site if (Option(s3bucket).filter(!_.isEmpty).isDefined) log.setArchiveHome(URI.create(s"s3://$s3bucket/$className/${log.getId}/")) log.onComplete(() => upload(log): Unit) // Fetch image (user upload prompt) and display a rescaled copy loadImages(log, styleUrl, (maxResolution * Math.sqrt(magnification.head)).toInt).foreach(img => log.p(log.jpg(img, "Input Style"))) val canvas = new RefAtomicReference[Tensor](null) // Generates a pretiled image (e.g. 3x3) to display def tiledCanvas = { val input = canvas.get() if (null == input) input else { val layer = new ImgTileAssemblyLayer(rowsAndCols, rowsAndCols) val result = layer.eval((1 to (rowsAndCols * rowsAndCols)).map(_ => input.addRef()): _*) input.freeRef() layer.freeRef() val tensorList = result.getData result.freeRef() val tensor = tensorList.get(0) tensorList.freeRef() tensor } } // Tiling layer used by the optimization engine. // Expands the canvas by a small amount, using tile wrap to draw in the expanded boundary. def viewLayer(dims: Seq[Int]) = { val paddingX = Math.min(max_padding, Math.max(min_padding, dims(0) * border_factor)).toInt val paddingY = Math.min(max_padding, Math.max(min_padding, dims(1) * border_factor)).toInt val layer = new AffineImgViewLayer(dims(0) + paddingX, dims(1) + paddingY, true) layer.setOffsetX(-paddingX / 2) layer.setOffsetY(-paddingY / 2) List(layer) } // Execute the main process while registered with the site index val registration = registerWithIndexJPG(() => tiledCanvas) try { // Display a pre-tiled image inside the report itself withMonitoredJpg(() => { val tensor = tiledCanvas val image = tensor.toImage tensor.freeRef() image }) { withMonitoredJpg(() => Option(canvas.get()).map(tensor => { val imgViewLayer = viewLayer(tensor.getDimensions).head val result = imgViewLayer.eval(tensor) imgViewLayer.freeRef() val tensorList = result.getData result.freeRef() val data = tensorList.get(0) tensorList.freeRef() val image = data.toRgbImage data.freeRef() image }).orNull) { // Display an additional, non-tiled image of the canvas withMonitoredJpg(() => Option(canvas.get()).map(tensor => { val image = tensor.toRgbImage tensor.freeRef() image }).orNull) { log.subreport("Painting", (sub: NotebookOutput) => { paint( contentUrl = initUrl, initUrl = initUrl, canvas = canvas.addRef(), network = new VisualStyleNetwork( styleLayers = List( // We select all the lower-level layers to achieve a good balance between speed and accuracy. VGG19.VGG19_0b, VGG19.VGG19_1a, VGG19.VGG19_1b1, VGG19.VGG19_1b2, VGG19.VGG19_1c1, VGG19.VGG19_1c2, VGG19.VGG19_1c3, VGG19.VGG19_1c4, VGG19.VGG19_1d1, VGG19.VGG19_1d2, VGG19.VGG19_1d3, VGG19.VGG19_1d4 ), styleModifiers = List( // These two operators are a good combination for a vivid yet accurate style new GramMatrixEnhancer(), new MomentMatcher() ), styleUrls = Seq(styleUrl), magnification = magnification, viewLayer = viewLayer ), optimizer = new BasicOptimizer { override val trainingMinutes: Int = 60 override val trainingIterations: Int = 15 override val maxRate = 1e9 }, aspect = Option(aspectRatio), resolutions = new GeometricSequence { override val min: Double = minResolution override val max: Double = maxResolution override val steps = TiledTexture.this.steps }.toStream.map(_.round.toDouble) )(sub) null }) }(log) } } null } finally { canvas.freeRef() registration.foreach(_.stop()(s3client, ec2client)) } null } })() } }




© 2015 - 2025 Weber Informatics LLC | Privacy Policy