Guide to Annotations
NeuroKernel Applications may use a list of annotations to ease the code generation, configuration and caching. Here you will find the detailed explanation of each annotation used in NeuroKernel API. Some of these annotations can only be used with the main application class that extends the NApplication
class.
1. Configure Annotation
Configure
annotation is used to set the runtime preferences of a task. This annotation can only be used with application main class to be effective.
Method | Description |
---|---|
value | Name of the application |
pluggable | if true, application can be plugged into another application |
compileIn | Modules to include |
compileOut | Modules to exclude for smaller size |
socketTransport | If true and running at server, use web sockets to communicate |
target | Target NeuroKernel version |
import com.neurokernel.client.*; import com.neurokernel.client.annotation.Configure; import com.neurokernel.client.annotation.LoadResources; import com.neurokernel.client.annotation.Source; @LoadResources( resources = { @Source(value = "resources/banner.png", name = "banner") } ) @Configure(socketTransport=true) public class ConfigureExample extends NApplication { @Override public void main(int argc, String[] argv) { NFrame mainFrame=getMainFrame(); new NImageView(mainFrame, (NImage)getResource("banner")); mainFrame.setTitle("Configure"); mainFrame.setBounds(20,20,200,200); mainFrame.setVisible(true); } }
2. Executable Annotation
This annotation is used to create necessary bootstrap files for an application. It can only be used with classes extending NApplication
. Both Remote
and Executable
annotations can be used at the same time. Remote
annotation is used as target for generating bootstrap files if both are defined. Applications solely deployed to servlet container and require JRE to run at server side, does not need this annotation.
Method | Description |
---|---|
value | Name of the application |
archives | Resources to pre-load if any |
cache | Caches entire application to an offline storage |
compress | Also compress the generated files |
developerMode | Sets the developer mode |
mergedExecutable | Merge compiled code to a single file |
version | Application Version |
whiteList | List of whiteList sites |
workerOnly | Support executing application only in a worker |
workerSupport | Support executing application in a worker |
import com.neurokernel.client.*; import com.neurokernel.client.constants.CodeSegment; import com.neurokernel.client.annotation.Executable; import com.neurokernel.client.annotation.LoadResources; import com.neurokernel.client.annotation.Source; @Executable ( value = "Banner", version= "0.1", workerSupport=true, ) @LoadResources( resources = { @Source(value = "resources/banner.png", name = "banner") } ) public class ExecutableExample extends NApplication { @Override public void main(int argc, String[] argv) { NFrame mainFrame=getMainFrame(); new NImageView(mainFrame, (NImage)getResource("banner")); mainFrame.setTitle("Executable"); mainFrame.setBounds(20,20,200,200); mainFrame.setVisible(true); } }
2.1 Exclude Annotation
This annotation tells generator to exclude specified task container modules from the executable code to shrink the produced code size. This is for advanced development because wrong doing will break execution at some point. It is important to note that there must be either Excludes or Includes. Both can not be used, and first one defined will be taken and processed.
Method | Description |
---|---|
value | type of code segment |
2.2 Include Annotation
This annotation tells generator which task container modules to include in the executable code and omit the others to shrink the generated code size. This is for advanced development because wrong doing will break execution at some point.
Method | Description |
---|---|
value | type of code segment |
2.3 Code Segment Types
Code segments are the designators of sub modules available in a task container which can be included or excluded from the executable code to shrink the size of the file generated. This enum class is used with Exclude
and Include
annotations.
Code Segment | Description |
---|---|
CALLBACKS | Callback support |
DEVICES | Device support |
FILESYSTEMS | File System support |
GAMEPAD | Gamepad support |
MAINFRAME | Main frame and UI support |
PEERPORTS | Peer ports support |
PLUGIN | Plugin support |
PLUGIN_BRANCHES | Plugin Branch support |
PLUGIN_CANVAS | Plugin Canvas support |
PLUGIN_DEVICES | Plugin Device support |
PLUGIN_FILESYSTEM | Plugin File System support |
PORTS | Port handling support |
PROTOCOL_CACHE | Protocol cache support |
SERVICES | Service call support |
STORAGE | Client Storage support |
TERMINAL | Terminal IO support |
TORRENTS | Torrents support |
WEBSOCKET | Web Socket support |
WORKERS | Web Worker support |
3. Remote Annotation
This annotation is used to create necessary remotely accessible bootstrap files for an application. It can only be used with classes extending NApplication
.
Executable annotation will be ignored when Remote
annotation is used. There is an internal Executable annotation definition in Remote annotation.
Method | Description |
---|---|
value | Name of the application |
executable | Executable annotation for remote application |
addMetaData | Adds meta data to the boot strapping page |
arguments | Information about the arguments allowed |
author | Author of the application |
description | Description of the application |
desktopMode | Application may execute in desktop mode if available |
execCommand | Execute command of the application |
image | base64 URI encoded application icon image |
keywords | Keywords for the application for indexing by search engines |
title | Application title |
NeuroKernel meta tags generated for the remote application are listed below depending on the annotation configuration entered. An application may have more than one device implementation including a file system.
Meta Tag | Description |
---|---|
neurokernel:title | Name of the application |
neurokernel:version | Application title |
neurokernel:description | Description of the application |
neurokernel:image | base64 url encoded application icon image |
neurokernel:author | Author of the application |
keywords | Keywords for the application for indexing by search engines |
neurokernel:exec | Execute command of the application |
neurokernel:arguments | Information about the arguments allowed |
neurokernel:filesystem | file system is any implemented |
neurokernel:deviceX | Device X (X being the device number) |
neurokernel:deviceXname | Device X name |
neurokernel:deviceXversion | Device X version |
neurokernel:deviceXvendor | Device X vendor |
neurokernel:deviceXicon | Device X icon in base64 URI encoded format |
neurokernel:deviceXmethod | Device X method (multiple of these tags are allowed) |
import com.neurokernel.client.*; import com.neurokernel.client.annotation.*; @LoadResources( resources = { @Source(value = "resources/banner.png", name = "banner") } ) @Remote( value="appcachedemo", executable = @Executable ( version= "0.1", workerSupport=true, ) ); public class RemoteExample extends NApplication { @Override public void main(int argc, String[] argv) { NFrame mainFrame=getMainFrame(); new NImageView(mainFrame, (NImage)getResource("banner")); mainFrame.setTitle("Remote Example"); mainFrame.setBounds(20,20,200,200); mainFrame.setVisible(true); } }
4. LoadResources Annotation
LoadResources
tells bootstrap file generator to include the resources in the executable
so that task can automatically load resources and make them available from getResource
method of NApplication
class. This includes all runtime targets. This annotation can
only be used with application and container classes. For applications, which require JRE
to execute at server side, this annotation can still be used but the resources
must be manually put the required folders in the class path of the application.
Method | Description |
---|---|
value | name of the application |
loadIcon | Application icon is automatically searched |
resources | Resources to pre-load |
import com.neurokernel.client.*; import com.neurokernel.client.annotation.LoadResources; import com.neurokernel.client.annotation.Source; @LoadResources( resources = { @Source(value = "resources/myicon.gif", name = "appicon") @Source(value = "resources/banner.png", name = "banner"), }, loadIcon = false ) public class ResourcesExample extends NApplication { @Override public void main(int argc, String[] argv) { loadIcon((NImage)getResource("appicon")); NFrame mainFrame=getMainFrame(); new NImageView(mainFrame, (NImage)getResource("banner")); mainFrame.setTitle("Resources"); mainFrame.setBounds(20,20,200,200); mainFrame.setVisible(true); } }
4.1 Source Annotation
Source
annotation is used to define a source for a resource such as Image in LoadResources
annotation
Method | Description |
---|---|
value | Source data path |
binary | Resource is Binary or Text |
name | Resource name |
merge | Merge source to executable or deploy to server |
5. Device Annotation
A Plugin application can define one or more devices to be used by the parent application. The advantage of using a device is the way the IPC is used. Although the event based communication is still available to use, devices also introduce RPC methods that can be called by parents. This makes the use same type devices by different applications from different authors to be used for the same purpose. The devices must have the same footprint by their name and method definitions. Some commonly used devices may be standardized by NeuroKernel Research via an NDR (NeuroKernel Device Request). NDRs will be considered after NeuroKernel is widely adapted by the community.
Method | Description |
---|---|
value | Name of the device |
icon | Base64 URI encoded device icon |
methods | List of device methods |
target | Minimum targeted NeuroKernel version |
title | Short description of the device |
type | Device type |
vendor | Device vendor |
version | Device version |
visual | Device has visual either as an interface or presentation |
import com.neurokernel.client.system.ICallback; import com.neurokernel.client.device.*; import com.neurokernel.client.NApplication; import com.neurokernel.client.constants.DataType; import com.neurokernel.client.annotation.Device; import com.neurokernel.client.annotation.Method; import java.util.Date; @Device( value="NDayTime", type="DayTimeDevice", methods={ @Method(value="getTime",returnType=DataType.LONG), @Method(value="getDate",returnType=DataType.DATE) } ) public class NDayTimeDevice extends NApplication { Date currentDate=new Date(); NMethod getTime; @Override public void main(int argc, String[] argv) { NDevice deviceInfo=getSystem().getDevice(); if(deviceInfo!=null) { getTime=deviceInfo.getDeviceMethod("getTime").setCallProcessor(new IMethodCall() { @Override public Object process(IAsyncResponse response,Object... args) { return currentDate.getTime(); } }); deviceInfo.getDeviceMethod("getDate").setCallProcessor(new IMethodCall() { @Override public Object process(IAsyncResponse response,Object... args) { return currentDate; } }); } } }
5.1 Method Annotation
Devices can define any number of methods which are used for RPC (Remote Procedure Call). It is not used for implementation. It is used to create a device definition info so that it can be easily recognized and used by plugin container and plugin system itself.
Method | Description |
---|---|
value | Device method name |
description | Method description |
returnType | Return type of the method |
params | List of parameter types |
6. DeviceArray Annotation
An application can defined and handle any number of devices in itself. This annotation is used to define multiple device profiles.
Method | Description |
---|---|
devices | List of devices |
import com.neurokernel.client.*; import com.neurokernel.annotation.*; @DeviceArray( devices={ @Device( value="TempGauge", type="GaugeDevice", title="Temperature Gauge", visual=true, methods={ @Method(value="setValue",params=DataType.INTEGER), } ), @Device( value="NDayTime", type="DayTimeDevice", methods={ @Method(value="getTime",returnType=DataType.LONG), @Method(value="getDate",returnType=DataType.DATE) } ) } ) public class DeviceArray extends NApplication { Date currentDate=new Date(); NMethod getTime; NGauge gauge; @Override public void main(int argc, String[] argv) { NFrame mainFrame=getMainFrame(); renderGauge(mainFrame); NDevice deviceInfo=getSystem(). getDeviceByType("DayTimeDevice"); getTime=deviceInfo.getDeviceMethod("getTime").setCallProcessor(new IMethodCall() { @Override public Object process(IAsyncResponse response,Object... args) { return currentDate.getTime(); } }); deviceInfo.getDeviceMethod("getDate").setCallProcessor(new IMethodCall() { @Override public Object process(IAsyncResponse response,Object... args) { return currentDate; } }); deviceInfo=getSystem().getDeviceByType("GaugeDevice"); deviceInfo.getDeviceMethod("setValue").setCallProcessor(new IMethodCall() { @Override public Object process(IAsyncResponse response,Object... args) { gauge.setValue((Integer)args[0],false); return null; } }); } private void renderGauge(NContainer container) { gauge=new NGauge(container); gauge.setMinimum(-50); gauge.setMaximum(50); gauge.setName("Temperature"); gauge.setStrokeTicks(false); gauge.setShadowGlow(true); gauge.setUnits("°C"); gauge.setColor(NGauge.GaugePart.PLATE, new NColor(0x22,0x22,0x22)); gauge.setColor(NGauge.GaugePart.MAJOR_TICKS, new NColor(0xf5,0xf5,0xf5)); gauge.setColor(NGauge.GaugePart.MINOR_TICKS, new NColor(0xdd,0xdd,0xdd)); gauge.setColor(NGauge.GaugePart.TITLE, NColor.WHITE); gauge.setColor(NGauge.GaugePart.NUMBERS, new NColor(0xee,0xee,0xee)); gauge.setMajorTicks("-50","-40","-30","-20","-10","0","10","20","30","40","50"); gauge.setValueBox(new NGaugeValueBox().setValueFormat(2,2)); gauge.addColorRange(-50, 0, new NColor(0,255,0,50)); gauge.addColorRange(0, 50, new NColor(255,0,0,50)); gauge.setValue(0,false); container.setBackground(NColor.BLACK); } }
7. ProtocolCache Annotation
Applications can cache their protocol from the initial launch to up until the main window is fully visible on the screen. This will increase the launch speed of the applications because protocol is already created for the main window and stored. Protocol can be stored to persistent storage if available so that when the same application is executed again in a new session, system will pick its initial protocol from the persistent storage and immediately process it. Initial protocol for each window can also be cached to persistent storage. For remote applications, request to access to the data storage may be asked by the browser.
Method | Description |
---|---|
value | Name of the protocol cache point |
clearif | Clears the protocol cache from storage if given name exists |
dynamic | Protocol cache is allowed to take multiple paths if true |
persist | Stores the protocol to persistent client storage if true |
loadFromResource | Loads a cached protocol from a resource or file (default false) |
saveToFile | Saves cached protocol to a file (default false) |
import com.neurokernel.client.*; import com.neurokernel.client.annotation.*; @ProtocolCache("ProtocolCache") public class ProtocolCacheExample extends NApplication { @Override public void main(int argc, String[] argv) { NFrame mainFrame=getMainFrame(); new NButton(mainFrame, "Hello"); mainFrame.setTitle("Protocol Cache Example"); mainFrame.setBounds(20,20,200,200); mainFrame.setVisible(true); } }
8. ApplicationCache Annotation
NeuroKernel client side applications can be cached to the browser for offline access. This may be particularly useful if the site to the application is down. Service workers are supported including fallback to AppCache mode. There may be client based limitations that could be solved in a later version. Please take note that, the site must have an HTTPS certification for this to work.
Method | Description |
---|---|
value | Name of the service installer |
cacheAll | List of files to cache |
fallback | Allow falling back to AppCache |
rootURL | AppCache manifest only |
version | Cache version |
import com.neurokernel.client.*; import com.neurokernel.client.annotation.*; @LoadResources( resources = { @Source(value = "resources/banner.png", name = "banner"), } ) @Executable( cache = { @ApplicationCache(version = "1.0") } ) public class AppCacheExample extends NApplication { @Override public void main(int argc, String[] argv) { NFrame mainFrame=getMainFrame(); new NImageView(mainFrame, (NImage)getResource("banner")); mainFrame.setTitle("AppCache Example"); mainFrame.setBounds(20,20,200,200); mainFrame.setVisible(true); } }