6.0 Extension and Controlling API Transition Guide

Robert Grider edited this page Feb 6, 2018 · 12 revisions

This is a guide for extension authors about how NetLogo internals have changed in NetLogo 6.0.


A number of classes have been renamed. The following is a list of top-level, public classes known to have changed. If your extension depended on inner classes or package-private classes, those will not be listed here.

  • api.CompilerException -> core.CompilerException
  • api.ErrorSource -> core.ErrorSource
  • api.File -> core.File
  • api.FileMode -> core.FileMode
  • api.I18N -> core.I18N
  • api.Instruction -> core.Instruction
  • api.Let -> core.Let
  • api.LogoList -> core.LogoList
  • api.Nobody -> core.Nobody
  • api.PlotPenInterface -> core.PlotPenInterface (some changes)
  • api.Primitive -> core.Primitive
  • api.Program -> core.Program
  • api.Shape -> core.Shape
  • api.ShapeList -> core.ShapeList
  • api.Task -> api.AnonymousProcedure
  • api.CommandTask -> api.AnonymousCommand
  • api.ReporterTask -> api.AnonymousReporter
  • api.Token -> core.Token (several fields renamed as well)
  • api.TokenType -> core.TokenType
  • api.TokenizerInterface -> core.TokenizerInterface
  • api.WorldDimensions -> core.WorldDimensions (now immutable)
  • compiler.Instantiator -> core.Instantiator
  • util.MersenneTwisterFast -> api.MersenneTwisterFast
  • util.Exceptions -> api.Exceptions
  • nvm.Workspace.UpdateMode -> core.UpdateMode
  • nvm.Workspace.OutputDestination -> api.OutputDestination
  • More renames are likely to be listed in the future...

Java 8 Changes

General notes

  • Many swing classes are now generic
  • Thread.stop() now errors

JOGL and java3D

Java 3D is not supported in Java 8. We upgraded JOGL in the 5.3 series of releases and it is also updated here. The primary difference is the package formerly known as javax.media.opengl is now com.jogamp.opengl. More complex refactors will be needed in some cases involving scala due to the way scala handles static interface members. Those cases can usually be resolved by changing the name of a class or interface from something like GL to something like GL2 or GL2ES3.

Non-Rename Changes

Simplification of the ExtensionManager API

The following methods have been removed from api.ExtensionManager:

  • getExtensionNames - use loadedExtensions instead.
  • getJarPaths - no longer needed now that applets are dead.
  • getSource - use workspace.getSource instead.
  • getFile - use workspace.fileManager.getFile(workspace.attachModelDir) instead.
  • profilingEnabled - check if the profiler extension is one of the loadedExtensions instead.
  • addToLibraryPath - avoid using if possible, but if needed use org.nlogo.api.JavaLibraryPath.setLibraryPath(classManager.getClass, directoryName).
  • resolvePath - use new java.io.File(workspace.attachModelDir(path)) if needed.
  • resolvePathAsURL - this was most useful for applets. If you need a file, see resolvePath above, otherwise use workspace.attachModelDir or new java.net.URL.

In addition, ExtensionManager has been split into core.ExtensionManager and api.ExtensionManager. This split is purely for interface segregation and extension code should continue to use api.ExtensionManager.

Changes to org.nlogo.api.Program

The representation of a NetLogo Program has changed dramatically. The class representing a program is now located in the org.nlogo.core package. Users are advised to consult the source code for a more thorough look at the changes, but the following are some highlights:

  • scala.collection.Seq is used for list representations instead of java.util.List.
  • Programs now contain a "dialect", a container for miscellaneous information about the environment (3D vs 2D, Desktop vs Web).
  • The handling of breeds is quite different. Breeds are now represented as case classes (see org.nlogo.core.Breed) which are stored in a map by name.
  • userGlobals and interfaceGlobals are available as separate methods or combined in the globals method along with observer variables.
  • Since the breeds are no longer AgentSets, AgentSets containing the agents within a breed should be retrieved from the World.

core.AgentKind replaces Agent.class as way to identify agent type

The following table shows replacements:

