org.cosplay

package org.cosplay

Type members

Classlikes

abstract class CPAnimation(id: String) extends CPGameObject with CPAsset

Definition of the animation.

Definition of the animation.

Animation is defined as a sequence of key frames. Each key frame has an image and the index of its position in the sequence of key frames. Animation produces a key frame given animation context via method keyFrame. Note that animation definition is abstracted out from the way it is rendered. The same animation can be rendered differently. One such rendering is implemented by the built-in sprite CPAnimationSprite class.

Animation is an asset. Just like other assets such as images, sounds, fonts or videos they are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

Class CPAnimationSprite provides convenient built-in support for animation-driven sprites. In most cases you will to use or extend this sprite class to work with this animation.

Note that companion object provides factory methods that produce often used types of animation:

Refresh Rate

Even though CosPlay's effective FPS is usually around 1,000 on modern computers, the typical ANSI terminal struggles to render a full screen update even at partly 30 FPS. Large frame updates tend to result in "rolling shutter" effect, which is pronounced more for certain shapes and certain movement directions.

It is important to note that this effect is more pronounced for horizontal movement of large vertical shapes. Try to avoid this type of movement in your games.

Discrete Animation

It should come as no surprise that animation in ANSI terminal can only happen in one character units. You can't move by individual pixel - you only move by 10-20 pixel at a time depending on the font size used by your terminal. Even the specific font size is not directly available to the native ASCII game.

Discrete animation is obviously more jerky and more stuttering comparing to the pixel-based animation of the traditional graphics games. Vertical movement is more jerky than horizontal one since character height is usually larger than the character width (and we can move only a one character at a time).

There are two ways to mitigate this limitation:

  • Use smaller shapes for animation, prefer horizontal movement, and avoid prolong movements. "Rolling shutter" effect does not happen on each frame (more like every 20-40 frames) and so shorter animation sequences have a lesser chance of encountering this effect.
  • Use discrete animation as an artistic tool. When used properly and consistently it can result in a unique visual design of the game.

Different Ways To Animate

In CosPlay there are different ways one could implement animated scene objects. In the end, all of these approaches deliver similar results but each individual technique is tailor-made for a specific animation type:

Animated Sprites

This is a classic sprite animation technique ideally suited for animations that can be defined as a sequence of individual similarly or identically sized images. When played, each individual images is shown for a short period of time one after another delivering animation effect.

Lets consider an animation of the airplane in a top-down view game play. The basic animations for the airplane banking left or right, taking off or landing are ideally suited for sprite-based animation as they can easily be defined as a short sequence of individual images.

Particle Effects

Particle effect animation is based on the concept of a pixel-based particle and particle emitter. Particle emitter emits particles. Each particle and its emitter have a fully programmable behavior. The key characteristic of particle effect animation is the randomness over the large number of individual elements that you can easily model and implement using fully programmable particles and emitters.

In our airplane example, lets consider how one could implement the explosion when the airplane is hit with the missile. One could potentially implement such animated explosion as a long sequence of images but such process would be very tidies and lack the desired randomness. Particle effect-based animation fits the bill perfectly in such cases allowing to implement such random explosion animation in just a few lines of code.

Canvas Drawing

Sometime, a simple drawing on the canvas is all that's needed for a desired animation. Consider how one could implement a laser strike in our airplane example. A laser strike can be defined as a variable length line of pixel shown for a split second. The best way to implement it is with one line of code using many of the drawing functions in CPCanvas class and putting this logic into CPSceneObject.render method.

Video Sprites

Video sprite is a variation of sprite-based animation. In case of video, there are typically a lot more frames (often 1000s of frames) and all these frames have the same dimension. CPVideo and CPVideoSprite provide easy-to-use mechanism to implement it. Back to our airplane example, the video-based animation would be ideal choice for the cutscenes, entry video, etc.

Shaders

Shader is a piece of user-defined code that is executed on each frame for each scene object that has one or more shaders attached to it. There are types of animations that simply don't fit any previous type. The typical example of shader-based animation is the various lighting effect: flash-lite, sun shadows, transitions, highlighting, etc. These types of animation simply cannot be reasonably implemented using sprites, or particles, or canvas drawing. In such cases, shaders provide simple and effective contract to implement this behavior. Yet another unique characteristic of shaders is their application reusability. In fact, the same shader can be added to multiple scene objects to provide its effect.

In our airplane example, shaders can be used for shadow effect or "flashing" the airplane when it is hit by the enemy fire.

Value parameters:
id

Unique ID of the animation.

See also:

CPAnimationSprite for the built-in sprite that works with this animation.

Example:

See CPAnimationExample source code for an example of animation functionality.

Companion:
object
Source:
CPAnimation.scala

Companion object containing factory methods.

Companion object containing factory methods.

Companion:
class
Source:
CPAnimation.scala

Animation context that is passed into CPAnimation.keyFrame method.

Animation context that is passed into CPAnimation.keyFrame method.

See also:
Example:

See CPAnimationExample source code for an example of animation functionality.

Source:
CPAnimationContext.scala
case class CPAnimationKeyFrame(animationId: String, image: CPImage, index: Int)

Animation key frame consisting of an image and its index in the sequence of key frames.

Animation key frame consisting of an image and its index in the sequence of key frames.

Value parameters:
animationId

ID of the animation this key frame belongs to.

image

Key frame image.

index

Index of this key frame in the animation sequence.

Example:

See CPAnimationExample source code for an example of animation functionality.

Source:
CPAnimationKeyFrame.scala
class CPAnimationSprite(id: String, anis: Seq[CPAnimation], x: Int, y: Int, z: Int, initAniId: String, collidable: Boolean, shaders: Seq[CPShader], tags: String*) extends CPSceneObject

A scene objet tailor-made for showing animations based on CPAnimation.

A scene objet tailor-made for showing animations based on CPAnimation.

This sprite allows to implement a visual scene object that has one or more animations associated with it. These animations can be controlled either by the sprite itself or from the outside. This class provides necessary implementation for update and render methods. Make sure to call super if overriding any of these methods.

There are additional methods that allow access to and the control of the animation in the sprite:

Typically, to create a moving sprite, one would override this class and implement movement logic in overridden update method (making sure to call super), as well as overriding getX, getY and getDim methods to return current coordinates and dimension. Note that in most cases, one do need to override or change render method.

Value parameters:
anis

Sequence of animation. Must have at least one animation in it.

collidable

Whether or not this sprite is collidable.

id

Optional ID of the sprite.

initAniId

ID of the initial animation to play. This animation starts to play immediately.

shaders

Optional sequence of shaders for this sprite. Default value is an empty list.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

x

Initial X-coordinate.

y

Initial Y-coordinate.

z

Initial Z-index.

See also:
Example:

See CPAnimationExample source code for an example of animation functionality.

Source:
CPAnimationSprite.scala
class CPArray2D[T](val width: Int, val height: Int)(using c: ClassTag[T])

Immutable 2D-array. Optionally, has a clear value that is used to clear out array.

Immutable 2D-array. Optionally, has a clear value that is used to clear out array.

Type parameters:
T

Type of the array element.

Value parameters:
height

Height of the array. Must be >= 0.

width

Width of the array. Must be >= 0.

Note:

If clear value is not set, the default clear value is null.

Companion:
object
Source:
CPArray2D.scala
object CPArray2D

Contains factory methods for 2D arrays.

Contains factory methods for 2D arrays.

Companion:
class
Source:
CPArray2D.scala
class CPArrayImage(data: CPArray2D[CPPixel], origin: String) extends CPImage

An image based on two-dimensional pixel array.

An image based on two-dimensional pixel array.

This is the primary tool for creating in-code images. This class has number of constructors and companion utility methods to aid in creating in-code images in variety of ways. Here's a typical example of using this class to create an in-code image. Note the use of companion object function prepSeq():

object CPAlienImage extends CPArrayImage(
   prepSeq("""
       |    .  .
       |     \/
       |    (@@)
       | g/\_)(_/\e
       |g/\(=--=)/\e
       |    //\\
       |   _|  |_
     """),
   (ch, _, _) => ch&C_LIME
)
Value parameters:
data

Image data. Note that given data array should not have null values.

origin

The origin of the image like file path or URL.

Companion:
object
Source:
CPArrayImage.scala

Companion object contains utility functions.

Companion object contains utility functions.

Companion:
class
Source:
CPArrayImage.scala

ASCII-based table with minimal styling support. Can be used for structured logging and provides output like this:

ASCII-based table with minimal styling support. Can be used for structured logging and provides output like this:

+------------------------------------------------------+
|   Name        |               Value                  |
+===============+======================================+
| Game ID       | 52050358-d7a1-4def-b53f-db2bee8aea33 |
| Game name     | My Cool Game                         |
| Game URL      | 'null'                               |
| Description   | 'null'                               |
+------------------------------------------------------+
Companion:
object
Source:
CPAsciiTable.scala

Companion object contains utility functions.

Companion object contains utility functions.

Companion:
class
Source:
CPAsciiTable.scala
trait CPAsset

