1
0
mirror of https://github.com/gsi-upm/soil synced 2024-11-14 15:32:29 +00:00

Download results

This commit is contained in:
Tasio Mendez 2018-04-12 18:00:44 +02:00
parent 87a21d8884
commit 563587193a
5 changed files with 92 additions and 11 deletions

View File

@ -12,6 +12,7 @@ import yaml
import webbrowser import webbrowser
from contextlib import contextmanager from contextlib import contextmanager
from time import sleep from time import sleep
from xml.etree.ElementTree import tostring
logger = logging.getLogger(__name__) logger = logging.getLogger(__name__)
logger.setLevel(logging.INFO) logger.setLevel(logging.INFO)
@ -118,7 +119,7 @@ class SocketHandler(tornado.websocket.WebSocketHandler):
logger.info('Trial {} requested!'.format(msg['data'])) logger.info('Trial {} requested!'.format(msg['data']))
self.send_log('INFO.user', 'Trial {} requested!'.format(msg['data'])) self.send_log('INFO.user', 'Trial {} requested!'.format(msg['data']))
self.write_message({'type': 'get_trial', self.write_message({'type': 'get_trial',
'data': self.get_trial( int(msg['data'] )) }) 'data': self.get_trial( int(msg['data']) ) })
elif msg['type'] == 'run_simulation': elif msg['type'] == 'run_simulation':
if self.application.verbose: if self.application.verbose:
@ -127,6 +128,28 @@ class SocketHandler(tornado.websocket.WebSocketHandler):
self.config['environment_params'] = msg['data'] self.config['environment_params'] = msg['data']
self.run_simulation() self.run_simulation()
elif msg['type'] == 'download_gexf':
G = self.simulation[ int(msg['data']) ].history_to_graph()
for node in G.nodes():
if 'pos' in G.node[node]:
G.node[node]['viz'] = {"position": {"x": G.node[node]['pos'][0], "y": G.node[node]['pos'][1], "z": 0.0}}
del (G.node[node]['pos'])
writer = nx.readwrite.gexf.GEXFWriter(version='1.2draft')
writer.add_graph(G)
self.write_message({'type': 'download_gexf',
'filename': self.config['name'] + '_trial_' + str(msg['data']),
'data': tostring(writer.xml).decode(writer.encoding) })
elif msg['type'] == 'download_json':
G = self.simulation[ int(msg['data']) ].history_to_graph()
for node in G.nodes():
if 'pos' in G.node[node]:
G.node[node]['viz'] = {"position": {"x": G.node[node]['pos'][0], "y": G.node[node]['pos'][1], "z": 0.0}}
del (G.node[node]['pos'])
self.write_message({'type': 'download_json',
'filename': self.config['name'] + '_trial_' + str(msg['data']),
'data': nx.node_link_data(G) })
else: else:
if self.application.verbose: if self.application.verbose:
logger.info('Unexpected message!') logger.info('Unexpected message!')

View File

@ -197,6 +197,7 @@
</ul> </ul>
<ul class="nav navbar-nav navbar-right"> <ul class="nav navbar-nav navbar-right">
<li><a href="#" id="run_simulation" role="button">Run simulation</a></li> <li><a href="#" id="run_simulation" role="button">Run simulation</a></li>
<li><a href="#" id="download_simulation" role="button" data-toggle="modal" data-target="#download_modal">Download</a></li>
</ul> </ul>
</div> </div>
<script type="text/javascript"> <script type="text/javascript">
@ -332,7 +333,7 @@
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button> <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">New simulation</h4> <h4 class="modal-title">New simulation</h4>
</div> </div>
<div class="modal-body"> <div class="modal-body text-justify">
<p>You are going to run a new simulation, all charts and trials are going to be lost. A new ones will be available after the simulation.</p> <p>You are going to run a new simulation, all charts and trials are going to be lost. A new ones will be available after the simulation.</p>
<p>Check your new environment variables for this simulation.</p> <p>Check your new environment variables for this simulation.</p>
<table class="table"> <table class="table">
@ -341,8 +342,32 @@
</table> </table>
</div> </div>
<div class="modal-footer"> <div class="modal-footer">
<button type="button" class="btn btn-danger" data-dismiss="modal">Cancel</button>
<button type="button" class="btn btn-success">Run</button> <button type="button" class="btn btn-success">Run</button>
<button type="button" class="btn btn-danger" data-dismiss="modal">Cancel</button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
<div class="modal fade" tabindex="-1" role="dialog" id="download_modal">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Download Simulation Results</h4>
</div>
<div class="modal-body text-justify">
<p>You can download the results of the selected trial in GEXF or JSON Graph format for your personal purposes.</p>
<ul >
<li><b>GEXF</b> <i>(Graph Exchange XML Format)</i> is a language for describing complex network structures, their associated data and dynamics. It can be used to visualize the simulation with Gephi.</li>
<li><b>JSON Graph</b> generate and parse JSON serializable data for NetworkX graphs. It is a convention for modeling graph information as a JSON object that can be parsed by any JSON parser.</li>
</ul>
<p>For downloading the results of the other trials simulated, please first select them in menu.</p>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-success" disabled="disabled" id="download_gexf">GEXF</button>
<button type="button" class="btn btn-success" disabled="disabled" id="download_json">JSON Graph</button>
<button type="button" class="btn btn-danger" data-dismiss="modal">Cancel</button>
</div> </div>
</div><!-- /.modal-content --> </div><!-- /.modal-content -->
</div><!-- /.modal-dialog --> </div><!-- /.modal-dialog -->

