blob: 3b7759366b1feb3850cd0b9acf1e714e0d3bdfc9 [file] [log] [blame]
<!DOCTYPE html><html lang="en-us" >
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="generator" content="Source Themes Academic 4.8.0">
<meta name="author" content="Fraunhofer FOKUS">
<meta name="description" content="">
<link rel="alternate" hreflang="en-us" href="https://www.eclipse.org/mosaic/tutorials/barnim_advanced/">
<meta name="theme-color" content="#68145C">
<script src="/mosaic/js/mathjax-config.js"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/academicons/1.8.6/css/academicons.min.css" integrity="sha512-MCWBwPSput2UWNwyznVFLbD2iUc1e5VsdD1zahsWVzkDSUzyHhMZ4kCS3wgYSRm0mU+glwD/Q9lSJrDPwbUL2A==" crossorigin="anonymous">
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.12.0-1/css/all.min.css" integrity="sha512-ZYg+hQvLlM0W9C3P6vTpes5LmJ66G2EsroxDNzwD6qiulckldb29eD9I672HL2X+LH5nRhY1sQqZLJGB+aUUPg==" crossorigin="anonymous">
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/fancybox/3.5.7/jquery.fancybox.min.css" integrity="sha512-H9jrZiiopUdsLpg94A333EfumgUBpO9MdbxStdeITo+KEIMaNfHNvwyjjDJb+ERPaRS6DpyRlKbvPUasNItRyw==" crossorigin="anonymous">
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/styles/atom-one-light.min.css" crossorigin="anonymous" title="hl-light">
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/styles/atom-one-light.min.css" crossorigin="anonymous" title="hl-dark" disabled>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/leaflet/1.5.1/leaflet.css" integrity="sha512-xwE/Az9zrjBIphAcBb3F6JVqxf46+CDLwfLMHloNu6KEQCAWi6HcDUbeOfBIptF7tcCzusKFjFw2yuvEpDL9wQ==" crossorigin="anonymous">
<script src="https://cdnjs.cloudflare.com/ajax/libs/lazysizes/5.2.2/lazysizes.min.js" integrity="sha512-TmDwFLhg3UA4ZG0Eb4MIyT1O1Mb+Oww5kFG0uHqXsdbyZz9DcvYQhKpGgNkamAI6h2lGGZq2X8ftOJvF/XjTUg==" crossorigin="anonymous" async></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/3.1.0/es5/tex-chtml.min.js" integrity="sha512-uwL1UtpYdWra2iqJlAW8Ts0s9Os6IxWLDJDF/BnWdhDmT7DEMFba3GPsFwmV3QiTNcUyl2GB5vsgycB/MOvo9g==" crossorigin="anonymous" async></script>
<link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Lato:400,400i,700,700i%7CRoboto+Mono&display=swap">
<link rel="stylesheet" href="/mosaic/css/academic.css">
<link rel="alternate" href="/mosaic/tutorials/barnim_advanced/index.xml" type="application/rss+xml" title="Eclipse MOSAIC – A Multi-Domain and Multi-Scale Simulation Framework for Connected and Automated Mobility">
<link rel="manifest" href="/mosaic/index.webmanifest">
<link rel="icon" type="image/png" href="/mosaic/images/icon_hu6bdfb97c7e23190c70e41ca0e15a9fce_30436_32x32_fill_lanczos_center_2.png">
<link rel="apple-touch-icon" type="image/png" href="/mosaic/images/icon_hu6bdfb97c7e23190c70e41ca0e15a9fce_30436_192x192_fill_lanczos_center_2.png">
<link rel="canonical" href="https://www.eclipse.org/mosaic/tutorials/barnim_advanced/">
<meta property="twitter:card" content="summary">
<meta property="og:site_name" content="Eclipse MOSAIC – A Multi-Domain and Multi-Scale Simulation Framework for Connected and Automated Mobility">
<meta property="og:url" content="https://www.eclipse.org/mosaic/tutorials/barnim_advanced/">
<meta property="og:title" content="Barnim Advanced | Eclipse MOSAIC – A Multi-Domain and Multi-Scale Simulation Framework for Connected and Automated Mobility">
<meta property="og:description" content=""><meta property="og:image" content="https://www.eclipse.org/mosaic/images/logo.svg">
<meta property="twitter:image" content="https://www.eclipse.org/mosaic/images/logo.svg"><meta property="og:locale" content="en-us">
<meta property="og:updated_time" content="2019-05-05T00:00:00&#43;01:00">
<title>Barnim Advanced | Eclipse MOSAIC – A Multi-Domain and Multi-Scale Simulation Framework for Connected and Automated Mobility</title>
</head>
<body id="top" data-spy="scroll" data-offset="70" data-target="#TableOfContents" class=" page-mosaic page-tutorials page-barnim_advanced ">
<aside class="search-results" id="search">
<div class="container">
<section class="search-header">
<div class="row no-gutters justify-content-between mb-3">
<div class="col-10 col-md-3">
<div class="logo" style="background-image: url(/mosaic/img/logos/mosaic/EclipseMOSAIC-Logo-RGB-positiv.svg)"></div>
</div>
<div class="col-2 col-md-4 col-search-close">
<a class="js-search" href="#"><i class="fas fa-times-circle text-muted" aria-hidden="true"></i></a>
</div>
</div>
<div id="search-box">
<input name="q" id="search-query" placeholder="Search..." autocapitalize="off"
autocomplete="off" autocorrect="off" spellcheck="false" type="search">
</div>
</section>
<section class="section-search-results">
<div id="search-hits">
</div>
</section>
</div>
</aside>
<nav class="navbar navbar-expand-lg navbar-light compensate-for-scrollbar" id="navbar-main">
<div class="container">
<div class="d-none d-lg-inline-flex">
<a style="visibility:visible;" class="navbar-brand" href="/mosaic/"><img src="/mosaic/images/logo.svg" alt="Eclipse MOSAIC – A Multi-Domain and Multi-Scale Simulation Framework for Connected and Automated Mobility"></a>
</div>
<button type="button" class="navbar-toggler" data-toggle="collapse"
data-target="#navbar-content" aria-controls="navbar" aria-expanded="false" aria-label="Toggle navigation">
<span><i class="fas fa-bars"></i></span>
</button>
<div class="navbar-brand-mobile-wrapper d-inline-flex d-lg-none">
<a class="navbar-brand" href="/mosaic/"><img src="/mosaic/images/logo.svg" alt="Eclipse MOSAIC – A Multi-Domain and Multi-Scale Simulation Framework for Connected and Automated Mobility"></a>
</div>
<div class="navbar-collapse main-menu-item collapse justify-content-start" id="navbar-content">
<ul class="navbar-nav d-md-inline-flex">
<li class="nav-item">
<a class="nav-link " href="/mosaic/about"><span>About</span></a>
</li>
<li class="nav-item">
<a class="nav-link " href="/mosaic/news"><span>News</span></a>
</li>
<li class="nav-item">
<a class="nav-link " href="/mosaic/docs"><span>Documentation</span></a>
</li>
<li class="nav-item">
<a class="nav-link active" href="/mosaic/tutorials"><span>Tutorials</span></a>
</li>
<li class="nav-item">
<a class="nav-link " href="/mosaic/download"><span>Download</span></a>
</li>
<li class="nav-item">
<a class="nav-link " href="/mosaic/community"><span>Community</span></a>
</li>
</ul>
</div>
<ul class="nav-icons navbar-nav flex-row ml-auto d-flex pl-md-2">
<li class="nav-item">
<a class="nav-link js-search" href="#" aria-label="Search"><i class="fas fa-search" aria-hidden="true"></i></a>
</li>
<li class="nav-item ">
<a href="https://github.com/eclipse/mosaic" target="blank">
<i class="fab fa-github" aria-hidden="true"></i>
</a>
</li>
</ul>
</div>
</nav>
<div class="universal-wrapper pt-3">
<h1>Barnim Advanced</h1>
</div>
<div class="universal-wrapper">
<div class="article-style"><div class="alert alert-note">
<div>
<p>All files you need for this tutorial are included in the Eclipse MOSAIC zip file:<br>
<strong><a href="/mosaic/download" title="Download Eclipse MOSAIC">Download Eclipse MOSAIC</a></strong></p>
</div>
</div>
<p>The <strong>Barnim Advanced</strong> tutorial extends the preceding tutorial and focuses on the implementation of applications
used in the Barnim scenario. In this section, the actual source code used to create the applications is explained,
giving a first impression on the API of the <strong>Eclipse MOSAIC Application</strong> simulator. After completing this tutorial you will be able to:</p>
<ul>
<li>Define an arbitrary geographical area (e.g. circular, rectangular) and allow broadcast communication in this defined area.</li>
<li>Use and react to DENMs (Decentralized Environmental Notification Message), respectively create a specific message according to the requirements.</li>
<li>Transmit and receive V2X-messages periodically or on request depending on the network type and communication mode (e.g. Topocast, Geocbroadcast, etc.).</li>
<li>Calculating of alternative routes to the destination to circumnavigate a road obstacle.</li>
</ul>
<p>As mentioned in
<a href="/tutorials/barnim_basic/#overview-of-applications">Barnim Basic</a>, the Barnim tutorial is structured in four applications.</p>
<ol>
<li><code>WeatherServer</code> - Broadcasts information about bad road conditions via cellular communication.</li>
<li><code>WeatherWarningApp</code> - Detects bad road conditions, broadcasts information via ITS-G5, circumnavigates areas with bad road conditions.</li>
<li><code>WeatherWarningAppCell</code>- Receives messages from <code>WeatherServer</code>, circumnavigates areas with bad road conditions.</li>
<li><code>SlowDownApp</code> - Models driver behavior by slowing the vehicle down as soon as it enters an affected road segment.</li>
</ol>
<h3 id="weatherserver-application">WeatherServer Application</h3>
<p>Basically, the <code>WeatherServer</code> is an enhanced RSU which has knowledge about the hazardous area and it is responsible to
transmit DEN-Messages periodically to vehicles equipped with <code>WeatherWarningAppCell</code>-application via cellular communication.
Firstly, the hazardous area (Road-ID and GeoPoint coordinates), the type of the warning (Sensor type), message interval
and the resulted speed will be defined to be used later:</p>
<pre><code class="language-java">private final static long INTERVAL = 2 * TIME.SECOND;
private final static GeoPoint HAZARD_LOCATION = GeoPoint.latlon(52.633047, 13.565314);
private final static String HAZARD_ROAD = &quot;-3366_2026362940_1313885502&quot;;
private final static SensorType SENSOR_TYPE = SensorType.Ice;
private final static float SPEED = 25 / 3.6f;
</code></pre>
<p>During the initialization procedure of communicating applications, the communication module (CellModule) needs to be
activated. This is achieved in the <code>onStartup()</code>-method. The following code snipped shows the activating the
CellModule as communication mode:</p>
<pre><code class="language-java">public void onStartup() {
getLog().infoSimTime(this, &quot;Initialize WeatherServer application&quot;);
getOperatingSystem().getCellModule().enable();
getLog().infoSimTime(this, &quot;Activated Cell Module&quot;);
sample();
}
</code></pre>
<p>A DENM will be transmitted in <strong>2s</strong> intervals (as configured above) to the vehicles equipped with cellular
communication within reach as an event;</p>
<pre><code class="language-java">private void sample() {
final Denm denm = constructDenm();
getOperatingSystem().getCellModule().sendV2xMessage(denm);
getLog().infoSimTime(this, &quot;Sent DENM&quot;);
getOperatingSystem().getEventManager().addEvent(new Event(getOperatingSystem().getSimulationTime() + INTERVAL, this));
}
</code></pre>
<p>The <code>Event</code> created in this method is passed with a <code>this</code> argument, which represents an <code>EventProcessor</code> which gets notified
as soon as the proposed event time is reached. As this class implements the <code>EventProcessor</code> interface, the method
<code>processEvent()</code> will be called by the application simulator ons the simulation time is reached:</p>
<pre><code class="language-java">@Override
public void processEvent(Event event) throws Exception {
sample();
}
</code></pre>
<p>Finally, in the method <code>contructDenm</code>, the necessary data will be added to a message container <code>DenmContent</code> and we create
a circular area for the rerouting (3000 m) of the DEN-Message as Broadcast. All vehicles within this area which
have the cellular module activated, will receive this message.</p>
<pre><code class="language-java">private Denm constructDenm() {
final GeoCircle geoCircle = new GeoCircle(HAZARD_LOCATION, 3000.0D);
final MessageRouting routing = getOperatingSystem().getCellModule().createMessageRouting().geoBroadCast(geoCircle);
final int strength = getOperatingSystem().getStateOfEnvironmentSensor(SENSOR_TYPE);
return new Denm(routing,
new DenmContent(
getOperatingSystem().getSimulationTime(),
getOs().getInitialPosition(),
HAZARD_ROAD,
SENSOR_TYPE,
strength,
SPEED,
0.0f,
HAZARD_LOCATION,
null,
null
)
);
}
</code></pre>
<h2 id="weatherwarningapp">WeatherWarningApp</h2>
<p>The WeatherWarningApp application illustrates the vehicles and their behaviour in particular with regard to the
detecting hazardous area, the receiving and sending messages. We will also cover how alternative routes
will be calculated and how the change the route in order to circumnavigate the affected road area.</p>
<p>The simulating vehicles can be operated as Cellular or Ad-hoc equipped. Accordingly, the kind of used communication
network will be activated in the <code>onStartup()</code> method as following:</p>
<pre><code class="language-java">public void onStartup() {
getLog().infoSimTime(this, &quot;Initialize application&quot;);
if (useCellNetwork()) {
getOperatingSystem().getCellModule().enable();
getLog().infoSimTime(this, &quot;Activated Cell Module&quot;);
} else {
getOperatingSystem().getAdHocModule().enable(new AdHocModuleConfiguration()
.addRadio()
.channel(AdHocChannel.CCH)
.power(50)
.create());
getLog().infoSimTime(this, &quot;Activated AdHoc Module&quot;);
}
getOperatingSystem().requestVehicleParametersUpdate()
.changeColor(Color.RED)
.apply();
}
</code></pre>
<p>In case the sensor detects an environmental hazard the vehicle sends out a DEN-message to warn
other vehicles. In the <code>reactOnEnvironmentData()</code> method, the sending is handled with
regard to used communication network. If <code>WeatherWarningAppCell</code> is mapped, cellular communication is used,
in case of <code>WeatherWarningApp</code> ITS-G5 communication is used as described in the
<a href="/tutorials/tiergarten">Tiergarten tutorial</a>.</p>
<pre><code class="language-java">private void reactOnEnvironmentData(SensorType type, int strength) {
GeoPoint vehiclePosition = getOperatingSystem().getPosition();
String roadId = getOperatingSystem().getVehicleInfo().getRoadPosition().getConnection().getId();
// reach all vehicles in a 3000m radius
GeoCircle dest = new GeoCircle(vehiclePosition, 3000);
MessageRouting mr;
if (useCellNetwork()) {
mr = getOperatingSystem().getCellModule().createMessageRouting().geoBroadCast(dest);
} else {
mr = getOperatingSystem().getAdHocModule().createMessageRouting().geoBroadCast(dest);
}
Denm denm = new Denm(mr, new DENMContent(
getOperatingSystem().getSimulationTime(), vehiclePosition, roadId, type, strength, SPEED, 0.0f, vehiclePosition, null, null)
);
if (useCellNetwork()) {
getOperatingSystem().getCellModule().sendV2XMessage(denm);
} else {
getOperatingSystem().getAdHocModule().sendV2XMessage(denm);
}
}
</code></pre>
<p>Next, we look at the receiving side of the DENM here. Since the message is a simple V2X message it
is received through the <code>receiveV2xMessage()</code>-method which is part of the application interface.
Analogous to a normal message, here we check with <code>instanceof</code>, if it is of a type that we are interested in, in
this case <code>Denm</code>. In that very case, we perform a potential route change if not already done.</p>
<pre><code class="language-java">public void receiveV2xMessage(ReceivedV2xMessage receivedV2xMessage) {
final V2xMessage msg = receivedV2xMessage.getMessage();
if (!(msg instanceof Denm)) {
return;
}
final Denm denm = (Denm)msg;
if (routeChanged) {
getLog().infoSimTime(this, &quot;Route already changed&quot;);
} else {
reactUponDENMessageChangeRoute(denm);
}
}
</code></pre>
<p>In order to calculate alternative routes to the destination and to change the actual route to the next best route,
the method <code>circumnavigateAffectedRoad()</code> is implemented. The affected road segment is identified by the road id parameter.
The route calculation needs to be parametrized in a way, that it avoids this road segment to include in the calculation.
This is achieved by using the specific cost function <code>ReRouteSpecificConnectionsCostFunction</code> and passing it
to the <code>RoutingParameters</code> object.</p>
<pre><code class="language-java">private void circumnavigateAffectedRoad(DENM denm, final String affectedRoadId) {
ReRouteSpecificConnectionsCostFunction myCostFunction = new ReRouteSpecificConnectionsCostFunction();
myCostFunction.setConnectionSpeedMS(affectedRoadId, denm.getCausedSpeed());
INavigationModule navigationModule = getOperatingSystem().getNavigationModule();
RoutingParameters routingParameters = new RoutingParameters().costFunction(myCostFunction);
RoutingResponse response = navigationModule.calculateRoutes(new RoutingPosition(navigationModule.getTargetPosition()), routingParameters);
CandidateRoute newRoute = response.getBestRoute();
if (newRoute != null) {
getLog().infoSimTime(this, &quot;Sending Change Route Command at position: {}&quot;, denm.getSenderPosition());
navigationModule.switchRoute(newRoute);
}
}
</code></pre>
<h2 id="weatherwarningappcell">WeatherWarningAppCell</h2>
<p>The only difference of the WeatherWarningAppCell to detailed described WeatherWarningApp is that the
<code>WeatherWarningAppCell</code>-application enabled the use of the cellular network.</p>
<h2 id="slowdownapp">SlowDownApp</h2>
<p>The <code>SlowDownApp</code> induces a speed reduction as soon as the on-board sensors detect hazardous conditions.
To detect the change in the on-board sensors, the state of the sensors have to be queried whenever the
vehicle has moved. This is achieved by implementing the <code>onVehicleUpdated()</code> method which is called
whenever the traffic simulator executed one simulation step.</p>
<p>In this specific implementation, the speed of the vehicle is reduced to <em>25 km/h</em> within the entire hazardous area.
After leaving the hazardous area, the vehicles returns to their original speed again:</p>
<pre><code class="language-java">public void onVehicleUpdated(VehicleData previousVehicleData, VehicleData updatedVehicleData) {
SensorType[] types = SensorType.values();
int strength = 0;
for (SensorType currentType : types) {
strength = getOs().getStateOfEnvironmentSensor(currentType);
if (strength &gt; 0) {
break;
}
}
if (strength &gt; 0 &amp;&amp; !hazardousArea) {
getOs().changeSpeedWithInterval(SPEED, 5000);
hazardousArea = true;
}
if (strength == 0 &amp;&amp; hazardousArea) {
getOs().resetSpeed();
hazardousArea = false;
}
}
</code></pre>
</div>
</div>
<script src="https://code.jquery.com/jquery-3.4.1.min.js" integrity="sha384-vk5WoKIaW/vJyUAd9n/wmopsmNhiy+L2Z+SBxGYnUkunIxVxAv/UtMOhba/xskxh" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery.imagesloaded/4.1.4/imagesloaded.pkgd.min.js" integrity="sha512-S5PZ9GxJZO16tT9r3WJp/Safn31eu8uWrzglMahDT4dsmgqWonRY9grk3j+3tfuPr9WJNsfooOR7Gi7HL5W2jw==" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery.isotope/3.0.6/isotope.pkgd.min.js" integrity="sha512-Zq2BOxyhvnRFXu0+WE6ojpZLOU2jdnqbrM1hmVdGzyeCa1DgM3X5Q4A/Is9xA1IkbUeDd7755dNNI/PzSf2Pew==" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/fancybox/3.5.7/jquery.fancybox.min.js" integrity="sha512-uURl+ZXMBrF4AwGaWmEetzrd+J5/8NRkWAvJx5sbPSSuOb0bZLqf+tOzniObO00BjHa/dD7gub9oCGMLPQHtQA==" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/mermaid/8.4.8/mermaid.min.js" integrity="sha512-1tS1YUns336Mtxl+vkaLcADPwE1CPNVy3WEf7nrI7DGMMb6/FAVBgL2IzAWVBkB6vVuK94s2zVoiXcw1QZ9S1g==" crossorigin="anonymous" title="mermaid"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/highlight.min.js" integrity="sha512-1LdB3V708w6G4QRl7NsVdTr7MDibyRXr9stQZ+EGjEE0ZPMZkA//ir7kCWmFyxdAJNIRXdR/ZeJmCV0boyiCXw==" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/languages/java.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/languages/json.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/languages/xml.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/languages/shell.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.18.1/languages/dos.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/leaflet/1.5.1/leaflet.js" integrity="sha512-GffPMF3RvMeYyc1LWMHtK8EbPv0iNZ8/oTtHPx9/cc2ILxQ+u905qIwdpULaqDkyBKgOaB57QTMg7ztg8Jm2Og==" crossorigin="anonymous"></script>
<script>const code_highlighting = true;</script>
<script>const isSiteThemeDark = false;</script>
<script>
const search_config = {"indexURI":"/mosaic/index.json","minLength":1,"threshold":0.3};
const i18n = {"no_results":"No results found","placeholder":"Search...","results":"results found"};
const content_type = {
'post': "Posts",
'project': "Projects",
'publication' : "Publications",
'talk' : "Talks"
};
</script>
<script id="search-hit-fuse-template" type="text/x-template">
<div class="search-hit" id="summary-{{key}}">
<div class="search-hit-content">
<div class="search-hit-name">
<a href="{{relpermalink}}">{{title}}</a>
<div class="article-metadata search-hit-type">{{type}}</div>
<p class="search-hit-description">{{snippet}}</p>
</div>
</div>
</div>
</script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/fuse.js/3.2.1/fuse.min.js" integrity="sha512-o38bmzBGX+hD3JHWUFCDA09btWaqrNmoJ3RXLlrysA7PP01Kgs4UlE4MhelE1v5dJR3+cxlR4qQlotsW7jKsnw==" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/mark.js/8.11.1/jquery.mark.min.js" integrity="sha512-mhbv5DqBMgrWL+32MmsDOt/OAvqr/cHimk6B8y/bx/xS88MVkYGPiVv2ixKVrkywF2qHplNRUvFsAHUdxZ3Krg==" crossorigin="anonymous"></script>
<script type="application/javascript" src="/mosaic/js/academic.min.1824b36a85a484362f116f1e24481eb9.js"></script>
<script type="application/javascript" src="/mosaic/js/mosaic-wg-cards.js"></script>
<div class="footer-wrap">
<div class="container">
<footer class="site-footer">
<div class="row">
<div class="col-sm-4 mb-3 mb-md-0">
<b>Eclipse MOSAIC</b>
<ul>
<li>
<a href="/mosaic/download/" title="Download Eclipse MOSAIC" >
Download Eclipse MOSAIC
</a>
</li>
<li>
<a href="/mosaic/docs" title="Documentation" >
Documentation
</a>
</li>
<li>
<a href="/mosaic/tutorials" title="Tutorials" >
Tutorials
</a>
</li>
<li>
<a href="/mosaic/community/#projects" title="Projects" >
Projects
</a>
</li>
<li>
<a href="/mosaic/publications" title="Publications" >
Publications
</a>
</li>
</ul>
</div>
<div class="col-sm-4 mb-3 mb-md-0">
<b>Community</b>
<ul>
<li>
<a href="/mosaic/community" title="Eclipse MOSAIC Community" >
Eclipse MOSAIC Community
</a>
</li>
<li>
<a href="/mosaic/contribution" title="How to contribute" >
How to contribute
</a>
</li>
<li>
<a href="https://github.com/eclipse/mosaic" title="Github" target="_blank" rel="noopener">
Github
</a>
</li>
<li>
<a href="/mosaic/get_in_contact" title="Contact &amp; Mailing list" >
Contact & Mailing list
</a>
</li>
</ul>
</div>
<div class="col-sm-4 mb-3 mb-md-0">
<b>Eclipse Foundation</b>
<ul>
<li>
<a href="https://www.eclipse.org/" title="About Eclipse Foundation" target="_blank" rel="noopener">
About Eclipse Foundation
</a>
</li>
<li>
<a href="https://www.eclipse.org/legal/privacy.php" title="Privacy Policy" target="_blank" rel="noopener">
Privacy Policy
</a>
</li>
<li>
<a href="https://www.eclipse.org/legal/termsofuse.php" title="Website terms of use" target="_blank" rel="noopener">
Website terms of use
</a>
</li>
<li>
<a href="https://www.eclipse.org/legal/copyright.php" title="Copyright" target="_blank" rel="noopener">
Copyright
</a>
</li>
<li>
<a href="https://www.eclipse.org/legal" title="Legal" target="_blank" rel="noopener">
Legal
</a>
</li>
</ul>
</div>
</div>
<div class="row justify-content-center mt-3 position-relative">
<p class="powered-by text-center font-italic mb-0 pb-0">
Powered by the
<a href="https://sourcethemes.com/academic/" target="_blank" rel="noopener">Academic theme</a> for
<a href="https://gohugo.io" target="_blank" rel="noopener">Hugo</a>.
<br>
Header image &#169; fanjianhua/ iStock
</p>
<span class="position-absolute mr-3 mr-md-0" aria-hidden="true" style="right: 0;">
<a href="#" class="back-to-top">
<span class="button_icon">
<i class="fas fa-chevron-up fa-2x"></i>
</span>
</a>
</span>
</div>
</footer>
</div>
</div>
<div id="modal" class="modal fade" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title">Cite</h5>
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
<pre><code class="tex hljs"></code></pre>
</div>
<div class="modal-footer">
<a class="btn btn-outline-primary my-1 js-copy-cite" href="#" target="_blank">
<i class="fas fa-copy"></i> Copy
</a>
<a class="btn btn-outline-primary my-1 js-download-cite" href="#" target="_blank">
<i class="fas fa-download"></i> Download
</a>
<div id="modal-error"></div>
</div>
</div>
</div>
</div>
</body>
</html>