Mark up type indicating that the object is an asset.

Mark up type indicating that the object is an asset.

Assets like images, sounds, fonts, animations or videos are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

Here's current list of assets:

Source:
CPAsset.scala

Base type for various scene-related context classes.

Base type for various scene-related context classes.

See also:
Source:
CPBaseContext.scala
final class CPCache(delayedQ: ArrayBuffer[() => Unit])

A map-like type that is used by CPSceneObjectContext for game-wide and scene-wide user-data containers.

A map-like type that is used by CPSceneObjectContext for game-wide and scene-wide user-data containers.

The instances of this class are created and managed by the game engine and available via CPSceneObjectContext.getSceneCache and CPSceneObjectContext.getGameCache methods. Scene and game caches can be used to exchange and store user-defined data between frames of the same scene or between scenes of the game. Note that by default these caches are in-memory only and not persistent between game executions. One coule, however, add persistence using one of the lifecycle methods available through CPLifecycle type that is extended by both CPSceneObject and CPScene types.

Note that all mutating operations will be queued up and executed at the end of the current frame processing. Specifically, any changes will be "visible" to other scene objects only on the next frame.

Value parameters:
delayedQ

Queue for delayed operations. Used internally by the game engine.

See also:
Source:
CPCache.scala
open class CPCamera

Camera panning descriptor.

Camera panning descriptor.

Camera tracking is the process by which the game engine automatically focuses on a particular scene object and tracks its movement across screen keeping so that it stays in focus. Without camera tracking a scene object could move outside the visible screen and become invisible.

Camera descriptor defines a rectangular sub-region of the screen called focus frame. A tracking object can move freely as long as it is fully contained in that focus frame. Once the tracking object (at least partially) moves outside the focus frame, the focus frame and therefore the visible portion of the current scene will shift to bring the tracking object back into the focus frame. The amount of shift as well as its velocity is also controlled by this descriptor:

+--------------------------------------------------+
|scene                                             |
|         +-------------------------------+        |
|         |screen/canvas                  |        |
|         |     +--------------------+    |        |
|         |     |focus frame         |    |        |
|         |     |                    |    |        |
|         |     |       o            |    |        |
|         |     |      /|\ tracking  |    |        |
|         |     |      / \ object    |    |        |
|         |     |                    |    |        |
|         |     +--------------------+    |        |
|         |                               |        |
|         +-------------------------------+        |
|                                                  |
+--------------------------------------------------+

Camera control is a property of scene and available via CPScene.getCamera method. The camera descriptor is a mutable object. Once obtained via CPScene.getCamera method you can configure it. Note that the default camera descriptor returned by the scene is not configured for tracking.

Example:

See CPCameraExample class for the example of using camera.

Source:
CPCamera.scala
class CPCanvas(pane: CPZPixelPane, clip: CPRect)

2D rendering pane. Canvas is synonymous with screen, i.e. it is an object that allows to draw on the screen.

2D rendering pane. Canvas is synonymous with screen, i.e. it is an object that allows to draw on the screen.

For each game frame, the game engine creates a new empty canvas for all scene objects to draw on. This canvas is available to scene objects via CPSceneObjectContext.getCanvas method. Game engine then compares previous canvas and this one to determine which areas of the terminal need redrawing. You can also create the canvas object outside game loop using companion object methods.

Canvas (0,0) coordinate point is located in the top left corner. X-axis goes to the right and Y-axis points down. Every drawn pixel on the canvas also has a Z-index or depth. Pixel with larger or equal Z-index visually overrides the pixel with the smaller Z-index.

ASCII-based graphics are vastly different from the traditional raster-based graphics. Since ASCII-based drawing uses printable characters from ASCII character set that are displayed on basic text terminal most differences are obvious but some are more subtle and unexpected. For example, while straight vertical and horizontal lines are easy to implement many curved lines are much trickier to draw. Specifically, circles and ellipses, for example, are hard to do properly in automated way. Moreover, many complex curves need to be done manually, especially if they are dynamically redrawn on each frame update.

This class provides many methods for basic line and rectangular drawing, circle and polylines, anti-aliasing, "color" fill in, and much more. Most functions have multiple overridden variants with different parameters so that they can be easily used in different contexts. Note also that this class deals primarily with line ASCII art and has only few functions like antialiasing for the solid ASCII art.

One of the useful techniques of obtaining a complex "drawn-on-canvas" images is to create a new canvas object at the scene's start (see CPLifecycle.onStart method), draw all necessary ASCII art on it and then capture the image using one of the capture() methods in this class. Once image is obtained you can use it with any image-based sprites to display it.

There are many online tutorials for ASCII art that are highly recommended, including from:

See also the following resources for general ASCII art collections:

Value parameters:
clip

Clipping region.

pane

Underlying z-pane.

See also:
Example:

See CPCanvasExample class for the example of using canvas.

Companion:
object
Source:
CPCanvas.scala
object CPCanvas

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPCanvas.scala
abstract class CPCanvasSprite(id: String, shaders: Seq[CPShader], tags: String*) extends CPSceneObject

Scene object tailor-made for canvas drawing.

Scene object tailor-made for canvas drawing.

Canvas sprite takes dimension of the current camera frame. That allows its CPSceneObject.render method, the only one method that needs to be implemented by the sub-type, to draw on entire camera frame of the terminal.

Note that by default this sprite sets its position and dimension equal to the entire camera frame. This may affect shaders attached to this sprite if they are configured to work with object vs. entire frame since this sprite will report its size as entire camera frame size. Shaders that work with this sprite should account for it.

Note, if overriding CPSceneObject.update method make sure to call super.update(...).

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Value parameters:
id

Optional ID of this sprite.

shaders

Optional list of shaders attached to this canvas sprite.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

Source:
CPCanvasSprite.scala
final case class CPColor(red: Int, green: Int, blue: Int, name: String) extends Ordered[CPColor] with Serializable

An RGB/HSB color.

An RGB/HSB color.

A color is an immutable container for 24-bit RGB value.

Color Creation

Color companion object provides 100s of the pre-built color constants for all xterm and X11 standard colors. New color creation is an expensive process. It is highly recommended using one of the many built-in color constants or pre-create the colors you need upfront. As a rule of thumb - avoid new color creation on each frame update.

8-Bit & 24-Bit Color Depth

Most modern ANSI terminals support "True Color" 24-bit colors, the unlimited combination of Red, Green, and Blue values in RGB. Some older terminals, however, only provide support for 8-bit colors where each color is a lookup number into 256-color lookup table (LUT). These are also often called xterm colors despite the fact that xterm terminal application does support the 24-bit colors. Note that there's only an approximate translation from a true 24-bit color to 8-bit color, i.e. the closest 8-bit color will be used when translating from 24-bit color to 8-bit color. More specifically, many darker 24-bit colors will convert as 8-bit dark grey.

By default, CosPlay stores all colors in 24-bit format internally and renders all colors as 24-bit colors in both native terminal and the built-in terminal emulator. If, however, you want to automatically convert 24-bit color to the nearest 8-bit color during rendering you need to set system property COSPLAY_FORCE_8BIT_COLOR=true. Note that this will force both native terminal and built-in terminal emulator to use 8-bit color conversion even though technically the built-in terminal emulator can always display true 24-bit color. This is only necessary if running the game in the native terminal that does not support 24-bit colors.

Note also that since 8-bit color space is much smaller many color effects like fade in and fade out, color gradients, etc. will look less smooth when using 8-bit colors.

XTerm vs X11 Color Names

Companion object provides constants for pre-built colors:

You are free to use any constants with any naming convention, as well as mix and match - they are all just colors. Note that although there are many similar and identical colors across two naming groups, they do differ in some as well as offer some unique colors. CosPlay provides these two sets of constants for convenience. Please, refer to the following links for specific color references:

Value parameters:
blue

Blue RGB component.

green

Green RGB component.

name

Optional color name. Can be null or empty string. For built-in color this is color's constant name in this class.

red

Red RGB component.

Companion:
object
Source:
CPColor.scala
object CPColor

Companion object contains utility functions and color constants.

Companion object contains utility functions and color constants.

Companion:
class
Source:
CPColor.scala
object CPCurve

Set of utilities for interpolation functions.

Set of utilities for interpolation functions.

Source:
CPCurve.scala
final case class CPDim(width: Int, height: Int) extends Ordered[CPDim] with Serializable

2D dimension immutable container.

2D dimension immutable container.

Value parameters:
height

Height in characters.

width

Width in characters.

Companion:
object
Source:
CPDim.scala
object CPDim

Companion object with static utility functions.

Companion object with static utility functions.

Companion:
class
Source:
CPDim.scala
object CPEngine

CosPlay game engine.

CosPlay game engine.

Game engine is mostly an internal object, and it is only used at the beginning of the game. It provides variety of utility and miscellaneous methods for games.

Most CosPlay games follow this basic game organization:

import org.cosplay.*