View File

@ -75,6 +75,15 @@ ws.onmessage = function(message) {
} }
break; break;
case 'download_gexf':
var xml_declaration = '<?xml version="1.0" encoding="utf-8"?>';
download(msg['filename'] + '.gexf', 'xml', xml_declaration + msg['data']);
break;
case 'download_json':
download(msg['filename'] + '.json', 'json', JSON.stringify(msg['data'], null, 4));
break;
default: default:
console.warn('Unexpected message!') console.warn('Unexpected message!')
} }
@ -91,7 +100,8 @@ var _socket = {
error: function(message) { error: function(message) {
$('#error-message').text(message); $('#error-message').text(message);
$('.alert.alert-danger').show(); $('.alert.alert-danger').show();
} },
current_trial: undefined
}; };
var set_trials = function(trials) { var set_trials = function(trials) {
@ -104,9 +114,11 @@ var set_trials = function(trials) {
var a = $('.dropdown-toggle .caret'); var a = $('.dropdown-toggle .caret');
$('.dropdown-toggle').text($(this).text() + ' ').append(a); $('.dropdown-toggle').text($(this).text() + ' ').append(a);
_socket.send($(this).val(), 'get_trial'); _socket.send($(this).val(), 'get_trial');
_socket.current_trial = $(this).val();
}); });
// Request first trial as default // Request first trial as default
_socket.send(0, 'get_trial') _socket.send(0, 'get_trial')
_socket.current_trial = 0
}; };
var reset_trials = function() { var reset_trials = function() {
@ -200,6 +212,15 @@ var set_configuration = function() {
// Enable 'Run configuration' button // Enable 'Run configuration' button
$('#run_simulation').attr('data-toggle', 'modal').attr('data-target', '#simulation_modal'); $('#run_simulation').attr('data-toggle', 'modal').attr('data-target', '#simulation_modal');
// Enable 'Download' buttons
$('#download_modal .btn-success').prop('disabled', false);
$('#download_gexf').on('click', function() {
_socket.send(_socket.current_trial, 'download_gexf')
});
$('#download_json').on('click', function() {
_socket.send(_socket.current_trial, 'download_json')
});
} }
var reset_configuration = function() { var reset_configuration = function() {
@ -212,6 +233,10 @@ var reset_configuration = function() {
// 'Link Distance' slider // 'Link Distance' slider
$('#link-distance-slider').slider('disable').slider('setValue', 30); $('#link-distance-slider').slider('disable').slider('setValue', 30);
// 'Download' buttons
$('#download_gexf').off();
$('#download_json').off();
} }
var set_timeline = function(graph) { var set_timeline = function(graph) {
@ -422,3 +447,11 @@ var run_simulation = function() {
}); });
return environment_variables; return environment_variables;
} }
var download = function(filename, filetype, content) {
var file = document.createElement('a');
file.setAttribute('href', 'data:text/' + filetype + ';charset=utf-8,' + encodeURIComponent(content));
file.setAttribute('download', filename);
file.click();
delete file;
}

View File

@ -264,7 +264,7 @@
// Zoom // Zoom
zoom = d3.behavior zoom = d3.behavior
.zoom() .zoom()
.scaleExtent([1/10, 10]) .scaleExtent([1/5, 10])
.on('zoom', function () { .on('zoom', function () {
//console.trace("zoom", d3.event.translate, d3.event.scale); //console.trace("zoom", d3.event.translate, d3.event.scale);
groot.attr('transform', groot.attr('transform',

View File

@ -25,12 +25,12 @@ class Model():
simulation_results = sim.run_simulation() simulation_results = sim.run_simulation()
G = simulation_results[0].history_to_graph() # G = simulation_results[0].history_to_graph()
for node in G.nodes(): # for node in G.nodes():
if 'pos' in G.node[node]: # if 'pos' in G.node[node]:
G.node[node]['viz'] = {"position": {"x": G.node[node]['pos'][0], "y": G.node[node]['pos'][1], "z": 0.0}} # G.node[node]['viz'] = {"position": {"x": G.node[node]['pos'][0], "y": G.node[node]['pos'][1], "z": 0.0}}
del (G.node[node]['pos']) # del (G.node[node]['pos'])
nx.write_gexf(G, 'test.gexf', version='1.2draft') # nx.write_gexf(G, 'test.gexf', version='1.2draft')
return simulation_results return simulation_results