5.x java hexy java 5.x scala hexy scala
Class<? extends Agent> org.nlogo.core.AgentKind Class[_ <: Agent] org.nlogo.core.AgentKind
Patch.class org.nlogo.core.AgentKindJ.Patch() classOf[Patch] org.nlogo.core.AgentKind.Patch
Turtle.class org.nlogo.core.AgentKindJ.Turtle() classOf[Turtle] org.nlogo.core.AgentKind.Turtle
Link.class org.nlogo.core.AgentKindJ.Link() classOf[Link] org.nlogo.core.AgentKind.Link
Observer.class org.nlogo.core.AgentKindJ.Observer() classOf[Observer] org.nlogo.core.AgentKind.Observer
<agent>.getClass() <agent>.kind() <agent>.getClass <agent>.kind
<agentset>.type() <agentset>.kind() <agentset>.`type` <agentset>.kind

Additionally, the following points are worth noticing:

  • AgentSets (and their builders) take an AgentKind.
  • Agent has a kind method which returns the kind of that agent.

Changes to nvm.Procedure

The following were formerly fields on nvm.Procedure and are now methods:

  • topLevel
  • code
  • args
  • fileName (available as an alias for filename)
  • name
  • displayName
  • localsCount
  • pos
  • end

No longer available:

  • topLevel


  • taskFormals -> lambdaFormals
  • getTaskFormal -> getLambdaFormal
  • isTask -> isLambda
  • usableBy -> agentClassString
  • tyype -> isReporter (also changed from an enum to a boolean)

Changes to org.nlogo.api.JobOwner

  • innerSource(String) has been changed to innerSource_=(String) (scala) and innerSource_$eq(String) java

Renames for task to anonymous procedure

Renames in org.nlogo.api.Argument

  • getReporterTask has been renamed to getReporter
  • getCommandTask has been renamed to getCommand

Renames in org.nlogo.core.Syntax

  • Syntax.ReporterTaskType has been renamed to Syntax.ReporterType
  • Syntax.CommandTaskType has been renamed to Syntax.CommandType

Removal of DefaultCommand and DefaultReporter

Instead of org.nlogo.api.DefaultCommand and org.nlogo.api.DefaultReporter, use org.nlogo.api.Command and org.nlogo.api.Reporter. In addition to renaming the superclass, if your primitive overrides getAgentClassString set that in the Syntax returned by getSyntax. If you use core.Syntax in scala, provide the appropriate named parameter and if you use core.SyntaxJ in java, call any of the methods which take agentClassString as a parameter.

world is no longer a field / method on AgentSet

When constructing an AgentSet, a world is no longer needed. The world method has been removed from AgentSet. A world method has been added to ExtensionContext for easy access to the world.

Changes to ExtensionContext

  • A world method has been added to ExtensionContext for easy access to the world.
  • The logCustomMessage and logCustomGlobals methods have been removed from ExtensionContext. These can be replaced by calls to the appropriate methods on the workspace.

Syntax representation

org.nlogo.core.Syntax replaces org.nlogo.api.Syntax methods. core.SyntaxJ is recommended for Java users, but it returns the same core.Syntax objects produced by core.Syntax.

Observer changes

If your code depends on the perspective and/or location of the observer, you should review the changes made to org.nlogo.api.Observer. The primary change is the extraction of orientation into a scala.Option. This has been done to allow headless code to share the API for observer with NetLogo GUI without tracking irrelevant observer location information.

api.World changes

api.World has had an interface - api.WorldRenderable extracted from it which has various methods on world dealing with rendering updates. If your use of world depends on any of the methods in api.WorldRenderable, you should modify your extension to check that the world you are using implements WorldRenderable before performing those operations on it.


  • Extension code which formerly made use of org.nlogo.util.Femto should switch to org.nlogo.core.Femto. org.nlogo.util.Femto is likely to be removed in a future release.

Added functionality

Improvements to api.Context

api.Context now has world and workspace methods which make it possible to access the current world and workspace without needing to cast the Context to an ExtensionContext. It is recommended that extensions which do cast to an ExtensionContext rely on Context.workspace and the methods on api.Workspace if possible.

Introduction of api.Workspace