object Game:
  def main(args: Array[String]): Unit =
      // Initialize the engine.
      CPEngine.init(
           CPGameInfo(name = "My Game"),
           System.console() == null || args.contains("emuterm")
      )

      // Create game scenes & their scene objects.
      val sc1 = new CPScene(...)
      val sc2 = new CPScene(...)

      // Start the game & wait for exit.
      try CPEngine.startGame(sc1, sc2)
      finally CPEngine.dispose()

      sys.exit(0)

Notes:

  • Game start in a standard Scala way. It is recommended to use main(...) function for better compatibility.
  • Create CPGameInfo object that describes the game and its properties.
  • Initialize game engine by calling CPEngine.init method passing it game descriptor and terminal emulation flag.
  • Create all necessary scenes, scene objects and assets. You can organize these objects in any desirable way - CosPlay does not impose any restrictions or limitation on how it is should be done.
  • Once you have all scenes constructed - you can start the game by calling one of the CPEngine.startGame methods.
  • Make sure to call CPEngine.dispose method upon exit from CPEngine.startGame method.

System Properties

CosPlay game engine supports the following system properties that control various aspects of its operation. Note that these properties must be set before method CPEngine.init is called:

System PropertyValue TypeDescription
COSPLAY_EMUTERM_FONT_NAMEStringApplies to the built-in terminal emulator only. Specifies the font name to use.
COSPLAY_EMUTERM_FONT_SIZEIntApplies to the built-in terminal emulator only. Specifies the font size to use.
COSPLAY_EMUTERM_CH_WIDTH_OFFSETIntApplies to the built-in terminal emulator only. Specifies character width offset. Can be positive or negative. Default is zero.
COSPLAY_EMUTERM_CH_HEIGHT_OFFSETIntApplies to the built-in terminal emulator only. Specifies character height offset. Can be positive or negative. Default is zero.
COSPLAY_EMUTERM_ANTIALIASApplies to the built-in terminal emulator only. If system property is present - the font rendering will use antialiasing. By default, no antialiasing is used.
COSPLAY_FORCE_8BIT_COLORBooleanForces the automatic conversion from 24-bit color to 8-bit color. Only needed when running in the native terminal that does not support 24-bit color. Default value is false.
COSPLAY_TERM_CLASSNAMEStringFully qualified class name for the custom terminal emulator implementation. Class must implement org.cosplay.CPTerminal trait.

Reserved Keyboard Keys

There are three reserved key strokes that are used by the game engine itself and therefore NOT available to the game. These keystrokes are intercepted before frame update and not propagated to the scene object context:

  • 'CTRL+Q' - toggles in-game FPS overlay
  • 'CTRL+L' - opens GUI-based loc viewer & debugger
  • 'F12' - saves current frame screenshot as *.xp image to the current working folder.
Note:

See developer guide at https://cosplayengine.com

Example:

See all examples under org.cosplay.examples package. Each example has a complete demonstration of working with game engine including initialization and game start.

Source:
CPEngine.scala
class CPException(msg: String, cause: Throwable) extends RuntimeException

CosPlay exception.

CosPlay exception.

Many methods throughout CosPlay API throw this exception. In most cases - there's no expected recovery from these errors, such errors should be considered fatal and the game should be stopped. In rare cases where such recovery is possible - the documentation specifically highlights it.

Value parameters:
cause

Optional case of this error. Default value is null.

msg

Error message.

Source:
CPException.scala
class CPFIGLetFont(flfPath: String) extends CPFont

FIGLet font.

FIGLet font.

FIGLet fonts allow creating art text out of ordinary letters, for example:


 /$$$$$$                      /$$$$$$$  /$$
/$$__  $$                    | $$__  $$| $$
| $$  \__/  /$$$$$$   /$$$$$$$| $$  \ $$| $$  /$$$$$$  /$$   /$$
| $$       /$$__  $$ /$$_____/| $$$$$$$/| $$ |____  $$| $$  | $$
| $$      | $$  \ $$|  $$$$$$ | $$____/ | $$  /$$$$$$$| $$  | $$
| $$    $$| $$  | $$ \____  $$| $$      | $$ /$$__  $$| $$  | $$
|  $$$$$$/|  $$$$$$/ /$$$$$$$/| $$      | $$|  $$$$$$$|  $$$$$$$
\______/  \______/ |_______/ |__/      |__/ \_______/ \____  $$
  ___  _____  ___  ____  __      __   _  _            /$$  | $$
 / __)(  _  )/ __)(  _ \(  )    /__\ ( \/ )          |  $$$$$$/
( (__  )(_)( \__ \ )___/ )(__  /(__)\ \  /            \______/
 \___)(_____)(___/(__)  (____)(__)(__)(__)
                                       ,,
 .g8"""bgd                 `7MM"""Mq.`7MM
.dP'     `M                   MM   `MM. MM
dM'       ` ,pW"Wq.  ,pP"Ybd  MM   ,M9  MM   ,6"Yb.`7M'   `MF'
MM         6W'   `Wb 8I   `"  MMmmdM9   MM  8)   MM  VA   ,V
MM.        8M     M8 `YMMMa.  MM        MM   ,pm9MM   VA ,V
`Mb.     ,'YA.   ,A9 L.   I8  MM        MM  8M   MM    VVV
 `"bmmmd'  `Ybmd9'  M9mmmP'.JMML.    .JMML.`Moo9^Yo.  ,V
                                                     ,V
                                                  OOb"

You can read the full FIGLet specification here. This class provides relatively full implementation for FIGLet fonts with the following limitations:

  • code tags are NOT supported
  • only UTF-8 and windows-1252 charsets are supported
  • only left-to-right font direction is supported
  • vertical smushing iS NOT supported (ignored)

CosPlay comes with 277 built-in pre-packaged FIGLet fonts. Companion object for this class contains constants for all these fonts.

Here's an example of rendering FIGLet fonts using static image sprites. Note that when invoking render it returns an image that can be rendered or used just like any other image in CosPlay:

val spr1 = CPStaticImageSprite(30, 14, 4, FIG_OGRE.render("CosPlay", C_WHITE).trimBg())
val spr1 = CPStaticImageSprite(30, 20, 4, FIG_OGRE.withKerning().render("CosPlay", C_LIGHT_STEEL_BLUE).trimBg())
val spr1 = CPStaticImageSprite(30, 27, 4, FIG_OGRE.withFullWidth().render("CosPlay", C_LIGHT_CORAL).trimBg())

Here's the list of helpful links when working with FIGLet fonts:

Example:

See CPFontsExample source code for an example of FIGLet font functionality.

Companion:
object
Source:
CPFIGLetFont.scala

Companion object contains constants for all built-in FIGLet fonts.

Companion object contains constants for all built-in FIGLet fonts.

Useful links:

Companion:
class
Source:
CPFIGLetFont.scala
abstract class CPFont(origin: String) extends CPGameObject with CPAsset

Font descriptor.

Font descriptor.

Font is an asset. Just like other assets such as images, sounds, animations or videos they are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

CosPlay comes with a full support for FIGLet fonts as well as standard "system" font , all of which implement this interface. In other words, there's no difference whether you are drawing with a system (1-character height) font or a FIGLet font.

See also:

CPFIGLetFont FIGLet fonts.

CPSystemFont System font.

CPStyledString Styled string using system font.

CPCanvas.drawStyledString Canvas drawing using system font or styled strings.

Example:

See CPFontsExample source code for an example of font functionality.

Source:
CPFont.scala
final case class CPGameInfo(id: String, name: String, semVer: String, initDim: Option[CPDim], termBg: CPColor, minDim: Option[CPDim])

Descriptor of the game.

Descriptor of the game.

Value parameters:
id

Unique ID of the game. If not provided, the default value will be a randomly generated globally unique ID.

initDim

Optional initial game dimension. It is used only by emuterm built-in terminal emulator to set the initial terminal emulator dimension. It is ignored by the native terminal. If not provided, terminal emulator will use its default dimension.

minDim

Optional minimal native terminal window size. This is only checked for the native terminal. If the native terminal size is smaller - an exception is thrown before game is started. For terminal emulator it is ignored.

name

Public, display name of the game. This parameter is required and does not have default value.

semVer

Semantic version of the game. See https://semver.org/ for details. Default value is 1.0.0

termBg

Optional background color for the terminal. The default value is 0x111111 RGB color.

Source:
CPGameInfo.scala
abstract class CPGameObject(id: String, tags: Set[String])

Root type for CosPlay classes.

Root type for CosPlay classes.

Game object has ID and organizational tags that can be used to organize game objects. See CPSceneObjectContext.getObjectsForTags method for getting scene objects based on their tags.

Value parameters:
id

Unique ID of this game object. By default, a random 6-character ID will be used.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

See also:
Source:
CPGameObject.scala
abstract class CPImage(origin: String) extends CPGameObject with CPAsset

Defines rectangular shape and its content as a collection of pixels.

Defines rectangular shape and its content as a collection of pixels.

Image is one of the key types in CosPlay. Almost everything that is drawn on the screen is represented by an image: FIGLet font string, sprites, video and animation frames, etc. Image itself is just a container for pixels. It can be created in-code or loaded and saved from and to the external file or resource. To render the image on the screen you can use CPCanvas.drawImage method.

Image is an asset. Just like other assets such as fonts, sounds, animations or videos they are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

In-Code Images

One of the convenient features of CosPlay is that images can be created & painted (a.k.a. skinned) right in code with very minimal gestalt. The easiest way is to use CPArrayImage class that provides utility methods to convert a margin-based Scala string into an image. For example:

import org.cosplay.*
import CPColor.*
import CPArrayImage.*
import CPPixel.*

object CPAlienImage extends CPArrayImage(
   prepSeq("""
       |    .  .
       |     \/
       |    (@@)
       | g/\_)(_/\e
       |g/\(=--=)/\e
       |    //\\
       |   _|  |_
     """),
   (ch, _, _) => ch&C_LIME
)

Another example with more sophisticated skinning:

import org.cosplay.*
import CPColor.*
import CPArrayImage.*
import CPPixel.*

object CPAmigaImage extends CPArrayImage(
   prepSeq("""
     |  .---------.
     |  |.-------.|
     |  ||>run#xx||
     |  ||xxxxxxx||
     |  |"-------'|
     |.-^---------^-.
     ||x---~xxxAMiGA|
     |"-------------'
   """),
   (ch, _, _) => ch match
       case ' ' => XRAY
       case c @ ('A' | 'M' | 'i' | 'G') => CPPixel(c, C_NAVY, C_WHITE)
       case c @ ('r' | 'u' | 'n' | '#') => c&C_GREEN_YELLOW
       case 'x' => CPPixel(' ', C_BLACK)
       case '>' => '>'&C_GREEN_YELLOW
       case '~' => '~'&C_ORANGE_RED
       case c => c&C_WHITE
)

Loading Images

You can load images from the external source like URL or file path in one of the following formats:

  • *.xp REXPaint XP format. This is a native binary format supported by REXPaint ASCII editor. This format supports full color information.
  • *.csv REXPaint CSV format. This format is natively exported by REXPaint ASCII editor and also supported by CosPlay to save an image with. This format supports full color information.
  • *.txt format. Image in this format is a simple *.txt file and it does not provide or store any color information.

Use one of the following methods from the companion object to load the image from file path, resources folder or URL:

  • load()
  • loadRexCsv()
  • loadRexXp()
  • loadTxt()

For example:

val speckImg = CPImage.load(
   "prefab/images/speck.xp",
   (px, _, _) => px.withBg(None) // Make background transparent.
)

Saving Images

You can save image to the local file path in the following format:

  • *.csv REXPaint CSV format. This format is natively exported by REXPaint ASCII editor and also supported by CosPlay to save an image with. This format supports full color information.
  • *.xp REXPaint XP format. This is a native format used by REXPaint ASCII editor and can be loaded by the REXPaint.This format supports full color information.
  • *.txt Text format. This format does not retain color inforation.

Use the following methods to save the image to the file path:

ASCII Art Online

There's a vast collection of existing ASCII art imagery online. Here's some of the main resources where you can find it:

Prefabs

CosPlay comes with a list of prefab image, animations and video clips. All of them are shipped with CosPlay and can be found in org.cosplay.prefabs package and its sub-packages.

ASCII Art Editors

REXPaint ASCII editor is an excellent free editor for ASCII art from the creator of the Cogmind game. REXPaint editor is highly recommended for images with non-trivial coloring.

Value parameters:
origin

The origin of the image like file path or URL.

Example:

See CPImageCarouselExample class for the example of using images.

See CPImageFormatsExample class for the example of using images.

Companion:
object
Source:
CPImage.scala
object CPImage

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPImage.scala
class CPImageSprite(id: String, x: Int, y: Int, z: Int, img: CPImage, collidable: Boolean, shaders: Seq[CPShader], tags: String*) extends CPSceneObject

Scene object tailor-made for rendering images.

Scene object tailor-made for rendering images.

This sprite can be used to render static or moving image, the same image or changing images. For static unchanging images see CPStaticImageSprite for even simpler API.

Dynamic Image Position

If a game is intended to work with adaptive scene sizing than all of its scene objects must adapt to changing size of the scene. Image sprite provides simple and convenient way to support this logic. Here's an example of using image sprite to display an image at the center of the screen dynamically adjusting its position on each frame to the actual canvas size:

   val img = ...
   val spr = new CPImageSprite("logo", 0, 0, 0, img):
       override def update(ctx: CPSceneObjectContext): Unit =
           val canv = ctx.getCanvas
           setX((canv.dim.width - getImage.getWidth) / 2)
           setY((canv.dim.height - getImage.getHeight) / 2)

Notes:

  • All we have to do is override CPSceneObject.update method to update XY-coordinate on each frame.
  • Canvas instance will always have the current size of scene: whether it is defined explicitly or implicitly as the current size of the terminal.
  • Initial (0,0) position is not used as we override the actual position on each frame.
  • We use methods setX and setY to set current XY-coordinates.
  • Note that we don't need to override any other methods. Specifically, we don't need to override render method since it relies on getX and getY method in its implementation.

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Value parameters:
collidable

Whether or not this sprite has a collision shape. Default is false.

id

Optional ID of the sprite. By default, a random ID will be used.

img

The image to render. It can be changed later.

shaders

Optional sequence of shaders for this sprite. Default value is an empty sequence.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

x

Initial X-coordinate of the sprite.

y

Initial Y-coordinate of the sprite.

z

Z-index at which to render the image.

See also:
Example:

See CPImageCarouselExample class for the example of using images.

See CPImageFormatsExample class for the example of using images.

Companion:
object
Source:
CPImageSprite.scala

Companion object contains utility methods.

Companion object contains utility methods.

Companion:
class
Source:
CPImageSprite.scala
trait CPInput

Interface for the external input devices such as joysticks and game pads.

Interface for the external input devices such as joysticks and game pads.

You can add support for such devices by calling CPEngine.addInput and CPEngine.removeInput methods on the game engine. Note that keyboard support is built into CosPlay and you don't need to do anything additional to access it. This interface is designed to add additional external input devices that are not automatically supported by CosPlay.

See also:
Source:
CPInput.scala

External input device context.

External input device context.

Instance of this type is passed to CPInput.poll method.

See also:
Source:
CPInputContext.scala
final case class CPInsets(top: Int, left: Int, bottom: Int, right: Int)

Insets container as 4-int tuple.

Insets container as 4-int tuple.

Value parameters:
bottom

Bottom inset.

left

Left inset.

right

Right inset.

top

Top inset.

Companion:
object
Source:
CPInsets.scala
object CPInsets

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPInsets.scala
final class CPInt2(val i1: Int, val i2: Int) extends Ordered[CPInt2]

General 2-int tuple.

General 2-int tuple.

Value parameters:
i1

1st integer.

i2

2nd integer.

Companion:
object
Source:
CPInt2.scala
object CPInt2

Companion object with utility and factory methods.

Companion object with utility and factory methods.

Companion:
class
Source:
CPInt2.scala
class CPInt4(val i1: Int, val i2: Int, val i3: Int, val i4: Int) extends Ordered[CPInt4]

General 4-int tuple.

General 4-int tuple.

Value parameters:
i1

1st value.

i2

2nd value.

i3

3rd value.

i4

4th value.

Companion:
object
Source:
CPInt4.scala
object CPInt4

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPInt4.scala
final case class CPKeyboardEvent(key: CPKeyboardKey, sameAsLast: Boolean, eventFrame: Long, eventNs: Long, lastEventFrame: Long, lastEventNs: Long)

Container for the keyboard input event.

Container for the keyboard input event.

Your scene objects can access the current keyboard event using CPSceneObjectContext.getKbEvent method.

Value parameters:
eventFrame

Frame number for this event.

eventNs

Timestamp of the event in nanoseconds.

key

Keyboard key.

lastEventFrame

Frame number of the last keyboard event.

lastEventNs

Timestamp in nanoseconds of the last keyboard event.

sameAsLast

Whether or not last keyboard event had the same keyboard key.

See also:
Source:
CPKeyboardEvent.scala

Companion object contains utility functions.

Companion object contains utility functions.

See also:
Companion:
class
Source:
CPKeyboardKey.scala
enum CPKeyboardKey(val id: String, val isPrintable: Boolean, val ch: Char, val rawCodes: Seq[Char]*) extends HashMap[String, AnyRef]

Enumeration of all supported keyboard keys.

Enumeration of all supported keyboard keys.

Remapped Keys

The following keystrokes are automatically re-mapped:

  • CTRL+h is mapped to CPKeyboardKey.KEY_BACKSPACE.
  • CTRL+i is mapped to CPKeyboardKey.KEY_TAB.
  • CTRL+m is mapped to CPKeyboardKey.KEY_ENTER.

NOTE: CTRL+h, CTRL+i and CTRL+m will not be detected as-is, and you should use their conversions instead. Note that even-though this enumeration provides constants for CTRL+h, CTRL+i and CTRL+m they will never be returned to the scene objects since they would always be automatically remapped. This is the limitation of the ANSI terminals, i.e. CTRL+m generated the same ANSI code as Enter key press.

Reserved Keys

There are three reserved key strokes that are used by the game engine itself and therefore NOT available to the game. These keystrokes are intercepted before frame update and not propagated to the scene object context:

  • 'CTRL+Q' - toggles in-game FPS overlay
  • 'CTRL+L' - opens GUI-based loc viewer & debugger
  • 'F12' - saves current frame screenshot as *.xp image to the current working folder.
See also:

CPKeyboardEvent.key

Companion:
object
Source:
CPKeyboardKey.scala
class CPLabelSprite(id: String, x: Int, y: Int, z: Int, font: CPFont, text: String, fg: CPColor, bg: Option[CPColor], skin: (CPPixel, Int, Int) => CPPixel, collidable: Boolean, shaders: Seq[CPShader]) extends CPSceneObject

Scene object tailor-made for rendering text labels.

Scene object tailor-made for rendering text labels.

This sprite accepts text and the font along with skinning function and renders this text at the given XY-coordinates. Text of the label can change dynamically. Note that the dimension of the sprite is changing along with the change of the label's text.

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Value parameters:
bg

Optional background color. Default value is None.

collidable

Whether or not this sprite provides collision shape. Default value is false.

fg

Foreground color.

font

Font to use for label.

id

Optional ID of this sprite.

shaders

Optional sequence of shaders for this sprite. Default value is an empty sequence.

skin

Skinning function. The function takes an existing pixel, its X and Y coordinate and return a new pixel. Default value is the function that returns the same pixel.

text

Label text.

x

X-coordinate of the top-left corner of the label.

y

Y-coordinate of the top-left corner of the label.

z

Z-index at which to render the label.

Example:

See CPTextInputExample class for the example of using labels and text input.

Source:
CPLabelSprite.scala

Contains lifecycle state enumeration.

Contains lifecycle state enumeration.

Companion:
class
Source:
CPLifecycle.scala

Lifecycle type for scenes and scene objects.

Lifecycle type for scenes and scene objects.

Objects supporting this lifecycle transition their states as follows:

 +---------+   +------------+   +-----------+   +-------------+   +------------+
 | LF_INIT |-->| LF_STARTED |-->| LF_ACTIVE |-->| LF_INACTIVE |-->| LF_STOPPED |
 +---------+   +------------+   +-----------+   +-------------+   +------------+
                                      |                   |
                                      +---<-----<----<----+

Specifically, lifecycle objects are started and stopped only once but they can transition from active to inactive state more than once. When a scene starts it and its scene objects will be started, if they haven't been started before, and activated. When switching to another scene, the current scene and its scene objects will be deactivated. Scene and scene objects get stopped when either the entire game exits or an object gets removed.

The typical use case for the lifecycle events is resource initialization and disposal, logging, stats collections, etc. It is especially important in online games or the games that pull or stream online assets.

Note that when overriding the following callback methods make sure to call super:

Companion:
object
Source:
CPLifecycle.scala
trait CPLog

Game logging interface.

Game logging interface.

As CosPlay games are terminal-based they require a different approach to logging since CosPlay cannot use the standard terminal output (it will conflict the game rendering). All the log that goes through this interface always ends up in two places:

  • Built-in GUI-based log viewer that can be opened in any game by pressing Ctrl-l at any time.
  • In *.txt log files under ${USER_HOME}/.cosplay/log/xxx directory, where xxx is the name of the game.

The instance of this logger is available to any scene object via CPSceneObjectContext.getLog. You can also get a root logger at any time outside the frame update pass via CPEngine.rootLog method. Note that additionally to the standard familiar logging APIs this interface supports log throttling that's important in games since most of the game logic gets "touched" up to 30 times a second and log throttling is essential for not overflowing logging.

Underneath the implementation is using latest Log4j2 library. You can supply your own log4j2.xml file on the classpath of your game. Here's the default Log4j2 configuration:

<Configuration status="INFO" strict="true">
   <Appenders>
       <RollingFile
           name="file"
           fileName="${sys:user.home}/.cosplay/log/${sys:COSPLAY_GAME_NAME}/log.txt"
           filePattern="${sys:user.home}/.cosplay/log/${sys:COSPLAY_GAME_NAME}/$${date:yyyy-MM}/log-%d{MM-dd-yyyy}-%i.gz">
           <PatternLayout>
               <Pattern>%d %p %c{1.} [%t] %m%n</Pattern>
           </PatternLayout>
           <Policies>
               <TimeBasedTriggeringPolicy />
               <SizeBasedTriggeringPolicy size="250 MB"/>
           </Policies>
       </RollingFile>
   </Appenders>
   <Loggers>
       <Root level="trace">
           <AppenderRef ref="file"/>
       </Root>
   </Loggers>
</Configuration>
See also:
Source:
CPLog.scala

Log levels.

Log levels.

Source:
CPLog.scala
case class CPMarkup(fg: CPColor, bg: Option[CPColor], elements: Seq[CPMarkupElement]) extends Serializable

Markup specification that can be used to convert a sequence of characters to the sequence of pixels based on this specification.

Markup specification that can be used to convert a sequence of characters to the sequence of pixels based on this specification.

Each specification has mandatory default foreground and optional background colors. It also has a list of markup elements (potentially empty) where each element has opening and closing tag and a function that takes a character and returns pixel.

Here's an example of defining the markup:

   val markup = CPMarkup(
       C_GREEN,
       Option(C_BLACK),
       Seq(
           CPMarkupElement("<$", "$>", _&&(C_RED, C_WHITE)),
           CPMarkupElement("{#", "#}", _&&(C_BLUE, C_YELLOW)),
           CPMarkupElement("(?", "?)", _&&(C_BLACK, C_WHITE))
       )
   )

Once defined this markup can be used to convert a string ito sequence of pixels and then create an image:

   val pxs = markup.process("text <$ red on white (? black on white ?)$> {# blue on yellow #}")
   val img = CPArrayImage(pxs, bgPx, align = -1) // Left-aligned image.
Value parameters:
bg

Default optional background color.

elements

Markup elements. Can be empty.

fg

Default foreground color.

See also:

CPArrayImage.apply method for creating an image from the list of pixel representing text.

Source:
CPMarkup.scala
case class CPMarkupElement(openTag: String, closeTag: String, skin: Char => CPPixel) extends Serializable

Markup element.

Markup element.

Value parameters:
closeTag

Closing tag.

openTag

Open tag.

skin

Character to pixel converter.

See also:
Source:
CPMarkup.scala
class CPOffScreenSprite(id: String, shaders: Seq[CPShader], tags: String*) extends CPSceneObject

Scene object that has no rendering content of its own.

Scene object that has no rendering content of its own.

This type of sprites is typically used for keyboard handlers or shaders-only rendering, e.g. fade in of the entire screen, etc. Note that shaders must be attached to some scene object but that object doesn't have to be visible for the shader to render - hence the convenience of using off-screen sprites for screen-wide shader rendering. Off-screen sprite has its visible flag set to false, XY-coordinate set to (0,0) and its Z-index set to zero. Its dimension set to CPDim.ZERO and it shape set to CPRect.ZERO as well.

Since this is an off-screen, invisible sprite the method CPSceneObject.render will never be called. Use CPSceneObject.update callback, if necessary, instead and make sure to call super.update(...).

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Value parameters:
id

Optional ID of this scene object. By default, the random 6-character ID will be used.

shaders

Optional sequence of shaders for this sprite.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

Companion:
object
Source:
CPOffScreenSprite.scala

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPOffScreenSprite.scala

Programmable particle.

Programmable particle.

Particle is part of the particle effect animation support. Particle effect support consists of three key components:

Particle defines a single-pixel element (a-la mini-sprite) that has its own lifecycle and gets updated on each frame update. Particle emitter is a components that is responsible for creating particles. And particle sprite ties all that together into single renderable component. Particle sprite can have one or more particle emitters and each emitter can create multiple particles. One of the key features of particle effect support is its modularity: particle implementation can be reused by multiple emitters, and an emitter implementation can be reused by multiple independent particle sprites.

Example:

See CPParticleExample class for the example of using particle effect.

Source:
CPParticle.scala
abstract class CPParticleEmitter(id: String, tags: Set[String]) extends CPGameObject with CPAsset

Particle emitter.

Particle emitter.

Particle emitter is part of the particle effect animation support. Particle effect support consists of three key components:

Particle defines a single-pixel element (a-la mini-sprite) that has its own lifecycle and gets updated on each frame update. Particle emitter is a components that is responsible for creating particles. And particle sprite ties all that together into single renderable component. Particle sprite can have one or more particle emitters and each emitter can create multiple particles. One of the key features of particle effect support is its modularity: particle implementation can be reused by multiple emitters, and an emitter implementation can be reused by multiple independent particle sprites.

Particle emitter is an asset. Just like other assets such as fonts, images, animations or videos they are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

Value parameters:
id

Unique ID of this emitter. By default, a random 6-character ID will be used.

tags

Optional set of organizational tags. These tags are here only for the game developer benefits as they are not used by the game engine itself. By default, the empty set is used.

Example:

See CPParticleExample class for the example of using particle effect.

Source:
CPParticleEmitter.scala
class CPParticleSprite(id: String, emitters: Seq[CPParticleEmitter], collidable: Boolean, shaders: Seq[CPShader]) extends CPSceneObject

Scene object tailor-made for rendering particle effect.

Scene object tailor-made for rendering particle effect.

Particle sprite is part of the particle effect animation support. Particle effect support consists of three key components:

Particle defines a single-pixel element (a-la mini-sprite) that has its own lifecycle and gets updated on each frame update. Particle emitter is a components that is responsible for creating particles. And particle sprite ties all that together into single renderable component. Particle sprite can have one or more particle emitters and each emitter can create multiple particles. One of the key features of particle effect support is its modularity: particle implementation can be reused by multiple emitters, and an emitter implementation can be reused by multiple independent particle sprites.

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Value parameters:
collidable

Whether or not this sprite provides collision shape. Defualt value is false.

emitters

Set of particle emitters this sprite will use.

id

Optional ID of the sprite.

shaders

Optional sequence of shaders for this sprite. Default value is an empty sequence.

Example:

See CPParticleExample class for the example of using particle effect.

Source:
CPParticleSprite.scala
final case class CPPixel(char: Char, fg: CPColor, bg: Option[CPColor], tag: Int) extends Serializable

Single character pixel.

Single character pixel.

Character-pixel is a fundamental graphics unit in ASCII-based games. Just like the raster pixel on a graphics screen it represents the smallest area that can be rendered on the screen.

CosPlay pixel is immutable and consists of a character from the ASCII character set, a foreground color, an optional background color and an optional tag. Note that pixel itself does not have a Z-index as it can be rendered at any Z-index.

Pixel creation and manipulation is used extensively throughout a CosPlay game. There are several ways you can create a pixel:

   import org.cosplay.*
   import CPColor.*
   import CPPixel.*

   // Canonical black 'x' on white background.
   new CPPixel('x', C_BLACK, Some(C_WHITE), 0)

   // Few companion object shortcuts for often used cases...
   CPPixel('x', C_BLACK, C_WHITE) // Avoiding 'Some'.
   CPPixel('x', C_BLACK) // Skipping background all together.
   CPPixel('x', C_BLACK, 2) // Skipping background & setting a '2' ag.
   CPPixel('x', C_BLACK, C_WHITE, 2) // Setting up a '2' tag.

You can also use a convenient syntactic sugar '&' and '&&'based on given conversion and extension of Char type. The following unit test demonstrates that usage. Note that usage of '&' extension operators is the recommended way and that is what is used internally by CosPlay:

   import org.cosplay.*
   import CPColor.*
   import CPPixel.*
   // Must be enabled for conversions.
   import scala.language.implicitConversions

   val p1 = 'x'&C_BLACK // Recommended way.
   val p2: CPPixel = 'x' -> C_BLACK // Requires explicit type declaration.
   val p3: CPPixel = ('x', C_BLACK) // Requires explicit type declaration.
   val p4 = CPPixel('x', C_BLACK)
   val p5 = new CPPixel('x', C_BLACK, None, 0)

   assertTrue(p1 == p2)
   assertTrue(p2 == p3)
   assertTrue(p3 == p4)
   assertTrue(p4 == p5)

   val p6 = 'x'&&(C_BLACK, C_WHITE) // Recommended way.
   val p7 = new CPPixel('x', C_BLACK, Option(C_WHITE), 0)

   assertTrue(p6 == p7)
Value parameters:
bg

Background color. If not provided, the background color of this pixel will not be set when rendering on the screen.

char

Pixel character.

fg

Pixel foreground color.

tag

Pixel tag. Tag can be used to tag a pixel, for example, during a fill in algorithm to mark the pixel as touched.

See also:
Companion:
object
Source:
CPPixel.scala
object CPPixel

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPPixel.scala
final case class CPPosPixel(px: CPPixel, x: Int, y: Int) extends Ordered[CPPosPixel] with Serializable

Immutable container for pixel and its XY-coordinate.

Immutable container for pixel and its XY-coordinate.

Value parameters:
px

Pixel.

x

Pixel X-coordinate.

y

Pixel Y-coordinate.

See also:
Source:
CPPosPixel.scala
object CPRand

Provides convenient functions for random number generation and usage.

Provides convenient functions for random number generation and usage.

See also:

Random

Source:
CPRand.scala
final case class CPRect(x: Int, y: Int, width: Int, height: Int) extends CPInt4

Rectangular shape.

Rectangular shape.

This class is used to define any arbitrary rectangular shape. Note that this class only describes the rectangular shape but does not hold any content.

Value parameters:
height

Height of the rectangular.

width

Width of the rectangular.

x

X-coordinate of the left top corner.

y

Y-coordinate of the left top corner.

See also:

CPArray2D 2D content holder.

Companion:
object
Source:
CPRect.scala
object CPRect

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPRect.scala
case class CPRenderStats(frameCount: Long, sceneFrameCount: Long, fps: Int, avgFps: Int, low1PctFps: Int, userTimeNs: Long, sysTimeNs: Long, objCount: Long, visObjCount: Long, kbEvent: Option[CPKeyboardEvent])

Container for rendering statistics.

Container for rendering statistics.

Value parameters:
avgFps

Average frames-per-second (FPS) over the last 500 frames.

fps

Current frames-per-second (FPS) rate.

frameCount

Current frame number since the beginning of the game.

kbEvent

Keyboard event, if any, for the current frame.

low1PctFps

Average frames-per-second (FPS) value across lowest 1% of all FPS values for the last 500 frames.

objCount

Total count of scene objects (including visible and invisible ones).

sceneFrameCount

Current frame number since the start of the current scene.

sysTimeNs

Average time in nanoseconds spent by the CosPlay game engine for the processing and rendering the current frame.

userTimeNs

Time in nanoseconds spent in user logic for the current frame.

visObjCount

Total count of visible scene objects.

See also:
Source:
CPRenderStats.scala

Listener for rendering statistics.

open class CPScene(id: String, dim: Option[CPDim], bgPx: CPPixel) extends CPGameObject with CPLifecycle

A scene is a container for scene objects.

A scene is a container for scene objects.

Scene has an ID, optional dimension and one or more scene objects. Note that scene must always have at least one scene object. In CosPlay there is no hierarchy of scene objects in the scene - all scene objects form a simple flat structure inside of the scene. Just like with any other game objects, you can use tags to organize scenes and scene objects.

Creating A Scene

Scene has a strong encapsulation contract in relation to its scene objects: you can only add initial scene objects to the scene at the time of scene creation. Once scene is created, its constituent scene objects can only be manipulated via methods in CPSceneObjectContext class passed to scene objects on each frame update.

In CosPlay you create a new scene in one of two ways:

  • Instantiate CPScene class.
    When creating an instance of CPScene class you'll be using one of the constructors provided by CPScene class. Every constructor requires a set of initial scene objects to be supplied.
      val myScene = new CPScene("id", None, bgPx, spr1, spr2)
  • Extend CPScene class.
    When subclassing CPScene you need to use addObjects method available to the sub-classes to add initial scene objects.
       object MyScene extends CPScene("id", None, bgPx):
           addObjects(spr1, spr2)

Note that you can dynamically add and remove scene as well as scene objects via CPSceneObjectContext instance. See CPSceneObjectContext API for more details.

Scene Dimension

CosPlay scene can be adaptive or static in terms of its dimensions. When scene dimension is set it becomes unchangeable (static) for the lifecycle of the scene and its scene objects can rely on this fact. However, if scene dimension is set as None, it will adapt to the terminal dimension on each frame meaning that the scene's dimension and therefore its canvas on which all scene objects are rendered can change its size from frame to frame. Make sure that all scene objects in the adaptive scene take this into account in their rendering routines.

Value parameters:
bgPx

Background pixel of the scene. Background pixel is shown when none of the scene objects has drawn a pixel at that particular coordinate. Background pixel must have background color defined.

dim

Optional dimension of the scene. Note that if dimension is None then scene will adapt to the terminal dimension on each frame. That means that the scene's canvas on which all scene objects are rendered can change its size from frame to frame. In such case, make sure that all scene objects take this into account in their rendering routines.

id

ID of the scene.

See also:
Source:
CPScene.scala
abstract class CPSceneObject(id: String, tags: Set[String]) extends CPGameObject with CPLifecycle

Root type for all CosPlay scene objects.

Root type for all CosPlay scene objects.

Scene objects can be visible or invisible, have rectangular shape, have XY-coordinates of its left-top corner and Z-index. On each game frame and for each scene object the engine calls update method and, if object is visible and in frame, calls render method followed by calling all of its shaders.

Scene is a container for for scene objects. Scene objects can be added or removed from the scene dynamically via CPSceneObjectContext instance passed to update and render methods. Note that all scenes should have at least one scene object. In CosPlay there is no hierarchy of scene objects in the scene - all scene objects form a simple flat structure inside of the scene. Just like with any other game objects, you can use tags to organize scenes and scene objects.

Generally, you would use one of many existing scene object subclasses like the various sprites provided out-of-the-box. You can, however, just as easily subclass this class directly and provide the necessary implementation. At the minimum you need to implement all abstract methods and at least one of either render or update methods.

Here's a basic minimal scene object implementation that prints "Hello CosPlay!" text at (0,0) coordinate in black color:

object HelloSprite extends CPSceneObject("id"):
   override def getX: Int = 0
   override def getY: Int = 0
   override def getZ: Int = 0
   override def getDim: CPDim = CPDim(15, 1)
   override def render(ctx: CPSceneObjectContext): Unit =
       ctx.getCanvas.drawString(0, 0, 0, "Hello CosPlay!", CPColor.C_BLACK)

If scene object is invisible than only update method will be called on each frame. If object is visible and in camera frame - method render will be called as well to render itself. Note that shaders are called always, regardless of whether the object visible, in camera frame or invisible.

Note that shader pass consists of two phases:

  • On the 1st phase shaders for all visible scene objects are processed
  • On the 2nd phase shaders for all invisible scene objects are processed. This allows to minimize the interference between object shaders and full-screen shaders that are typically attached to the off-screen sprite that is invisible. In other words, full-screen shaders will be execute after all object shaders in a given scene.
Value parameters:
id

Optional ID of this scene object. By default, the random 6-character ID will be used.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

Source:
CPSceneObject.scala

Scene object context during frame update.

Scene object context during frame update.

This type is main access point to the most of CosPlay functionality for the scene objects comprising the gameplay. On each game frame update all scene objects from the current scene receive CPSceneObject.update call and optional CPSceneObject.render call both of which receive the instance of this type. Also, the shaders attached to that scene objects, if any, receive the callback with the instance of this type.

Scene object context functionality can be grouped into:

See also:
Source:
CPSceneObjectContext.scala
final class CPScreen(dim: CPDim, bgPixel: CPPixel) extends CPZPixelPane

Game engine view on terminal screen.

Game engine view on terminal screen.

Value parameters:
bgPixel

Background pixel for the screen.

dim

Screen dimension.

Source:
CPScreen.scala
trait CPShader extends CPAsset

A programmable shader for scene object.

A programmable shader for scene object.

Shader is a piece of user-defined code that is executed on each frame pass for each scene object that has one or more shaders attached to it.

Different Ways To Animate

In CosPlay there are different ways one could implement animated scene objects. In the end, all of these approaches deliver similar results but each individual technique is tailor-made for a specific animation type:

Animated Sprites

This is a classic sprite animation technique ideally suited for animations that can be defined as a sequence of individual similarly or identically sized images. When played, each individual images is shown for a short period of time one after another delivering animation effect.

Lets consider an animation of the airplane in a top-down view game play. The basic animations for the airplane banking left or right, taking off or landing are ideally suited for sprite-based animation as they can easily be defined as a short sequence of individual images.

Particle Effects

Particle effect animation is based on the concept of a pixel-based particle and particle emitter. Particle emitter emits particles. Each particle and its emitter have a fully programmable behavior. The key characteristic of particle effect animation is the randomness over the large number of individual elements that you can easily implement using fully programmable particles and emitters.

In our airplane example, lets consider how one could implement the explosion when the airplane is hit with the missile. One could potentially implement such animated explosion as a long sequence of images but such process would be very tidies and lack the desired randomness. Particle effect-based animation fits the bill perfectly in such cases allowing to implement such random explosion animation in just a few lines of code.

Canvas Drawing

Sometime, a simple drawing on the canvas is all that's needed for a desired animation. Consider how one could implement a laser strike in our airplane example. A laser strike can be defined as a variable length line of pixel shown for a split second. The best way to implement it is with one line of code using many of the drawing functions in CPCanvas class and putting this logic into CPSceneObject.render method.

Video Sprites

Video sprite is a variation of sprite-based animation. In case of video, there are typically a lot more frames (often 1000s of frames) and all these frames have the same dimension. CPVideo and CPVideoSprite provide easy-to-use mechanism to implement it. Back to our airplane example, the video-based animation would be ideal choice for the cutscenes, entry video, etc.

Shaders

CPShader Shader is a piece of user-defined code that is executed on each frame for each scene object that has one or more shaders attached to it. There are types of animations that simply don't fit any previous type. The typical example of shader-based animation is the various lighting effect: flash-lite, sun shadows, transitions, highlighting, etc. These types of animation simply cannot be reasonably implemented using sprites, or particles, or canvas drawing. In such cases, shaders provide simple and effective contract to implement this behavior. Yet another unique characteristic of shaders is their application reusability. In fact, the same shader can be added to multiple scene objects to provide its effect.

In our airplane example, shaders can be used for shadow effect or "flashing" the airplane when it is hit by the enemy fire.

Shader is an asset. Just like other assets such as fonts, images, animations or videos they are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

Full-Screen Shaders

Shader can work with either a scene object it is attached to or with full screen. Typically, a full screen shader will be attached to an off-screen sprite (since the particular scene object such shader is attached to is irrelevant). In more elaborate games, there could be multiple off-screen sprites with multiple full-screen shaders - where all these shaders work with the same screen real estate. In such cases it can be non-trivial to control the order in which shaders are executed, if required. The recommended technique for such cases is to have only one off-screen sprite that attaches all full-screen shaders so that their order can be easily defined and controlled.

Order Of Processing

Note that shader pass consists of two phases:

  • On the 1st phase shaders for all visible scene objects are processed
  • On the 2nd phase shaders for all invisible scene objects are processed. This allows to minimize the interference between object shaders and full-screen shaders that are typically attached to the off-screen sprite that is invisible. In other words, full-screen shaders will be execute after all object shaders in a given scene.
See also:
Example:

See CPShaderExample class for the example of using shaders.

Source:
CPShader.scala
class CPSound(src: String, tags: Set[String]) extends CPGameObject with CPAsset

Sound clip container.

Sound clip container.

Sounds object requires URI of the sound file in one of the supported formats: AIFF, AU or WAV. Sound object is immutable but its playback can be controlled with changing volume, balance, rate, fade in and out. Sounds are inherently asynchronous objects, you can have many sounds objects, all of them are independent of each other, and you can play them in parallel.

Sound is an asset. Just like other assets such as fonts, images, animations or videos they are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

NOTE: game engine must be initialized before sounds object can be created.

Value parameters:
src

RFC-2396 URI as required by java.net.URI or 'resource' file. URI should point to a sound file in one of the supported format: AIFF, AU or WAV. Only HTTP, FILE, and JAR URIs are supported.

tags

Optional set of organizational tags. Default is an empty set.

Note:

See https://freesound.org/ for the excellent source of royalty free sounds and audio-fx.

Example:

See CPSoundExample class for the example of using sounds.

Companion:
object
Source:
CPSound.scala
object CPSound

Companion object with utility functionality.

Companion object with utility functionality.

Companion:
class
Source:
CPSound.scala
class CPStaticImageSprite(id: String, x: Int, y: Int, z: Int, img: CPImage, collidable: Boolean, shaders: Seq[CPShader], tags: String*) extends CPSceneObject

Scene object tailor-made for rendering static images.

Scene object tailor-made for rendering static images.

This sprite is very similar to CPImageSprite sprite and they both provide the same functionality. However, for non-moving non-changing images this sprite provides shorter and simple API and better performance.

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Value parameters:
collidable

Whether or not this sprite has a collision shape. Default is false.

id

Optional ID of the sprite.

img

The image to render.

shaders

Optional sequence of shaders for this sprite. Default value is an empty sequence.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

x

X-coordinate of the sprite.

y

Y-coordinate of the sprite.

z

Z-index at which to render the image.

See also:
Example:

See CPImageCarouselExample class for the example of using images.

See CPImageFormatsExample class for the example of using images.

Source:
CPStaticImageSprite.scala

Builder for a styled string rendered using system font.

Builder for a styled string rendered using system font.

This utility class provides a builder pattern to built styled (colored) strings that are rendered using a system font. Once styled string is built it can be rendered via CPCanvas.drawStyledString method.

Here's an example of using styled string together with array image to quickly create an image with a styled textual content:

import CPStyledString.styleStr

val lblImg = new CPArrayImage(
   styleStr("[SPACE]", C_WHITE) ++ styleStr("Play|Pause ", C_GREEN) ++
   styleStr("[R]", C_WHITE) ++ styleStr("Rewind ", C_GREEN) ++
   styleStr("[Q]", C_WHITE) ++ styleStr("Quit ", C_GREEN) ++
   styleStr("[CTRL-L]", C_WHITE) ++ styleStr("Log ", C_GREEN) ++
   styleStr("[CTRL-Q]", C_WHITE) ++ styleStr("FPS Overlay", C_GREEN)
).trimBg()
See also:
Example:

See CPFontsExample source code for an example of font functionality.

Companion:
object
Source:
CPStyledString.scala

Companion object contains factory functions.

Companion object contains factory functions.

Companion:
class
Source:
CPStyledString.scala
object CPSystemFont extends CPFont

System 1-character high font.

System 1-character high font.

See also:
Example:

See CPFontsExample source code for an example of font functionality.

Source:
CPSystemFont.scala

Output terminal interface.

Output terminal interface.

This is game engine view on the underlying terminal. CosPlay comes built-in with two implementations for this interface:

  • org.cosplay.impl.jlineterm.CPJLineTerminal native JLine-based implementation that works with any OS command line terminal application supporting ANSI escape sequences are a standard for in-band signaling to control cursor location, color, font styling, and other options. For running games in xterm, iTerm, any VTE-based terminal, Windows Terminal, etc. this is the implementation to use.
  • org.cosplay.impl.emuterm.CPEmuTerminal GUI-based terminal emulator. It behaves in exactly the same manner as native ANSI-based terminal. It takes no advantage of raster graphics in drawing or color rendering. It also adheres to the FPS capping by the game engine. Terminal emulator is an ideal tool during the game development as you can quickly iterate, start and stop games right from IDEs without any need for the external builds.

When initializing CosPlay game engine using one of the CPEngine.init methods you are passing a boolean parameter which indicates whether to use native or a GUI-based terminal emulator. This way the game engine automatically knows which of the two built-in implementations to use and you don't need to specify these classes anywhere else. For the most use cases this is all that is needed.

Note that there's an easy way to check whether or not your game is running in the native terminal. Execute the following code somewhere in your game engine initialization routine:

   val isInNativeTerm = System.console() != null

and pass the appropriate flag into one of the CPEngine.init methods. This way your game will automatically choose the appropriate terminal implementation based on what environment it is running on.

Custom Terminal Implementation

You may decide to provide your own terminal implementation, for example, targeting iOS, Android or WebGL output. Here are the steps to do it:

  • Create a class that implements this trait.
  • This class should have at least one public constructor that takes one parameter of type CPGameInfo.
  • This class should be instantiable through standard reflection from Scala code.
  • Set system property COSPLAY_TERM_CLASSNAME=x.y.z.MyTerm, where x.y.z.MyTerm is a fully qualified name of the class you developed. Make sure to set this system property before calling one of the CPEngine.init methods.
  • Initialize the game engine as usual. Setting COSPLAY_TERM_CLASSNAME system property will override the default terminal selection.
See also:

org.cosplay.impl.jlineterm.CPJLineTerminal

org.cosplay.impl.emuterm.CPEmuTerminal

Source:
CPTerminal.scala
class CPTextInputSprite(id: String, x: Int, y: Int, z: Int, visLen: Int, maxBuf: Int, var initTxt: String, onSkin: (Char, Int, Boolean) => CPPixel, offSkin: (Char, Int, Boolean) => CPPixel, var next: Option[String], cancelKeys: Seq[CPKeyboardKey], submitKeys: Seq[CPKeyboardKey], tags: String*) extends CPSceneObject

Scene object tailor-made for accepting text input.

Scene object tailor-made for accepting text input.

This sprite acts as a classic input field: user can input text using keyboard and cursor keys. It supports different field and buffer lengths, skinning input (i.e. password field) as well as user-defined set of keys for submission and cancellation. You can also chain multiple text inputs together to create an auto-navigable forms. NOTE: this sprite works only with system font - you can't use FIGLeft fonts with this sprite.

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Value parameters:
cancelKeys

Optional set of keyboard keys to accept for cancellation action. When one of these keys is pressed the sprite will reset to its initial state. Default value is CPKeyboardKey.KEY_ESC.

id

Optional ID of this sprite.

initTxt

Optional initial text to show at the initial state. Default value is an empty string.

maxBuf

Overall buffer length of this field. It should always be greater then or equal to visible length.

next

Optional scene object ID to switch keyboard focus to after the user pressed one of the submit keys. Default value is None.

offSkin

The skinning function to the inactive state (when sprite does not have keyboard focus).

onSkin

The skinning function to the active state (when sprite has keyboard focus).

submitKeys

Optional set of keyboard keys to accept for submission action. When one of these keys is pressed the sprite will make result available via isReady method and will optionally switch keyboard focus for the next scene object, if any. Default value is CPKeyboardKey.KEY_ENTER.

tags

Optional set of organizational or grouping tags. By default, the empty set is used.

visLen

Visible length of this field.

x

X-coordinate of the top-left corner.

y

Y-coordinate of the top-left corner.

z

Z-index at which to render this sprite.

Example:

See CPTextInputExample class for the example of using labels and text input.

Source:
CPTextInputSprite.scala

Utility that provides tile mapping functionality.

Utility that provides tile mapping functionality.

Example:

See CPTileMapperExample class for the example of using tile mapper.

Source:
CPTileMapper.scala
abstract class CPVideo(id: String, origin: String, tags: Set[String]) extends CPGameObject with CPAsset

Definition of the video.

Definition of the video.

Video rendered in ASCII character is rather an acquired taste... However, when used carefully and tastefully it can provide striking visuals for ASCII-based game. There are plenty of tooling available that can help you to convert a standard video like MP4 into a set of JPEG images and then convert these images into ASCII art images. Once you have ASCII art images you can use CosPlay video support to playback that video.

Video support consists of three key components:

Video is defined as a sequence of same-sized frames where each frame is an image. CPVideoSprite provides rendering of that video while CPVideoSpriteListener allows the video playback to synchronize with other action in the game like sound or animation.

Video is an asset. Just like other assets such as fonts, sounds, animations or videos they are not managed or governed by the CosPlay game engine unlike scenes and scene objects that are managed and governed by the game engine. Assets are typically created outside the game loop and managed by the developer, they can be freely shared between scenes or scene objects as any other standard Scala objects.

Here's some useful links for ASCII videos:

Value parameters:
id

ID for this video.

origin

The origin of this video: file path or URL.

tags

Optional set of organizational tags. Default is an empty set.

Example:

See CPVideoExample class for the example of using video support.

Companion:
object
Source:
CPVideo.scala
object CPVideo

Companion object provides utility functions.

Companion object provides utility functions.

Companion:
class
Source:
CPVideo.scala
class CPVideoSprite(id: String, vid: CPVideo, x: Int, y: Int, z: Int, fps: Int, autoPlay: Boolean, loop: Boolean, collidable: Boolean, shaders: Seq[CPShader]) extends CPSceneObject

Scene object tailor-made for rendering videos.

Scene object tailor-made for rendering videos.

Video support consists of three key components:

Video is defined as a sequence of same-sized frames where each frame is an image. CPVideoSprite provides rendering of that video while CPVideoSpriteListener allows the video playback to synchronize with other action in the game like sound or animation. Note that video sprite does not provide any playback controls out of the box.

Sprites

CosPlay provides number of built-in sprites. A sprite is a scene objects, visible or off-screen, that is custom designed for a particular use case. Built-in sprites provide concrete implementations for the abstract methods in the base CPSceneObject class. Most non-trivial games will use combination of the built-in sprites and their own ones. Here's the list of the built-in sprites:

Here's some useful links for ASCII video in general:

Value parameters:
autoPlay

Whether to autoplay the video.

collidable

Whether or not this sprite has a collision shape. Default is false.

fps

Frame-per-second to use in rendering the video.

id

Optional ID of the sprite.

loop

Whether or not to loop the playback.

shaders

Optional sequence of shaders for this sprite. Default value is an empty sequence.

vid

Video to render.

x

Initial X-coordinate of the sprite.

y

Initial Y-coordinate of the sprite.

z

Z-index at which to render the image.

Example:

See CPVideoExample class for the example of using video support.

Source:
CPVideoSprite.scala

Listener for CPVideoSprite playback.

Listener for CPVideoSprite playback.

You can add and remove this listener to video sprite using CPVideoSprite.addListener and CPVideoSprite.removeListener methods.

Video support consists of three key components:

Video is defined as a sequence of same-sized frames where each frame is an image. CPVideoSprite provides rendering of that video while CPVideoSpriteListener allows the video playback to synchronize with other action in the game like sound or animation. Note that video sprite does not provide any playback controls out of the box.

Here's some useful links for ASCII video in general:

See also:
Example:

See CPVideoExample class for the example of using video support.

Source:
CPVideoSpriteListener.scala
final case class CPZPixel(px: CPPixel, z: Int) extends Serializable

Immutable container that combines pixel and its Z-index.

Immutable container that combines pixel and its Z-index.

Value parameters:
px

Pixel.

z

Pixel's Z-index.

See also:
Source:
CPZPixel.scala

(0,0)-based pane for CPZPixel.

(0,0)-based pane for CPZPixel.

It is used for internal purposes only.

See also:
Companion:
object
Source:
CPZPixelPane.scala

Companion object with utility functions.

Companion object with utility functions.

Companion:
class
Source:
CPZPixelPane.scala

Value members

Concrete methods

def E[T](msg: String, cause: Throwable): T

Global syntax sugar for throwing CPException.

Global syntax sugar for throwing CPException.

Value parameters:
cause

Optional cause.

msg

Exception message.

Source:
CPEngine.scala