api.Workspace was introduced in 6.0 and makes available a wealth of functionality which formerly was only available on nvm.Workspace. Since it's part of the api package, api.Workspace should remain binary-compatible for the duration of the 6.0 extensions API.

Changes to LogoList

LogoList was moved from org.nlogo.api to org.nlogo.core. api.LogoList implemented java.util.AbstractSequentialList<AnyRef> while core.LogoList does not implement it. It is possible to turn a LogoList into an AbstractSequentialList by using toJava (see table below). LogoList now implements scala.collection.IndexedSeq[AnyRef], giving it access to a number of powerful features accessible from Scala extensions. It also had a substantial number of method renames, see the table below:

5.x name hexy name type
iterator javaIterator java.util.Iterator<AnyRef>
scalaIterator iterator scala.collection.Iterator[AnyRef]
- javaIterable java.lang.Iterable[AnyRef]
- apply(i: Int) AnyRef
- toJava java.util.AbstractSequentialList<AnyRef>

Addendum: non-API changes from 6.0.1 to 6.0.2

Moving from 6.0.1 to 6.0.2 brought some fairly large changes to non-API classes.

Note that while a great deal of code (especially Scala code) using classes which have changed (per the below listing) will remain source-compatible, it is very likely to require recompilation before working 6.0.2 because of binary incompatibility. This will be true for most code which called methods on org.nlogo.agent.World or org.nlogo.agent.Turtle. Extensions which used only the API classes (org.nlogo.api.Turtle / org.nlogo.api.World) are unlikely to need recompilation for 6.0.2.

Following is a more complete listing of changes:

  • org.nlogo.agent.LogoHashObject has been removed. Use org.nlogo.api.LogoHashObject instead
  • org.nlogo.agent.Topology.getPatchAt has been removed. Use org.nlogo.agent.World.getPatchAt instead
  • org.nlogo.agent.Agent (and its subclasses) no longer implement java.util.Observable. Use org.nlogo.agent.World.addWatcher (and related methods) instead.
  • org.nlogo.agent.Agent (and its subclasses) no longer have the methods getAgentBit or getAgentClass. Use org.nlogo.agent.Agent.kind instead.
  • org.nlogo.agent.Agent no longer defines getObserverVariable / setObserverVariable.
  • org.nlogo.agent.World is no longer a concrete class and has been split into a hierarchy of classes and traits. Most of these are implementation details, but the general structure is as follows:
    • Most uses of org.nlogo.agent.World in 6.0.1 can be replaced by uses of org.nlogo.agent.World2D in 6.0.1 (except in those cases where NetLogo 3D is concerned, which will require the use of org.nlogo.agent.World3D instead).
    • org.nlogo.agent.World is now a Scala abstract class (Java authors may see it as an interface instead) which defines many of the same methods defined on World in 6.0.1, but missing those methods which assumed a 2D world.
    • org.nlogo.agent.CoreWorld and org.nlogo.agent.WorldKernel are base classes of org.nlogo.agent.World. Extension authors (and controlling API authors) should avoid using them as they are very likely to change in future releases
  • org.nlogo.agent.Turtle was a concrete class in 6.0.1, but in 6.0.2 has been split into several classes (like World).
    • org.nlogo.agent.Turtle contains shared methods between 2D and 3D
    • When instantiating a turtle, instantiate org.nlogo.agent.Turtle2D or org.nlogo.agent.Turtle3D.
    • 2D/3D-specific turtle methods should not be accessed before checking whether the turtle is actually a Turtle2D or a Turtle3D.
  • org.nlogo.agent.Observer.perspective(Perspective) was renamed to setPerspective(Perspective)
  • The constraint methods on observer have been renamed as follows:
    • assertVariableConstraint -> assertConstraint
    • variableConstraint(int) -> constraint(int)
    • variableConstraint(int, ValueConstraint) -> setConstraint(int, ValueConstraint)
  • org.nlogo.agent.Agent.variables is now a method instead of a field
  • org.nlogo.agent.Agent.id is now a method instead of a field
  • org.nlogo.agent.Agent.getVariableCount is no longer a method. Use org.nlogo.agent.Agent.variables().length.
  • The constraint methods assertVariableConstraint and variableConstraint have been removed from org.nlogo.agent.Agent. They are still available on org.nlogo.agent.Observer
  • The org.nlogo.agent.Patch.pcolorDouble() method has been removed. Use org.nlogo.agent.Patch.pcolor() instead and check the result, which can be either a java.lang.Double or an org.nlogo.core.LogoList.
  • org.nlogo.agent.World.ZERO and org.nlogo.agent.World.ONE have been removed. Use org.nlogo.agent.World.Zero() and org.nlogo.agent.World.One() instead.
  • org.nlogo.agent.World has had the following fields converted to methods:
    • tickCounter
    • inRadiusOrCone
    • tieManager
    • linkManager
    • linkBreedShapes
  • The following methods no longer exist on org.nlogo.agent.World. Although some of them are methods on World2D, we recommend against using them if at all possible:
    • rememberOldProgram()
    • compiler()
    • compiler_=(Compiler)
    • program(Program)
  • org.nlogo.nvm.AnonymousProcedure and org.nlogo.nvm.AnonymousCommand both are now initialized with an additional 5th parameter which contains the source code used to create them. Extension authors who instantiate these classes should provide a string indicating something about the contents of the anonymous procedure (and preferably the name of the extension that created it).
  • org.nlogo.core.BoxedValue.multiline no longer exists. multiline is still defined on org.nlogo.core.StringInput. We try to avoid breaking changes to the core and api modules between releases. We made a change here because we believe no extensions will be affected.
  • There are various changes to core primitive classes in org.nlogo.core.prim (and subpackages).
  • org.nlogo.swing.BrowserLauncher.openURL is now deprecated. We advise that extension authors use the openPath or openURI methods (also defined on BrowserLauncher) instead.
  • Various changes to classes in org.nlogo.app, org.nlogo.prim, and org.nlogo.workspace which should not affect most extensions.
  • The Pegdown library is no longer included with NetLogo. NetLogo now uses the flexmark-java library instead for markdown processing. If your extension relied on having the Pegdown library on the classpath, upgrade it to use flexmark.
  • org.nlogo.api.ValueSet and org.nlogo.api.EnumeratedValueSet are now deprecated. Use org.nlogo.api.RefValueSet and org.nlogo.api.RefEnumeratedValueSet instead.

Addendum: Proposed API and non-API changes after 6.0.2

  • Consolidate AbstractWorkspace and AbstractWorkspaceScala into a unified AbstractWorkspace
  • org.nlogo.workspace.ExtensionManager no longer has a method to access the workspace (this method was formerly workspace). Proposed replacement is to use the workspace provided by the Context passed into each primitive at execution.
  • org.nlogo.api.HubNetWorkspaceInterface no longer implements CompilerServices, has a field compilerServices which provides those services.
  • org.nlogo.api.VersionHistory no longer has the methods olderThan3DPreview3, olderThan3DPreview4, olderThan3DPreview5.
  • org.nlogo.app.App no longer has the following methods:
    • logger (Reference App.app.logger instead)
    • makeWidget (call makeWidget on the interfacePanel instead)
    • commandLine* methods. Interrogate App.app.params instead
  • The following methods are deprecated (need to add suggestions for replacement):
    • org.nlogo.api.Version.is3D
    • org.nlogo.api.ModelReader.modelSuffix
    • org.nlogo.api.ModelReader.emptyModelPath
  • org.nlogo.api.WorldDimensions3D is deprecated. Use org.nlogo.core.WorldDimensions3D instead.
  • ModelSaver is deprecated
  • org.nlogo.util.Pico has been moved to org.nlogo.api.Pico. Note that we do not recommend extension authors use this class (and have marked it private[nlogo] to that end).
  • api.AggregateManagerInterface, api.HubNetInterface, and api.PreviewCommands no longer extend ModelSections.ModelSaveable (and thus no longer have an updateModel(Model): Model method. We do not expect this to affect extension authors.
Clone this wiki locally
You can’t perform that action at this time.
You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session.
Press h to open a hovercard with more details.