commit 585182553048133fff369ccd36b910d6f366e52d
Author: Benedetta Parodi
Date: Sat Apr 20 13:50:27 2024 +0200
from facciamo.cisti.org
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..e7b4f21
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,13 @@
+.idea/
+*.iml
+*.iws
+*.eml
+out/
+.DS_Store
+.svn
+log/*.log
+tmp/**
+node_modules/
+.sass-cache
+css/reveal.min.css
+js/reveal.min.js
\ No newline at end of file
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
new file mode 100644
index 0000000..c2091e8
--- /dev/null
+++ b/CONTRIBUTING.md
@@ -0,0 +1,23 @@
+## Contributing
+
+Please keep the [issue tracker](http://github.com/hakimel/reveal.js/issues) limited to **bug reports**, **feature requests** and **pull requests**.
+
+
+### Personal Support
+If you have personal support or setup questions the best place to ask those are [StackOverflow](http://stackoverflow.com/questions/tagged/reveal.js).
+
+
+### Bug Reports
+When reporting a bug make sure to include information about which browser and operating system you are on as well as the necessary steps to reproduce the issue. If possible please include a link to a sample presentation where the bug can be tested.
+
+
+### Pull Requests
+- Should follow the coding style of the file you work in, most importantly:
+ - Tabs to indent
+ - Single-quoted strings
+- Should be made towards the **dev branch**
+- Should be submitted from a feature/topic branch (not your master)
+
+
+### Plugins
+Please do not submit plugins as pull requests. They should be maintained in their own separate repository. More information here: https://github.com/hakimel/reveal.js/wiki/Plugin-Guidelines
diff --git a/Gruntfile.js b/Gruntfile.js
new file mode 100644
index 0000000..b1eb5ea
--- /dev/null
+++ b/Gruntfile.js
@@ -0,0 +1,192 @@
+/* global module:false */
+module.exports = function(grunt) {
+ var port = grunt.option('port') || 8000;
+ var root = grunt.option('root') || '.';
+
+ if (!Array.isArray(root)) root = [root];
+
+ // Project configuration
+ grunt.initConfig({
+ pkg: grunt.file.readJSON('package.json'),
+ meta: {
+ banner:
+ '/*!\n' +
+ ' * reveal.js <%= pkg.version %> (<%= grunt.template.today("yyyy-mm-dd, HH:MM") %>)\n' +
+ ' * http://revealjs.com\n' +
+ ' * MIT licensed\n' +
+ ' *\n' +
+ ' * Copyright (C) 2017 Hakim El Hattab, http://hakim.se\n' +
+ ' */'
+ },
+
+ qunit: {
+ files: [ 'test/*.html' ]
+ },
+
+ uglify: {
+ options: {
+ banner: '<%= meta.banner %>\n',
+ screwIE8: false
+ },
+ build: {
+ src: 'js/reveal.js',
+ dest: 'js/reveal.min.js'
+ }
+ },
+
+ sass: {
+ core: {
+ src: 'css/reveal.scss',
+ dest: 'css/reveal.css'
+ },
+ themes: {
+ expand: true,
+ cwd: 'css/theme/source',
+ src: ['*.sass', '*.scss'],
+ dest: 'css/theme',
+ ext: '.css'
+ }
+ },
+
+ autoprefixer: {
+ core: {
+ src: 'css/reveal.css'
+ }
+ },
+
+ cssmin: {
+ options: {
+ compatibility: 'ie9'
+ },
+ compress: {
+ src: 'css/reveal.css',
+ dest: 'css/reveal.min.css'
+ }
+ },
+
+ jshint: {
+ options: {
+ curly: false,
+ eqeqeq: true,
+ immed: true,
+ esnext: true,
+ latedef: 'nofunc',
+ newcap: true,
+ noarg: true,
+ sub: true,
+ undef: true,
+ eqnull: true,
+ browser: true,
+ expr: true,
+ globals: {
+ head: false,
+ module: false,
+ console: false,
+ unescape: false,
+ define: false,
+ exports: false
+ }
+ },
+ files: [ 'Gruntfile.js', 'js/reveal.js' ]
+ },
+
+ connect: {
+ server: {
+ options: {
+ port: port,
+ base: root,
+ livereload: true,
+ open: true,
+ useAvailablePort: true
+ }
+ }
+ },
+
+ zip: {
+ bundle: {
+ src: [
+ 'index.html',
+ 'css/**',
+ 'js/**',
+ 'lib/**',
+ 'images/**',
+ 'plugin/**',
+ '**.md'
+ ],
+ dest: 'reveal-js-presentation.zip'
+ }
+ },
+
+ watch: {
+ js: {
+ files: [ 'Gruntfile.js', 'js/reveal.js' ],
+ tasks: 'js'
+ },
+ theme: {
+ files: [
+ 'css/theme/source/*.sass',
+ 'css/theme/source/*.scss',
+ 'css/theme/template/*.sass',
+ 'css/theme/template/*.scss'
+ ],
+ tasks: 'css-themes'
+ },
+ css: {
+ files: [ 'css/reveal.scss' ],
+ tasks: 'css-core'
+ },
+ html: {
+ files: root.map(path => path + '/*.html')
+ },
+ markdown: {
+ files: root.map(path => path + '/slides/*.md')
+ },
+ options: {
+ livereload: true
+ }
+ },
+
+ retire: {
+ js: [ 'js/reveal.js', 'lib/js/*.js', 'plugin/**/*.js' ],
+ node: [ '.' ]
+ }
+
+ });
+
+ // Dependencies
+ grunt.loadNpmTasks( 'grunt-contrib-connect' );
+ grunt.loadNpmTasks( 'grunt-contrib-cssmin' );
+ grunt.loadNpmTasks( 'grunt-contrib-jshint' );
+ grunt.loadNpmTasks( 'grunt-contrib-qunit' );
+ grunt.loadNpmTasks( 'grunt-contrib-uglify' );
+ grunt.loadNpmTasks( 'grunt-contrib-watch' );
+ grunt.loadNpmTasks( 'grunt-autoprefixer' );
+ grunt.loadNpmTasks( 'grunt-retire' );
+ grunt.loadNpmTasks( 'grunt-sass' );
+ grunt.loadNpmTasks( 'grunt-zip' );
+
+ // Default task
+ grunt.registerTask( 'default', [ 'css', 'js' ] );
+
+ // JS task
+ grunt.registerTask( 'js', [ 'jshint', 'uglify', 'qunit' ] );
+
+ // Theme CSS
+ grunt.registerTask( 'css-themes', [ 'sass:themes' ] );
+
+ // Core framework CSS
+ grunt.registerTask( 'css-core', [ 'sass:core', 'autoprefixer', 'cssmin' ] );
+
+ // All CSS
+ grunt.registerTask( 'css', [ 'sass', 'autoprefixer', 'cssmin' ] );
+
+ // Package presentation to archive
+ grunt.registerTask( 'package', [ 'default', 'zip' ] );
+
+ // Serve presentation locally
+ grunt.registerTask( 'serve', [ 'connect', 'watch' ] );
+
+ // Run tests
+ grunt.registerTask( 'test', [ 'jshint', 'qunit' ] );
+
+};
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..c3e6e5f
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,19 @@
+Copyright (C) 2017 Hakim El Hattab, http://hakim.se, and reveal.js contributors
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
\ No newline at end of file
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..28a6ced
--- /dev/null
+++ b/README.md
@@ -0,0 +1,38 @@
+Autodifesa Digitale I
+
+Slides di autodifesa digitale.
+
+## Usare
+Questa presentazione e' pensata per essere fatta in 3 sessioni da 2 ore l'una o 2 sessioni da tre ore l'una,
+ma e' stata fatta anche in una sola sessione da tre ore (tutte le persone presenti sono soprattissute).
+
+Clona questo repo con:
+`git clone https://git.lattuga.net/cisti/autodifesa-digitale-parte-1.git`
+
+Apri `index.html` con qualsiasi browser.
+
+Se vuoi fare il figo e stai usando un proiettore (non mirrorato)
+premi `S` (se viene fuori un messaggio di warning riguardo
+le finestre di popup, abilita i popup per questa tab).
+
+
+## Modificare
+
+Clona questo repo con:
+`git clone https://git.lattuga.net/cisti/autodifesa-digitale-parte-1.git`
+
+Installa le dipendenze:
+`npm install` o `yarn`
+
+Fai partire il server livereload di grunt:
+`grunt serve`
+Verrà scritto qualcosa come: `Started connect web server on http://localhost:8000`
+aprendo quell'indirizzo da un browser dovresti vedere la presentazione.
+
+Le slides sono scritte in markdown e separate per argomenti nella
+cartella `/slides`, ad ogni modifica `grunt` farà un refresh del browser,
+mantenendo la slides corrente.
+
+
+## Esportare
+eee ti piacerebbe :) non sono ancora arrivato li', in pdf dovrebbe essere facile pero'.
diff --git a/README.reveal.js.md b/README.reveal.js.md
new file mode 100644
index 0000000..7ec759a
--- /dev/null
+++ b/README.reveal.js.md
@@ -0,0 +1,1227 @@
+# reveal.js [![Build Status](https://travis-ci.org/hakimel/reveal.js.svg?branch=master)](https://travis-ci.org/hakimel/reveal.js)
+
+A framework for easily creating beautiful presentations using HTML. [Check out the live demo](http://lab.hakim.se/reveal-js/).
+
+reveal.js comes with a broad range of features including [nested slides](https://github.com/hakimel/reveal.js#markup), [Markdown contents](https://github.com/hakimel/reveal.js#markdown), [PDF export](https://github.com/hakimel/reveal.js#pdf-export), [speaker notes](https://github.com/hakimel/reveal.js#speaker-notes) and a [JavaScript API](https://github.com/hakimel/reveal.js#api). There's also a fully featured visual editor and platform for sharing reveal.js presentations at [slides.com](https://slides.com?ref=github).
+
+## Table of contents
+- [Online Editor](#online-editor)
+- [Instructions](#instructions)
+ - [Markup](#markup)
+ - [Markdown](#markdown)
+ - [Element Attributes](#element-attributes)
+ - [Slide Attributes](#slide-attributes)
+- [Configuration](#configuration)
+- [Presentation Size](#presentation-size)
+- [Dependencies](#dependencies)
+- [Ready Event](#ready-event)
+- [Auto-sliding](#auto-sliding)
+- [Keyboard Bindings](#keyboard-bindings)
+- [Touch Navigation](#touch-navigation)
+- [Lazy Loading](#lazy-loading)
+- [API](#api)
+ - [Slide Changed Event](#slide-changed-event)
+ - [Presentation State](#presentation-state)
+ - [Slide States](#slide-states)
+ - [Slide Backgrounds](#slide-backgrounds)
+ - [Parallax Background](#parallax-background)
+ - [Slide Transitions](#slide-transitions)
+ - [Internal links](#internal-links)
+ - [Fragments](#fragments)
+ - [Fragment events](#fragment-events)
+ - [Code syntax highlighting](#code-syntax-highlighting)
+ - [Slide number](#slide-number)
+ - [Overview mode](#overview-mode)
+ - [Fullscreen mode](#fullscreen-mode)
+ - [Embedded media](#embedded-media)
+ - [Stretching elements](#stretching-elements)
+ - [postMessage API](#postmessage-api)
+- [PDF Export](#pdf-export)
+- [Theming](#theming)
+- [Speaker Notes](#speaker-notes)
+ - [Share and Print Speaker Notes](#share-and-print-speaker-notes)
+ - [Server Side Speaker Notes](#server-side-speaker-notes)
+- [Multiplexing](#multiplexing)
+ - [Master presentation](#master-presentation)
+ - [Client presentation](#client-presentation)
+ - [Socket.io server](#socketio-server)
+- [MathJax](#mathjax)
+- [Installation](#installation)
+ - [Basic setup](#basic-setup)
+ - [Full setup](#full-setup)
+ - [Folder Structure](#folder-structure)
+- [License](#license)
+
+#### More reading
+- [Changelog](https://github.com/hakimel/reveal.js/releases): Up-to-date version history.
+- [Examples](https://github.com/hakimel/reveal.js/wiki/Example-Presentations): Presentations created with reveal.js, add your own!
+- [Browser Support](https://github.com/hakimel/reveal.js/wiki/Browser-Support): Explanation of browser support and fallbacks.
+- [Plugins](https://github.com/hakimel/reveal.js/wiki/Plugins,-Tools-and-Hardware): A list of plugins that can be used to extend reveal.js.
+
+## Online Editor
+
+Presentations are written using HTML or Markdown but there's also an online editor for those of you who prefer a graphical interface. Give it a try at [https://slides.com](https://slides.com?ref=github).
+
+
+## Instructions
+
+### Markup
+
+Here's a barebones example of a fully working reveal.js presentation:
+```html
+
+
+
+
+
+
+
+
+ Slide 1
+ Slide 2
+
+
+
+
+
+
+```
+
+The presentation markup hierarchy needs to be `.reveal > .slides > section` where the `section` represents one slide and can be repeated indefinitely. If you place multiple `section` elements inside of another `section` they will be shown as vertical slides. The first of the vertical slides is the "root" of the others (at the top), and will be included in the horizontal sequence. For example:
+
+```html
+
+```
+
+### Markdown
+
+It's possible to write your slides using Markdown. To enable Markdown, add the `data-markdown` attribute to your `` elements and wrap the contents in a `
"+escape(e.message+"",true)+"
"}throw e}}marked.options=marked.setOptions=function(opt){merge(marked.defaults,opt);return marked};marked.defaults={gfm:true,tables:true,breaks:false,pedantic:false,sanitize:false,sanitizer:null,mangle:true,smartLists:false,silent:false,highlight:null,langPrefix:"lang-",smartypants:false,headerPrefix:"",renderer:new Renderer,xhtml:false};marked.Parser=Parser;marked.parser=Parser.parse;marked.Renderer=Renderer;marked.Lexer=Lexer;marked.lexer=Lexer.lex;marked.InlineLexer=InlineLexer;marked.inlineLexer=InlineLexer.output;marked.parse=marked;if(typeof module!=="undefined"&&typeof exports==="object"){module.exports=marked}else if(typeof define==="function"&&define.amd){define(function(){return marked})}else{this.marked=marked}}).call(function(){return this||(typeof window!=="undefined"?window:global)}());
\ No newline at end of file
diff --git a/plugin/math/math.js b/plugin/math/math.js
new file mode 100755
index 0000000..e3b4089
--- /dev/null
+++ b/plugin/math/math.js
@@ -0,0 +1,67 @@
+/**
+ * A plugin which enables rendering of math equations inside
+ * of reveal.js slides. Essentially a thin wrapper for MathJax.
+ *
+ * @author Hakim El Hattab
+ */
+var RevealMath = window.RevealMath || (function(){
+
+ var options = Reveal.getConfig().math || {};
+ options.mathjax = options.mathjax || 'https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js';
+ options.config = options.config || 'TeX-AMS_HTML-full';
+
+ loadScript( options.mathjax + '?config=' + options.config, function() {
+
+ MathJax.Hub.Config({
+ messageStyle: 'none',
+ tex2jax: {
+ inlineMath: [['$','$'],['\\(','\\)']] ,
+ skipTags: ['script','noscript','style','textarea','pre']
+ },
+ skipStartupTypeset: true
+ });
+
+ // Typeset followed by an immediate reveal.js layout since
+ // the typesetting process could affect slide height
+ MathJax.Hub.Queue( [ 'Typeset', MathJax.Hub ] );
+ MathJax.Hub.Queue( Reveal.layout );
+
+ // Reprocess equations in slides when they turn visible
+ Reveal.addEventListener( 'slidechanged', function( event ) {
+
+ MathJax.Hub.Queue( [ 'Typeset', MathJax.Hub, event.currentSlide ] );
+
+ } );
+
+ } );
+
+ function loadScript( url, callback ) {
+
+ var head = document.querySelector( 'head' );
+ var script = document.createElement( 'script' );
+ script.type = 'text/javascript';
+ script.src = url;
+
+ // Wrapper for callback to make sure it only fires once
+ var finish = function() {
+ if( typeof callback === 'function' ) {
+ callback.call();
+ callback = null;
+ }
+ }
+
+ script.onload = finish;
+
+ // IE
+ script.onreadystatechange = function() {
+ if ( this.readyState === 'loaded' ) {
+ finish();
+ }
+ }
+
+ // Normal browsers
+ head.appendChild( script );
+
+ }
+
+})();
diff --git a/plugin/multiplex/client.js b/plugin/multiplex/client.js
new file mode 100644
index 0000000..3ffd1e0
--- /dev/null
+++ b/plugin/multiplex/client.js
@@ -0,0 +1,13 @@
+(function() {
+ var multiplex = Reveal.getConfig().multiplex;
+ var socketId = multiplex.id;
+ var socket = io.connect(multiplex.url);
+
+ socket.on(multiplex.id, function(data) {
+ // ignore data from sockets that aren't ours
+ if (data.socketId !== socketId) { return; }
+ if( window.location.host === 'localhost:1947' ) return;
+
+ Reveal.setState(data.state);
+ });
+}());
diff --git a/plugin/multiplex/index.js b/plugin/multiplex/index.js
new file mode 100644
index 0000000..8195f04
--- /dev/null
+++ b/plugin/multiplex/index.js
@@ -0,0 +1,64 @@
+var http = require('http');
+var express = require('express');
+var fs = require('fs');
+var io = require('socket.io');
+var crypto = require('crypto');
+
+var app = express();
+var staticDir = express.static;
+var server = http.createServer(app);
+
+io = io(server);
+
+var opts = {
+ port: process.env.PORT || 1948,
+ baseDir : __dirname + '/../../'
+};
+
+io.on( 'connection', function( socket ) {
+ socket.on('multiplex-statechanged', function(data) {
+ if (typeof data.secret == 'undefined' || data.secret == null || data.secret === '') return;
+ if (createHash(data.secret) === data.socketId) {
+ data.secret = null;
+ socket.broadcast.emit(data.socketId, data);
+ };
+ });
+});
+
+[ 'css', 'js', 'plugin', 'lib' ].forEach(function(dir) {
+ app.use('/' + dir, staticDir(opts.baseDir + dir));
+});
+
+app.get("/", function(req, res) {
+ res.writeHead(200, {'Content-Type': 'text/html'});
+
+ var stream = fs.createReadStream(opts.baseDir + '/index.html');
+ stream.on('error', function( error ) {
+ res.write('
reveal.js multiplex server.
Generate token');
+ res.end();
+ });
+ stream.on('readable', function() {
+ stream.pipe(res);
+ });
+});
+
+app.get("/token", function(req,res) {
+ var ts = new Date().getTime();
+ var rand = Math.floor(Math.random()*9999999);
+ var secret = ts.toString() + rand.toString();
+ res.send({secret: secret, socketId: createHash(secret)});
+});
+
+var createHash = function(secret) {
+ var cipher = crypto.createCipher('blowfish', secret);
+ return(cipher.final('hex'));
+};
+
+// Actually listen
+server.listen( opts.port || null );
+
+var brown = '\033[33m',
+ green = '\033[32m',
+ reset = '\033[0m';
+
+console.log( brown + "reveal.js:" + reset + " Multiplex running on port " + green + opts.port + reset );
\ No newline at end of file
diff --git a/plugin/multiplex/master.js b/plugin/multiplex/master.js
new file mode 100644
index 0000000..7f4bf45
--- /dev/null
+++ b/plugin/multiplex/master.js
@@ -0,0 +1,34 @@
+(function() {
+
+ // Don't emit events from inside of notes windows
+ if ( window.location.search.match( /receiver/gi ) ) { return; }
+
+ var multiplex = Reveal.getConfig().multiplex;
+
+ var socket = io.connect( multiplex.url );
+
+ function post() {
+
+ var messageData = {
+ state: Reveal.getState(),
+ secret: multiplex.secret,
+ socketId: multiplex.id
+ };
+
+ socket.emit( 'multiplex-statechanged', messageData );
+
+ };
+
+ // post once the page is loaded, so the client follows also on "open URL".
+ window.addEventListener( 'load', post );
+
+ // Monitor events that trigger a change in state
+ Reveal.addEventListener( 'slidechanged', post );
+ Reveal.addEventListener( 'fragmentshown', post );
+ Reveal.addEventListener( 'fragmenthidden', post );
+ Reveal.addEventListener( 'overviewhidden', post );
+ Reveal.addEventListener( 'overviewshown', post );
+ Reveal.addEventListener( 'paused', post );
+ Reveal.addEventListener( 'resumed', post );
+
+}());
diff --git a/plugin/multiplex/package.json b/plugin/multiplex/package.json
new file mode 100644
index 0000000..bbed77a
--- /dev/null
+++ b/plugin/multiplex/package.json
@@ -0,0 +1,19 @@
+{
+ "name": "reveal-js-multiplex",
+ "version": "1.0.0",
+ "description": "reveal.js multiplex server",
+ "homepage": "http://revealjs.com",
+ "scripts": {
+ "start": "node index.js"
+ },
+ "engines": {
+ "node": "~4.1.1"
+ },
+ "dependencies": {
+ "express": "~4.13.3",
+ "grunt-cli": "~0.1.13",
+ "mustache": "~2.2.1",
+ "socket.io": "~1.3.7"
+ },
+ "license": "MIT"
+}
diff --git a/plugin/notes-server/client.js b/plugin/notes-server/client.js
new file mode 100644
index 0000000..00b277b
--- /dev/null
+++ b/plugin/notes-server/client.js
@@ -0,0 +1,65 @@
+(function() {
+
+ // don't emit events from inside the previews themselves
+ if( window.location.search.match( /receiver/gi ) ) { return; }
+
+ var socket = io.connect( window.location.origin ),
+ socketId = Math.random().toString().slice( 2 );
+
+ console.log( 'View slide notes at ' + window.location.origin + '/notes/' + socketId );
+
+ window.open( window.location.origin + '/notes/' + socketId, 'notes-' + socketId );
+
+ /**
+ * Posts the current slide data to the notes window
+ */
+ function post() {
+
+ var slideElement = Reveal.getCurrentSlide(),
+ notesElement = slideElement.querySelector( 'aside.notes' );
+
+ var messageData = {
+ notes: '',
+ markdown: false,
+ socketId: socketId,
+ state: Reveal.getState()
+ };
+
+ // Look for notes defined in a slide attribute
+ if( slideElement.hasAttribute( 'data-notes' ) ) {
+ messageData.notes = slideElement.getAttribute( 'data-notes' );
+ }
+
+ // Look for notes defined in an aside element
+ if( notesElement ) {
+ messageData.notes = notesElement.innerHTML;
+ messageData.markdown = typeof notesElement.getAttribute( 'data-markdown' ) === 'string';
+ }
+
+ socket.emit( 'statechanged', messageData );
+
+ }
+
+ // When a new notes window connects, post our current state
+ socket.on( 'new-subscriber', function( data ) {
+ post();
+ } );
+
+ // When the state changes from inside of the speaker view
+ socket.on( 'statechanged-speaker', function( data ) {
+ Reveal.setState( data.state );
+ } );
+
+ // Monitor events that trigger a change in state
+ Reveal.addEventListener( 'slidechanged', post );
+ Reveal.addEventListener( 'fragmentshown', post );
+ Reveal.addEventListener( 'fragmenthidden', post );
+ Reveal.addEventListener( 'overviewhidden', post );
+ Reveal.addEventListener( 'overviewshown', post );
+ Reveal.addEventListener( 'paused', post );
+ Reveal.addEventListener( 'resumed', post );
+
+ // Post the initial state
+ post();
+
+}());
diff --git a/plugin/notes-server/index.js b/plugin/notes-server/index.js
new file mode 100644
index 0000000..b95f071
--- /dev/null
+++ b/plugin/notes-server/index.js
@@ -0,0 +1,69 @@
+var http = require('http');
+var express = require('express');
+var fs = require('fs');
+var io = require('socket.io');
+var Mustache = require('mustache');
+
+var app = express();
+var staticDir = express.static;
+var server = http.createServer(app);
+
+io = io(server);
+
+var opts = {
+ port : 1947,
+ baseDir : __dirname + '/../../'
+};
+
+io.on( 'connection', function( socket ) {
+
+ socket.on( 'new-subscriber', function( data ) {
+ socket.broadcast.emit( 'new-subscriber', data );
+ });
+
+ socket.on( 'statechanged', function( data ) {
+ delete data.state.overview;
+ socket.broadcast.emit( 'statechanged', data );
+ });
+
+ socket.on( 'statechanged-speaker', function( data ) {
+ delete data.state.overview;
+ socket.broadcast.emit( 'statechanged-speaker', data );
+ });
+
+});
+
+[ 'css', 'js', 'images', 'plugin', 'lib' ].forEach( function( dir ) {
+ app.use( '/' + dir, staticDir( opts.baseDir + dir ) );
+});
+
+app.get('/', function( req, res ) {
+
+ res.writeHead( 200, { 'Content-Type': 'text/html' } );
+ fs.createReadStream( opts.baseDir + '/index.html' ).pipe( res );
+
+});
+
+app.get( '/notes/:socketId', function( req, res ) {
+
+ fs.readFile( opts.baseDir + 'plugin/notes-server/notes.html', function( err, data ) {
+ res.send( Mustache.to_html( data.toString(), {
+ socketId : req.params.socketId
+ }));
+ });
+
+});
+
+// Actually listen
+server.listen( opts.port || null );
+
+var brown = '\033[33m',
+ green = '\033[32m',
+ reset = '\033[0m';
+
+var slidesLocation = 'http://localhost' + ( opts.port ? ( ':' + opts.port ) : '' );
+
+console.log( brown + 'reveal.js - Speaker Notes' + reset );
+console.log( '1. Open the slides at ' + green + slidesLocation + reset );
+console.log( '2. Click on the link in your JS console to go to the notes page' );
+console.log( '3. Advance through your slides and your notes will advance automatically' );
diff --git a/plugin/notes-server/notes.html b/plugin/notes-server/notes.html
new file mode 100644
index 0000000..ab8c5b1
--- /dev/null
+++ b/plugin/notes-server/notes.html
@@ -0,0 +1,585 @@
+
+
+
+
+
+ reveal.js - Slide Notes
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/plugin/notes/notes.js b/plugin/notes/notes.js
new file mode 100644
index 0000000..80fb6e2
--- /dev/null
+++ b/plugin/notes/notes.js
@@ -0,0 +1,155 @@
+/**
+ * Handles opening of and synchronization with the reveal.js
+ * notes window.
+ *
+ * Handshake process:
+ * 1. This window posts 'connect' to notes window
+ * - Includes URL of presentation to show
+ * 2. Notes window responds with 'connected' when it is available
+ * 3. This window proceeds to send the current presentation state
+ * to the notes window
+ */
+var RevealNotes = (function() {
+
+ function openNotes( notesFilePath ) {
+
+ if( !notesFilePath ) {
+ var jsFileLocation = document.querySelector('script[src$="notes.js"]').src; // this js file path
+ jsFileLocation = jsFileLocation.replace(/notes\.js(\?.*)?$/, ''); // the js folder path
+ notesFilePath = jsFileLocation + 'notes.html';
+ }
+
+ var notesPopup = window.open( notesFilePath, 'reveal.js - Notes', 'width=1100,height=700' );
+
+ // Allow popup window access to Reveal API
+ notesPopup.Reveal = this.Reveal;
+
+ /**
+ * Connect to the notes window through a postmessage handshake.
+ * Using postmessage enables us to work in situations where the
+ * origins differ, such as a presentation being opened from the
+ * file system.
+ */
+ function connect() {
+ // Keep trying to connect until we get a 'connected' message back
+ var connectInterval = setInterval( function() {
+ notesPopup.postMessage( JSON.stringify( {
+ namespace: 'reveal-notes',
+ type: 'connect',
+ url: window.location.protocol + '//' + window.location.host + window.location.pathname + window.location.search,
+ state: Reveal.getState()
+ } ), '*' );
+ }, 500 );
+
+ window.addEventListener( 'message', function( event ) {
+ var data = JSON.parse( event.data );
+ if( data && data.namespace === 'reveal-notes' && data.type === 'connected' ) {
+ clearInterval( connectInterval );
+ onConnected();
+ }
+ } );
+ }
+
+ /**
+ * Posts the current slide data to the notes window
+ */
+ function post( event ) {
+
+ var slideElement = Reveal.getCurrentSlide(),
+ notesElement = slideElement.querySelector( 'aside.notes' ),
+ fragmentElement = slideElement.querySelector( '.current-fragment' );
+
+ var messageData = {
+ namespace: 'reveal-notes',
+ type: 'state',
+ notes: '',
+ markdown: false,
+ whitespace: 'normal',
+ state: Reveal.getState()
+ };
+
+ // Look for notes defined in a slide attribute
+ if( slideElement.hasAttribute( 'data-notes' ) ) {
+ messageData.notes = slideElement.getAttribute( 'data-notes' );
+ messageData.whitespace = 'pre-wrap';
+ }
+
+ // Look for notes defined in a fragment
+ if( fragmentElement ) {
+ var fragmentNotes = fragmentElement.querySelector( 'aside.notes' );
+ if( fragmentNotes ) {
+ notesElement = fragmentNotes;
+ }
+ else if( fragmentElement.hasAttribute( 'data-notes' ) ) {
+ messageData.notes = fragmentElement.getAttribute( 'data-notes' );
+ messageData.whitespace = 'pre-wrap';
+
+ // In case there are slide notes
+ notesElement = null;
+ }
+ }
+
+ // Look for notes defined in an aside element
+ if( notesElement ) {
+ messageData.notes = notesElement.innerHTML;
+ messageData.markdown = typeof notesElement.getAttribute( 'data-markdown' ) === 'string';
+ }
+
+ notesPopup.postMessage( JSON.stringify( messageData ), '*' );
+
+ }
+
+ /**
+ * Called once we have established a connection to the notes
+ * window.
+ */
+ function onConnected() {
+
+ // Monitor events that trigger a change in state
+ Reveal.addEventListener( 'slidechanged', post );
+ Reveal.addEventListener( 'fragmentshown', post );
+ Reveal.addEventListener( 'fragmenthidden', post );
+ Reveal.addEventListener( 'overviewhidden', post );
+ Reveal.addEventListener( 'overviewshown', post );
+ Reveal.addEventListener( 'paused', post );
+ Reveal.addEventListener( 'resumed', post );
+
+ // Post the initial state
+ post();
+
+ }
+
+ connect();
+
+ }
+
+ if( !/receiver/i.test( window.location.search ) ) {
+
+ // If the there's a 'notes' query set, open directly
+ if( window.location.search.match( /(\?|\&)notes/gi ) !== null ) {
+ openNotes();
+ }
+
+ // Open the notes when the 's' key is hit
+ document.addEventListener( 'keydown', function( event ) {
+ // Disregard the event if the target is editable or a
+ // modifier is present
+ if ( document.querySelector( ':focus' ) !== null || event.shiftKey || event.altKey || event.ctrlKey || event.metaKey ) return;
+
+ // Disregard the event if keyboard is disabled
+ if ( Reveal.getConfig().keyboard === false ) return;
+
+ if( event.keyCode === 83 ) {
+ event.preventDefault();
+ openNotes();
+ }
+ }, false );
+
+ // Show our keyboard shortcut in the reveal.js help overlay
+ if( window.Reveal ) Reveal.registerKeyboardShortcut( 'S', 'Speaker notes view' );
+
+ }
+
+ return { open: openNotes };
+
+})();
diff --git a/plugin/print-pdf/print-pdf.js b/plugin/print-pdf/print-pdf.js
new file mode 100644
index 0000000..15ce43e
--- /dev/null
+++ b/plugin/print-pdf/print-pdf.js
@@ -0,0 +1,69 @@
+/**
+ * phantomjs script for printing presentations to PDF.
+ *
+ * Example:
+ * phantomjs print-pdf.js "http://revealjs.com?print-pdf" reveal-demo.pdf
+ *
+ * @author Manuel Bieh (https://github.com/manuelbieh)
+ * @author Hakim El Hattab (https://github.com/hakimel)
+ * @author Manuel Riezebosch (https://github.com/riezebosch)
+ */
+
+// html2pdf.js
+var system = require( 'system' );
+
+var probePage = new WebPage();
+var printPage = new WebPage();
+
+var inputFile = system.args[1] || 'index.html?print-pdf';
+var outputFile = system.args[2] || 'slides.pdf';
+
+if( outputFile.match( /\.pdf$/gi ) === null ) {
+ outputFile += '.pdf';
+}
+
+console.log( 'Export PDF: Reading reveal.js config [1/4]' );
+
+probePage.open( inputFile, function( status ) {
+
+ console.log( 'Export PDF: Preparing print layout [2/4]' );
+
+ var config = probePage.evaluate( function() {
+ return Reveal.getConfig();
+ } );
+
+ if( config ) {
+
+ printPage.paperSize = {
+ width: Math.floor( config.width * ( 1 + config.margin ) ),
+ height: Math.floor( config.height * ( 1 + config.margin ) ),
+ border: 0
+ };
+
+ printPage.open( inputFile, function( status ) {
+ console.log( 'Export PDF: Preparing pdf [3/4]')
+ printPage.evaluate(function() {
+ Reveal.isReady() ? window.callPhantom() : Reveal.addEventListener( 'pdf-ready', window.callPhantom );
+ });
+ } );
+
+ printPage.onCallback = function(data) {
+ // For some reason we need to "jump the queue" for syntax highlighting to work.
+ // See: http://stackoverflow.com/a/3580132/129269
+ setTimeout(function() {
+ console.log( 'Export PDF: Writing file [4/4]' );
+ printPage.render( outputFile );
+ console.log( 'Export PDF: Finished successfully!' );
+ phantom.exit();
+ }, 0);
+ };
+ }
+ else {
+
+ console.log( 'Export PDF: Unable to read reveal.js config. Make sure the input address points to a reveal.js page.' );
+ phantom.exit(1);
+
+ }
+} );
+
+
diff --git a/plugin/search/search.js b/plugin/search/search.js
new file mode 100644
index 0000000..f7e5c2f
--- /dev/null
+++ b/plugin/search/search.js
@@ -0,0 +1,206 @@
+/*
+ * Handles finding a text string anywhere in the slides and showing the next occurrence to the user
+ * by navigatating to that slide and highlighting it.
+ *
+ * By Jon Snyder , February 2013
+ */
+
+var RevealSearch = (function() {
+
+ var matchedSlides;
+ var currentMatchedIndex;
+ var searchboxDirty;
+ var myHilitor;
+
+// Original JavaScript code by Chirp Internet: www.chirp.com.au
+// Please acknowledge use of this code by including this header.
+// 2/2013 jon: modified regex to display any match, not restricted to word boundaries.
+
+function Hilitor(id, tag)
+{
+
+ var targetNode = document.getElementById(id) || document.body;
+ var hiliteTag = tag || "EM";
+ var skipTags = new RegExp("^(?:" + hiliteTag + "|SCRIPT|FORM)$");
+ var colors = ["#ff6", "#a0ffff", "#9f9", "#f99", "#f6f"];
+ var wordColor = [];
+ var colorIdx = 0;
+ var matchRegex = "";
+ var matchingSlides = [];
+
+ this.setRegex = function(input)
+ {
+ input = input.replace(/^[^\w]+|[^\w]+$/g, "").replace(/[^\w'-]+/g, "|");
+ matchRegex = new RegExp("(" + input + ")","i");
+ }
+
+ this.getRegex = function()
+ {
+ return matchRegex.toString().replace(/^\/\\b\(|\)\\b\/i$/g, "").replace(/\|/g, " ");
+ }
+
+ // recursively apply word highlighting
+ this.hiliteWords = function(node)
+ {
+ if(node == undefined || !node) return;
+ if(!matchRegex) return;
+ if(skipTags.test(node.nodeName)) return;
+
+ if(node.hasChildNodes()) {
+ for(var i=0; i < node.childNodes.length; i++)
+ this.hiliteWords(node.childNodes[i]);
+ }
+ if(node.nodeType == 3) { // NODE_TEXT
+ if((nv = node.nodeValue) && (regs = matchRegex.exec(nv))) {
+ //find the slide's section element and save it in our list of matching slides
+ var secnode = node;
+ while (secnode != null && secnode.nodeName != 'SECTION') {
+ secnode = secnode.parentNode;
+ }
+
+ var slideIndex = Reveal.getIndices(secnode);
+ var slidelen = matchingSlides.length;
+ var alreadyAdded = false;
+ for (var i=0; i < slidelen; i++) {
+ if ( (matchingSlides[i].h === slideIndex.h) && (matchingSlides[i].v === slideIndex.v) ) {
+ alreadyAdded = true;
+ }
+ }
+ if (! alreadyAdded) {
+ matchingSlides.push(slideIndex);
+ }
+
+ if(!wordColor[regs[0].toLowerCase()]) {
+ wordColor[regs[0].toLowerCase()] = colors[colorIdx++ % colors.length];
+ }
+
+ var match = document.createElement(hiliteTag);
+ match.appendChild(document.createTextNode(regs[0]));
+ match.style.backgroundColor = wordColor[regs[0].toLowerCase()];
+ match.style.fontStyle = "inherit";
+ match.style.color = "#000";
+
+ var after = node.splitText(regs.index);
+ after.nodeValue = after.nodeValue.substring(regs[0].length);
+ node.parentNode.insertBefore(match, after);
+ }
+ }
+ };
+
+ // remove highlighting
+ this.remove = function()
+ {
+ var arr = document.getElementsByTagName(hiliteTag);
+ while(arr.length && (el = arr[0])) {
+ el.parentNode.replaceChild(el.firstChild, el);
+ }
+ };
+
+ // start highlighting at target node
+ this.apply = function(input)
+ {
+ if(input == undefined || !input) return;
+ this.remove();
+ this.setRegex(input);
+ this.hiliteWords(targetNode);
+ return matchingSlides;
+ };
+
+}
+
+ function openSearch() {
+ //ensure the search term input dialog is visible and has focus:
+ var inputboxdiv = document.getElementById("searchinputdiv");
+ var inputbox = document.getElementById("searchinput");
+ inputboxdiv.style.display = "inline";
+ inputbox.focus();
+ inputbox.select();
+ }
+
+ function closeSearch() {
+ var inputboxdiv = document.getElementById("searchinputdiv");
+ inputboxdiv.style.display = "none";
+ if(myHilitor) myHilitor.remove();
+ }
+
+ function toggleSearch() {
+ var inputboxdiv = document.getElementById("searchinputdiv");
+ if (inputboxdiv.style.display !== "inline") {
+ openSearch();
+ }
+ else {
+ closeSearch();
+ }
+ }
+
+ function doSearch() {
+ //if there's been a change in the search term, perform a new search:
+ if (searchboxDirty) {
+ var searchstring = document.getElementById("searchinput").value;
+
+ if (searchstring === '') {
+ if(myHilitor) myHilitor.remove();
+ matchedSlides = null;
+ }
+ else {
+ //find the keyword amongst the slides
+ myHilitor = new Hilitor("slidecontent");
+ matchedSlides = myHilitor.apply(searchstring);
+ currentMatchedIndex = 0;
+ }
+ }
+
+ if (matchedSlides) {
+ //navigate to the next slide that has the keyword, wrapping to the first if necessary
+ if (matchedSlides.length && (matchedSlides.length <= currentMatchedIndex)) {
+ currentMatchedIndex = 0;
+ }
+ if (matchedSlides.length > currentMatchedIndex) {
+ Reveal.slide(matchedSlides[currentMatchedIndex].h, matchedSlides[currentMatchedIndex].v);
+ currentMatchedIndex++;
+ }
+ }
+ }
+
+ var dom = {};
+ dom.wrapper = document.querySelector( '.reveal' );
+
+ if( !dom.wrapper.querySelector( '.searchbox' ) ) {
+ var searchElement = document.createElement( 'div' );
+ searchElement.id = "searchinputdiv";
+ searchElement.classList.add( 'searchdiv' );
+ searchElement.style.position = 'absolute';
+ searchElement.style.top = '10px';
+ searchElement.style.right = '10px';
+ searchElement.style.zIndex = 10;
+ //embedded base64 search icon Designed by Sketchdock - http://www.sketchdock.com/:
+ searchElement.innerHTML = '';
+ dom.wrapper.appendChild( searchElement );
+ }
+
+ document.getElementById("searchbutton").addEventListener( 'click', function(event) {
+ doSearch();
+ }, false );
+
+ document.getElementById("searchinput").addEventListener( 'keyup', function( event ) {
+ switch (event.keyCode) {
+ case 13:
+ event.preventDefault();
+ doSearch();
+ searchboxDirty = false;
+ break;
+ default:
+ searchboxDirty = true;
+ }
+ }, false );
+
+ document.addEventListener( 'keydown', function( event ) {
+ if( event.key == "F" && (event.ctrlKey || event.metaKey) ) {//Control+Shift+f
+ event.preventDefault();
+ toggleSearch();
+ }
+ }, false );
+ if( window.Reveal ) Reveal.registerKeyboardShortcut( 'Ctrl-Shift-F', 'Search' );
+ closeSearch();
+ return { open: openSearch };
+})();
diff --git a/plugin/zoom-js/zoom.js b/plugin/zoom-js/zoom.js
new file mode 100644
index 0000000..8531790
--- /dev/null
+++ b/plugin/zoom-js/zoom.js
@@ -0,0 +1,272 @@
+// Custom reveal.js integration
+(function(){
+ var revealElement = document.querySelector( '.reveal' );
+ if( revealElement ) {
+
+ revealElement.addEventListener( 'mousedown', function( event ) {
+ var defaultModifier = /Linux/.test( window.navigator.platform ) ? 'ctrl' : 'alt';
+
+ var modifier = ( Reveal.getConfig().zoomKey ? Reveal.getConfig().zoomKey : defaultModifier ) + 'Key';
+ var zoomLevel = ( Reveal.getConfig().zoomLevel ? Reveal.getConfig().zoomLevel : 2 );
+
+ if( event[ modifier ] && !Reveal.isOverview() ) {
+ event.preventDefault();
+
+ zoom.to({
+ x: event.clientX,
+ y: event.clientY,
+ scale: zoomLevel,
+ pan: false
+ });
+ }
+ } );
+
+ }
+})();
+
+/*!
+ * zoom.js 0.3 (modified for use with reveal.js)
+ * http://lab.hakim.se/zoom-js
+ * MIT licensed
+ *
+ * Copyright (C) 2011-2014 Hakim El Hattab, http://hakim.se
+ */
+var zoom = (function(){
+
+ // The current zoom level (scale)
+ var level = 1;
+
+ // The current mouse position, used for panning
+ var mouseX = 0,
+ mouseY = 0;
+
+ // Timeout before pan is activated
+ var panEngageTimeout = -1,
+ panUpdateInterval = -1;
+
+ // Check for transform support so that we can fallback otherwise
+ var supportsTransforms = 'WebkitTransform' in document.body.style ||
+ 'MozTransform' in document.body.style ||
+ 'msTransform' in document.body.style ||
+ 'OTransform' in document.body.style ||
+ 'transform' in document.body.style;
+
+ if( supportsTransforms ) {
+ // The easing that will be applied when we zoom in/out
+ document.body.style.transition = 'transform 0.8s ease';
+ document.body.style.OTransition = '-o-transform 0.8s ease';
+ document.body.style.msTransition = '-ms-transform 0.8s ease';
+ document.body.style.MozTransition = '-moz-transform 0.8s ease';
+ document.body.style.WebkitTransition = '-webkit-transform 0.8s ease';
+ }
+
+ // Zoom out if the user hits escape
+ document.addEventListener( 'keyup', function( event ) {
+ if( level !== 1 && event.keyCode === 27 ) {
+ zoom.out();
+ }
+ } );
+
+ // Monitor mouse movement for panning
+ document.addEventListener( 'mousemove', function( event ) {
+ if( level !== 1 ) {
+ mouseX = event.clientX;
+ mouseY = event.clientY;
+ }
+ } );
+
+ /**
+ * Applies the CSS required to zoom in, prefers the use of CSS3
+ * transforms but falls back on zoom for IE.
+ *
+ * @param {Object} rect
+ * @param {Number} scale
+ */
+ function magnify( rect, scale ) {
+
+ var scrollOffset = getScrollOffset();
+
+ // Ensure a width/height is set
+ rect.width = rect.width || 1;
+ rect.height = rect.height || 1;
+
+ // Center the rect within the zoomed viewport
+ rect.x -= ( window.innerWidth - ( rect.width * scale ) ) / 2;
+ rect.y -= ( window.innerHeight - ( rect.height * scale ) ) / 2;
+
+ if( supportsTransforms ) {
+ // Reset
+ if( scale === 1 ) {
+ document.body.style.transform = '';
+ document.body.style.OTransform = '';
+ document.body.style.msTransform = '';
+ document.body.style.MozTransform = '';
+ document.body.style.WebkitTransform = '';
+ }
+ // Scale
+ else {
+ var origin = scrollOffset.x +'px '+ scrollOffset.y +'px',
+ transform = 'translate('+ -rect.x +'px,'+ -rect.y +'px) scale('+ scale +')';
+
+ document.body.style.transformOrigin = origin;
+ document.body.style.OTransformOrigin = origin;
+ document.body.style.msTransformOrigin = origin;
+ document.body.style.MozTransformOrigin = origin;
+ document.body.style.WebkitTransformOrigin = origin;
+
+ document.body.style.transform = transform;
+ document.body.style.OTransform = transform;
+ document.body.style.msTransform = transform;
+ document.body.style.MozTransform = transform;
+ document.body.style.WebkitTransform = transform;
+ }
+ }
+ else {
+ // Reset
+ if( scale === 1 ) {
+ document.body.style.position = '';
+ document.body.style.left = '';
+ document.body.style.top = '';
+ document.body.style.width = '';
+ document.body.style.height = '';
+ document.body.style.zoom = '';
+ }
+ // Scale
+ else {
+ document.body.style.position = 'relative';
+ document.body.style.left = ( - ( scrollOffset.x + rect.x ) / scale ) + 'px';
+ document.body.style.top = ( - ( scrollOffset.y + rect.y ) / scale ) + 'px';
+ document.body.style.width = ( scale * 100 ) + '%';
+ document.body.style.height = ( scale * 100 ) + '%';
+ document.body.style.zoom = scale;
+ }
+ }
+
+ level = scale;
+
+ if( document.documentElement.classList ) {
+ if( level !== 1 ) {
+ document.documentElement.classList.add( 'zoomed' );
+ }
+ else {
+ document.documentElement.classList.remove( 'zoomed' );
+ }
+ }
+ }
+
+ /**
+ * Pan the document when the mosue cursor approaches the edges
+ * of the window.
+ */
+ function pan() {
+ var range = 0.12,
+ rangeX = window.innerWidth * range,
+ rangeY = window.innerHeight * range,
+ scrollOffset = getScrollOffset();
+
+ // Up
+ if( mouseY < rangeY ) {
+ window.scroll( scrollOffset.x, scrollOffset.y - ( 1 - ( mouseY / rangeY ) ) * ( 14 / level ) );
+ }
+ // Down
+ else if( mouseY > window.innerHeight - rangeY ) {
+ window.scroll( scrollOffset.x, scrollOffset.y + ( 1 - ( window.innerHeight - mouseY ) / rangeY ) * ( 14 / level ) );
+ }
+
+ // Left
+ if( mouseX < rangeX ) {
+ window.scroll( scrollOffset.x - ( 1 - ( mouseX / rangeX ) ) * ( 14 / level ), scrollOffset.y );
+ }
+ // Right
+ else if( mouseX > window.innerWidth - rangeX ) {
+ window.scroll( scrollOffset.x + ( 1 - ( window.innerWidth - mouseX ) / rangeX ) * ( 14 / level ), scrollOffset.y );
+ }
+ }
+
+ function getScrollOffset() {
+ return {
+ x: window.scrollX !== undefined ? window.scrollX : window.pageXOffset,
+ y: window.scrollY !== undefined ? window.scrollY : window.pageYOffset
+ }
+ }
+
+ return {
+ /**
+ * Zooms in on either a rectangle or HTML element.
+ *
+ * @param {Object} options
+ * - element: HTML element to zoom in on
+ * OR
+ * - x/y: coordinates in non-transformed space to zoom in on
+ * - width/height: the portion of the screen to zoom in on
+ * - scale: can be used instead of width/height to explicitly set scale
+ */
+ to: function( options ) {
+
+ // Due to an implementation limitation we can't zoom in
+ // to another element without zooming out first
+ if( level !== 1 ) {
+ zoom.out();
+ }
+ else {
+ options.x = options.x || 0;
+ options.y = options.y || 0;
+
+ // If an element is set, that takes precedence
+ if( !!options.element ) {
+ // Space around the zoomed in element to leave on screen
+ var padding = 20;
+ var bounds = options.element.getBoundingClientRect();
+
+ options.x = bounds.left - padding;
+ options.y = bounds.top - padding;
+ options.width = bounds.width + ( padding * 2 );
+ options.height = bounds.height + ( padding * 2 );
+ }
+
+ // If width/height values are set, calculate scale from those values
+ if( options.width !== undefined && options.height !== undefined ) {
+ options.scale = Math.max( Math.min( window.innerWidth / options.width, window.innerHeight / options.height ), 1 );
+ }
+
+ if( options.scale > 1 ) {
+ options.x *= options.scale;
+ options.y *= options.scale;
+
+ magnify( options, options.scale );
+
+ if( options.pan !== false ) {
+
+ // Wait with engaging panning as it may conflict with the
+ // zoom transition
+ panEngageTimeout = setTimeout( function() {
+ panUpdateInterval = setInterval( pan, 1000 / 60 );
+ }, 800 );
+
+ }
+ }
+ }
+ },
+
+ /**
+ * Resets the document zoom state to its default.
+ */
+ out: function() {
+ clearTimeout( panEngageTimeout );
+ clearInterval( panUpdateInterval );
+
+ magnify( { x: 0, y: 0 }, 1 );
+
+ level = 1;
+ },
+
+ // Alias
+ magnify: function( options ) { this.to( options ) },
+ reset: function() { this.out() },
+
+ zoomLevel: function() {
+ return level;
+ }
+ }
+
+})();
diff --git a/screenshots/00_start.jpg b/screenshots/00_start.jpg
new file mode 100644
index 0000000..925ec11
Binary files /dev/null and b/screenshots/00_start.jpg differ
diff --git a/screenshots/01_update_3parti.jpg b/screenshots/01_update_3parti.jpg
new file mode 100644
index 0000000..0e286b2
Binary files /dev/null and b/screenshots/01_update_3parti.jpg differ
diff --git a/screenshots/02_scegliere_cifratura.jpg b/screenshots/02_scegliere_cifratura.jpg
new file mode 100644
index 0000000..c049b35
Binary files /dev/null and b/screenshots/02_scegliere_cifratura.jpg differ
diff --git a/screenshots/03_passphrase_discreta.jpg b/screenshots/03_passphrase_discreta.jpg
new file mode 100644
index 0000000..8abd408
Binary files /dev/null and b/screenshots/03_passphrase_discreta.jpg differ
diff --git a/screenshots/04_passphrase_buona.jpg b/screenshots/04_passphrase_buona.jpg
new file mode 100644
index 0000000..aa40883
Binary files /dev/null and b/screenshots/04_passphrase_buona.jpg differ
diff --git a/screenshots/05_partizionamento.jpg b/screenshots/05_partizionamento.jpg
new file mode 100644
index 0000000..2904441
Binary files /dev/null and b/screenshots/05_partizionamento.jpg differ
diff --git a/screenshots/06_tastiera.jpg b/screenshots/06_tastiera.jpg
new file mode 100644
index 0000000..2b63a1d
Binary files /dev/null and b/screenshots/06_tastiera.jpg differ
diff --git a/screenshots/07_timezone.jpg b/screenshots/07_timezone.jpg
new file mode 100644
index 0000000..46f1808
Binary files /dev/null and b/screenshots/07_timezone.jpg differ
diff --git a/screenshots/08_user_pwfragile.jpg b/screenshots/08_user_pwfragile.jpg
new file mode 100644
index 0000000..a6503b3
Binary files /dev/null and b/screenshots/08_user_pwfragile.jpg differ
diff --git a/screenshots/09_waiting.jpg b/screenshots/09_waiting.jpg
new file mode 100644
index 0000000..4dd6818
Binary files /dev/null and b/screenshots/09_waiting.jpg differ
diff --git a/screenshots/10_end.jpg b/screenshots/10_end.jpg
new file mode 100644
index 0000000..43fff16
Binary files /dev/null and b/screenshots/10_end.jpg differ
diff --git a/screenshots/11_ask_passphrase.jpg b/screenshots/11_ask_passphrase.jpg
new file mode 100644
index 0000000..1961bba
Binary files /dev/null and b/screenshots/11_ask_passphrase.jpg differ
diff --git a/screenshots/12_login.jpg b/screenshots/12_login.jpg
new file mode 100644
index 0000000..72e2747
Binary files /dev/null and b/screenshots/12_login.jpg differ
diff --git a/screenshots/13_menu.jpg b/screenshots/13_menu.jpg
new file mode 100644
index 0000000..85d3562
Binary files /dev/null and b/screenshots/13_menu.jpg differ
diff --git a/screenshots/13_menu_keypassx.jpg b/screenshots/13_menu_keypassx.jpg
new file mode 100644
index 0000000..cb2e6f5
Binary files /dev/null and b/screenshots/13_menu_keypassx.jpg differ
diff --git a/screenshots/14_keypassx.jpg b/screenshots/14_keypassx.jpg
new file mode 100644
index 0000000..5efb2ef
Binary files /dev/null and b/screenshots/14_keypassx.jpg differ
diff --git a/screenshots/15_nuovodb.jpg b/screenshots/15_nuovodb.jpg
new file mode 100644
index 0000000..95cf5b3
Binary files /dev/null and b/screenshots/15_nuovodb.jpg differ
diff --git a/screenshots/15_setpw.jpg b/screenshots/15_setpw.jpg
new file mode 100644
index 0000000..7e85e79
Binary files /dev/null and b/screenshots/15_setpw.jpg differ
diff --git a/screenshots/16_addcredenziali.jpg b/screenshots/16_addcredenziali.jpg
new file mode 100644
index 0000000..a0d2666
Binary files /dev/null and b/screenshots/16_addcredenziali.jpg differ
diff --git a/screenshots/16_addcredenziali2.jpg b/screenshots/16_addcredenziali2.jpg
new file mode 100644
index 0000000..ca7751d
Binary files /dev/null and b/screenshots/16_addcredenziali2.jpg differ
diff --git a/screenshots/19_2credenziali.jpg b/screenshots/19_2credenziali.jpg
new file mode 100644
index 0000000..97c433d
Binary files /dev/null and b/screenshots/19_2credenziali.jpg differ
diff --git a/screenshots/20_savedb.jpg b/screenshots/20_savedb.jpg
new file mode 100644
index 0000000..eef1d14
Binary files /dev/null and b/screenshots/20_savedb.jpg differ
diff --git a/screenshots/21_search_francia.jpg b/screenshots/21_search_francia.jpg
new file mode 100644
index 0000000..6dcc1c4
Binary files /dev/null and b/screenshots/21_search_francia.jpg differ
diff --git a/screenshots/22_reopen.jpg b/screenshots/22_reopen.jpg
new file mode 100644
index 0000000..2736cab
Binary files /dev/null and b/screenshots/22_reopen.jpg differ
diff --git a/screenshots/23_usbdisk_menu_tutto.jpg b/screenshots/23_usbdisk_menu_tutto.jpg
new file mode 100644
index 0000000..c422347
Binary files /dev/null and b/screenshots/23_usbdisk_menu_tutto.jpg differ
diff --git a/screenshots/24_usbdisk_menu_search_dischi.jpg b/screenshots/24_usbdisk_menu_search_dischi.jpg
new file mode 100644
index 0000000..3e9baa1
Binary files /dev/null and b/screenshots/24_usbdisk_menu_search_dischi.jpg differ
diff --git a/screenshots/25_usbdisk_diskutility.jpg b/screenshots/25_usbdisk_diskutility.jpg
new file mode 100644
index 0000000..403085d
Binary files /dev/null and b/screenshots/25_usbdisk_diskutility.jpg differ
diff --git a/screenshots/26_usbdisk_scelgo_crittare.jpg b/screenshots/26_usbdisk_scelgo_crittare.jpg
new file mode 100644
index 0000000..76cb056
Binary files /dev/null and b/screenshots/26_usbdisk_scelgo_crittare.jpg differ
diff --git a/screenshots/27_usbdisk_chiaverobusta.jpg b/screenshots/27_usbdisk_chiaverobusta.jpg
new file mode 100644
index 0000000..5157e77
Binary files /dev/null and b/screenshots/27_usbdisk_chiaverobusta.jpg differ
diff --git a/screenshots/28_usbdisk_creata_chiedepw.jpg b/screenshots/28_usbdisk_creata_chiedepw.jpg
new file mode 100644
index 0000000..f1f4abf
Binary files /dev/null and b/screenshots/28_usbdisk_creata_chiedepw.jpg differ
diff --git a/screenshots/29_usbdisk_decrittata.jpg b/screenshots/29_usbdisk_decrittata.jpg
new file mode 100644
index 0000000..d2f5c2f
Binary files /dev/null and b/screenshots/29_usbdisk_decrittata.jpg differ
diff --git a/screenshots/30_wipe_azionepers.jpg b/screenshots/30_wipe_azionepers.jpg
new file mode 100644
index 0000000..be4bd23
Binary files /dev/null and b/screenshots/30_wipe_azionepers.jpg differ
diff --git a/screenshots/31_wipe_aggiungoazione.jpg b/screenshots/31_wipe_aggiungoazione.jpg
new file mode 100644
index 0000000..a6ba699
Binary files /dev/null and b/screenshots/31_wipe_aggiungoazione.jpg differ
diff --git a/screenshots/32_wipe_settandoazione1.jpg b/screenshots/32_wipe_settandoazione1.jpg
new file mode 100644
index 0000000..6e4b650
Binary files /dev/null and b/screenshots/32_wipe_settandoazione1.jpg differ
diff --git a/screenshots/33_wipe_settandoazione2.jpg b/screenshots/33_wipe_settandoazione2.jpg
new file mode 100644
index 0000000..4720d4a
Binary files /dev/null and b/screenshots/33_wipe_settandoazione2.jpg differ
diff --git a/screenshots/34_wipe_file_dir.jpg b/screenshots/34_wipe_file_dir.jpg
new file mode 100644
index 0000000..f222fda
Binary files /dev/null and b/screenshots/34_wipe_file_dir.jpg differ
diff --git a/screenshots/35_metadata_brutti.jpg b/screenshots/35_metadata_brutti.jpg
new file mode 100644
index 0000000..2f3a4ba
Binary files /dev/null and b/screenshots/35_metadata_brutti.jpg differ
diff --git a/screenshots/36_metadata_brutti2pdf.jpg b/screenshots/36_metadata_brutti2pdf.jpg
new file mode 100644
index 0000000..db7b5c4
Binary files /dev/null and b/screenshots/36_metadata_brutti2pdf.jpg differ
diff --git a/screenshots/37_metadata_brutti3doc.jpg b/screenshots/37_metadata_brutti3doc.jpg
new file mode 100644
index 0000000..cafb350
Binary files /dev/null and b/screenshots/37_metadata_brutti3doc.jpg differ
diff --git a/screenshots/38_metadata_azionepers.jpg b/screenshots/38_metadata_azionepers.jpg
new file mode 100644
index 0000000..be4bd23
Binary files /dev/null and b/screenshots/38_metadata_azionepers.jpg differ
diff --git a/screenshots/39_metadata_aggiungoazione.jpg b/screenshots/39_metadata_aggiungoazione.jpg
new file mode 100644
index 0000000..a6ba699
Binary files /dev/null and b/screenshots/39_metadata_aggiungoazione.jpg differ
diff --git a/screenshots/40_metadata_settandoazione1.jpg b/screenshots/40_metadata_settandoazione1.jpg
new file mode 100644
index 0000000..0c48a44
Binary files /dev/null and b/screenshots/40_metadata_settandoazione1.jpg differ
diff --git a/screenshots/42_metadata_settandoazione2.jpg b/screenshots/42_metadata_settandoazione2.jpg
new file mode 100644
index 0000000..9473fd3
Binary files /dev/null and b/screenshots/42_metadata_settandoazione2.jpg differ
diff --git a/screenshots/crealista.sh b/screenshots/crealista.sh
new file mode 100755
index 0000000..8a22efb
--- /dev/null
+++ b/screenshots/crealista.sh
@@ -0,0 +1,8 @@
+!#/bin/bash
+
+for i in `cat $1`; do
+echo "
+ ##
+ ![](./screenshots/$i)
+ "
+done
diff --git a/screenshots/e nu b/screenshots/e nu
new file mode 100644
index 0000000..a2f819e
--- /dev/null
+++ b/screenshots/e nu
@@ -0,0 +1,43 @@
+00_start.jpg
+01_update_3parti.jpg
+02_scegliere_cifratura.jpg
+03_passphrase_discreta.jpg
+04_passphrase_buona.jpg
+05_partizionamento.jpg
+06_tastiera.jpg
+07_timezone.jpg
+08_user_pwfragile.jpg
+09_waiting.jpg
+10_end.jpg
+11_ask_passphrase.jpg
+12_login.jpg
+13_menu.jpg
+13_menu_keypassx.jpg
+14_keypassx.jpg
+15_nuovodb.jpg
+15_setpw.jpg
+16_addcredenziali2.jpg
+16_addcredenziali.jpg
+19_2credenziali.jpg
+20_savedb.jpg
+21_search_francia.jpg
+22_reopen.jpg
+23_usbdisk_menu_tutto.jpg
+24_usbdisk_menu_search_dischi.jpg
+25_usbdisk_diskutility.jpg
+26_usbdisk_scelgo_crittare.jpg
+27_usbdisk_chiaverobusta.jpg
+28_usbdisk_creata_chiedepw.jpg
+29_usbdisk_decrittata.jpg
+30_wipe_azionepers.jpg
+31_wipe_aggiungoazione.jpg
+32_wipe_settandoazione1.jpg
+33_wipe_settandoazione2.jpg
+34_wipe_file_dir.jpg
+35_metadata_brutti.jpg
+36_metadata_brutti2pdf.jpg
+37_metadata_brutti3doc.jpg
+38_metadata_azionepers.jpg
+39_metadata_aggiungoazione.jpg
+40_metadata_settandoazione1.jpg
+42_metadata_settandoazione2.jpg
diff --git a/screenshots/lista_immagini b/screenshots/lista_immagini
new file mode 100644
index 0000000..115a018
--- /dev/null
+++ b/screenshots/lista_immagini
@@ -0,0 +1,44 @@
+00_start.jpg
+01_update_3parti.jpg
+02_scegliere_cifratura.jpg
+03_passphrase_discreta.jpg
+04_passphrase_buona.jpg
+05_partizionamento.jpg
+06_tastiera.jpg
+07_timezone.jpg
+08_user_pwfragile.jpg
+09_waiting.jpg
+10_end.jpg
+11_ask_passphrase.jpg
+12_login.jpg
+13_menu.jpg
+13_menu_keypassx.jpg
+14_keypassx.jpg
+15_nuovodb.jpg
+15_setpw.jpg
+16_addcredenziali2.jpg
+16_addcredenziali.jpg
+19_2credenziali.jpg
+20_savedb.jpg
+21_search_francia.jpg
+22_reopen.jpg
+23_usbdisk_menu_tutto.jpg
+24_usbdisk_menu_search_dischi.jpg
+25_usbdisk_diskutility.jpg
+26_usbdisk_scelgo_crittare.jpg
+27_usbdisk_chiaverobusta.jpg
+28_usbdisk_creata_chiedepw.jpg
+29_usbdisk_decrittata.jpg
+30_wipe_azionepers.jpg
+31_wipe_aggiungoazione.jpg
+32_wipe_settandoazione1.jpg
+33_wipe_settandoazione2.jpg
+34_wipe_file_dir.jpg
+35_metadata_brutti.jpg
+36_metadata_brutti2pdf.jpg
+37_metadata_brutti3doc.jpg
+38_metadata_azionepers.jpg
+39_metadata_aggiungoazione.jpg
+40_metadata_settandoazione1.jpg
+42_metadata_settandoazione2.jpg
+
diff --git a/screenshots/listaimmagini.md b/screenshots/listaimmagini.md
new file mode 100644
index 0000000..f779a09
--- /dev/null
+++ b/screenshots/listaimmagini.md
@@ -0,0 +1,184 @@
+
+ ##
+ ![](./screenshots/00_start.jpg)
+
+
+ ##
+ ![](./screenshots/01_update_3parti.jpg)
+
+
+ ##
+ ![](./screenshots/02_scegliere_cifratura.jpg)
+
+
+ ##
+ ![](./screenshots/03_passphrase_discreta.jpg)
+
+
+ ##
+ ![](./screenshots/04_passphrase_buona.jpg)
+
+
+ ##
+ ![](./screenshots/05_partizionamento.jpg)
+
+
+ ##
+ ![](./screenshots/06_tastiera.jpg)
+
+
+ ##
+ ![](./screenshots/07_timezone.jpg)
+
+
+ ##
+ ![](./screenshots/08_user_pwfragile.jpg)
+
+
+ ##
+ ![](./screenshots/09_waiting.jpg)
+
+
+ ##
+ ![](./screenshots/10_end.jpg)
+
+
+ ##
+ ![](./screenshots/11_ask_passphrase.jpg)
+
+
+ ##
+ ![](./screenshots/12_login.jpg)
+
+
+ ##
+ ![](./screenshots/13_menu.jpg)
+
+
+ ##
+ ![](./screenshots/13_menu_keypassx.jpg)
+
+
+ ##
+ ![](./screenshots/14_keypassx.jpg)
+
+
+ ##
+ ![](./screenshots/15_nuovodb.jpg)
+
+
+ ##
+ ![](./screenshots/15_setpw.jpg)
+
+
+ ##
+ ![](./screenshots/16_addcredenziali2.jpg)
+
+
+ ##
+ ![](./screenshots/16_addcredenziali.jpg)
+
+
+ ##
+ ![](./screenshots/19_2credenziali.jpg)
+
+
+ ##
+ ![](./screenshots/20_savedb.jpg)
+
+
+ ##
+ ![](./screenshots/21_search_francia.jpg)
+
+
+ ##
+ ![](./screenshots/22_reopen.jpg)
+
+
+ ##
+ ![](./screenshots/23_usbdisk_menu_tutto.jpg)
+
+
+ ##
+ ![](./screenshots/24_usbdisk_menu_search_dischi.jpg)
+
+
+ ##
+ ![](./screenshots/25_usbdisk_diskutility.jpg)
+
+
+ ##
+ ![](./screenshots/26_usbdisk_scelgo_crittare.jpg)
+
+
+ ##
+ ![](./screenshots/27_usbdisk_chiaverobusta.jpg)
+
+
+ ##
+ ![](./screenshots/28_usbdisk_creata_chiedepw.jpg)
+
+
+ ##
+ ![](./screenshots/29_usbdisk_decrittata.jpg)
+
+
+ ##
+ ![](./screenshots/30_wipe_azionepers.jpg)
+
+
+ ##
+ ![](./screenshots/31_wipe_aggiungoazione.jpg)
+
+
+ ##
+ ![](./screenshots/32_wipe_settandoazione1.jpg)
+
+
+ ##
+ ![](./screenshots/33_wipe_settandoazione2.jpg)
+
+
+ ##
+ ![](./screenshots/34_wipe_file_dir.jpg)
+
+
+ ##
+ ![](./screenshots/35_metadata_brutti.jpg)
+
+
+ ##
+ ![](./screenshots/36_metadata_brutti2pdf.jpg)
+
+
+ ##
+ ![](./screenshots/37_metadata_brutti3doc.jpg)
+
+
+ ##
+ ![](./screenshots/38_metadata_azionepers.jpg)
+
+
+ ##
+ ![](./screenshots/39_metadata_aggiungoazione.jpg)
+
+
+ ##
+ ![](./screenshots/40_metadata_settandoazione1.jpg)
+
+
+ ##
+ ![](./screenshots/42_metadata_settandoazione2.jpg)
+
+
+ ##
+ ![](./screenshots/e)
+
+
+ ##
+ ![](./screenshots/nu)
+
+
+ ##
+ ![](./screenshots/lista_immagini)
+
diff --git a/slides/anonimato.md b/slides/anonimato.md
new file mode 100644
index 0000000..d27e5c1
--- /dev/null
+++ b/slides/anonimato.md
@@ -0,0 +1,122 @@
+
+
+## anonimato
+
+--
+
+## anonimato
+
+Come la sicurezza, non è una proprietà, non si compra, non si installa, ci
+devi mettere il cervello. stacce.
+
+Ci sono strumenti, da usare in determinate occasioni, dipende dal vostro
+modello di rischio.
+
+--
+
+## chi sono?
+
+L'indirizzo ip è un numero composto da 4 cifre da 0 a 255 che indica il
+dispositivo che ci collega ad internet in un momento X (anche il telefono
+ne ha uno).
+
+Gli operatori telefonici tengono dei registri delle assegnazioni di questi
+indirizzi.
+
+Quando interagisco con un sito (ad esempio invio la foto di un corteo),
+quel sito e tutti quelli che sono tra me e il sito, sapranno l'indirizzo ip
+del mittente, quindi se quella foto è problematica, verranno a bussarmi
+sotto casa.
+
+notes: pippa su ipv6
+
+--
+
+## Tor
+
+Tor è lo "strumento" più famoso per ottenere l'anonimato in rete.
+
+In sostanza un'altra persona si prende l'accollo e la responsabilità delle
+tue attività, senza poter sapere chi sei e cosa vuoi (ma perchè lo fa?).
+
+Un'eventuale ascoltatore (attaccante) vedrà che stai interagendo attraverso
+la rete Tor, ma non cosa fai e con chi.
+
+Numeri: utenti: più di 2milioni al giorno nodi: 7mila
+
+--
+
+
+
+--
+
+## Tor Browser
+
+Tor Browser è un browser appositamente studiato per funzionare attraverso
+la rete Tor in automatico e senza troppo sbattimento.
+
+Si occupa anche di preservare l'anonimato in altri modi.
+
+Su android ci sono Tor Browser e Orbot!
+
+--
+
+## Deanonimizzare
+
+La tua identità non è correlata solamente ad un indirizzo ip.
+
+Se postate un commento dal vostro account facebook con Tor Browser, mi
+serve l'ip per capire chi ha scritto quel commento?
+
+--
+
+### Deanonimizzare
+
+Ci sono mille altri modi per deanonimizzare, in sostanza si cerca di creare
+un'impronta univoca vostra, attraverso varie tecniche:
+
+- la risoluzione del monitor che state usando
+- caratteristiche del browser (lingue supportate, font, sistema operativo,
+ plugin installati, impostazioni, velocità)
+- attacchi basati su tempo/spazio particolari.
+- comportamenti particolari ([biometria](https://www.typingdna.com/)
+ [comportamentale](https://www.keytrac.net/en/tryout))
+- aneddoto hardvard
+
+[Tor Browser](https://www.torproject.org/download/download-easy.html.en)
+cerca di risolvere la maggior parte di questi attacchi.
+
+--
+
+## VPN
+
+Le VPN sono un modo sicuro di collegare computer su internet.
+
+Vengono utilizzate ad esempio per collegare uffici di una stessa azienda
+senza che nessuno possa sbirciare il traffico (il collegamento è cifrato).
+
+--
+
+## VPN
+
+Ci sono VPN che vengono invece usate per offrire protezione agli utenti
+facendoli accedere ad internet attraverso di loro
+([riseup](https://riseup.net/en/vpn) [protonvpn](https://protonvpn.com/))
+
+- proteggervi dal controllo da parte dei provider (ISP)
+- ovviare alla censura di stato
+- accedere a servizi vietati nel vostro paese
+- bypassare il firewall del vostro ufficio
+- rendere più sicuro il vostro traffico su reti Wi-Fi non protette
+
+--
+
+## Tails
+
+[The amnesic incognito live system](https://tails.boum.org/index.it.html)
+
+E' un sistema operativo live, vuole dire che non lo installi ma parte da
+una pennetta USB:
+
+- non lascia tracce delle tue scorribande perche' non salva niente.
+- usa Tor per tutto.
\ No newline at end of file
diff --git a/slides/comunicare.md b/slides/comunicare.md
new file mode 100644
index 0000000..d07a173
--- /dev/null
+++ b/slides/comunicare.md
@@ -0,0 +1,51 @@
+
+
+## Comunicazione
+
+--
+
+## uno a uno
+
+- mail
+- telefonata
+- sms
+- whatsapp
+- telegram
+- jabber
+- cifrare lecomunicazioni
+
+--
+
+## molti a molti (gruppi)
+
+- whatsapp
+- telegram
+- facebook
+- mailing list
+- jabber
+- irc
+- mastodon
+- cifrare le comunicazioni
+
+--
+
+## Ma quindi...
+
+--
+
+## PGP (mail cifrate)
+
+- criptografia forte
+- funziona
+- è un casino da usare
+
+--
+
+## Signal
+
+- criptografia forte
+- come qualsiasi app di messaggistica
+- comunicazione real time
+- autodistruzione dei messaggi
+- si può impostare il pin (fatelo!)
+
diff --git a/slides/dati.md b/slides/dati.md
new file mode 100644
index 0000000..804a7fc
--- /dev/null
+++ b/slides/dati.md
@@ -0,0 +1,76 @@
+
+
+### Sicurezza dei dati
+
+--
+
+### Sicurezza dei dati
+
+Puoi perdere/rompere un dispositivo o possono sequestrarlo.
+Prima o poi succede...
+
+![think](img/think.jpg)
+
+
+--
+
+## Come risolvo?
+
+ - con frequenti backup
+ - cifrando i dati
+
+--
+
+### Backup
+
+- disco locale (ok, ma se nel nostro modello di rischio c'e' un probabile sequestro non funziona)
+- remoto (ok, cifrato va bene dove vogliamo, anche su google/dropbox)
+
+dei programmi che ci sentiamo di consigliare sono:
+- per linux [Déjà Dup](https://wiki.gnome.org/Apps/DejaDup) che si basa su [duplicity](http://duplicity.nongnu.org/)
+- per android consigliamo [adb](https://www.androidworld.it/2018/03/27/backup-android-543009/) agli smanettoni
+
+--
+
+## Cifratura disco
+
+E' facile! Richiede solo l'inserimento di una passphrase all'avvio del computer o di un pin all'avvio del telefono.
+
+Con una [buona passphrase](#/2/11)/pin il contenuto del disco sarà al sicuro per un po'.
+
+--
+
+## Alcune precisazioni
+
+I dati sono in chiaro a computer acceso,
+quindi non lasciarlo incustodito (per poco tempo blocca lo schermo per qualsiasi modello di rischio),
+un'alternativa e' fare un'altra partizione cifrata da aprire
+solo quando lavori con quel materiale sensibile.
+
+notes:
+se suonano alla porta, spegni il computer o smonta la partizione cifrata prima di aprire.
+
+--
+
+## Cancellazione sicura dei dati
+
+Per ottimizzare, quando eliminiamo un file, il sistema operativo segna solo
+come libero il posto che occupa, non ne sovrascrive il contenuto.
+E' possibile recuperarne il contenuto.
+
+Nel caso il disco sia cifrato il pericolo e' minore, anche nel caso
+il disco sia un SSD.
+
+Se passate la frontiera o vendete il vostro computer, consideratelo:
+esistono vari programmi per eliminare in maniera sicura i file.
+
+--
+
+## Compartimentazione
+
+Ho bisogno di avere tutti i dati su ogni dispositivo?
+
+- mi servono le mail sul telefono?
+- ho bisogno delle chat sul computer?
+
+Spesso la miglior tutela dei dati si ottiene non avendoli ;)
diff --git a/slides/intro.md b/slides/intro.md
new file mode 100644
index 0000000..6a4849a
--- /dev/null
+++ b/slides/intro.md
@@ -0,0 +1,101 @@
+
+
+## Autodifesa digitale
+
+
+[underscore_to hacklab](https://autistici.org/underscore)
+
+notes:
+qui compariranno delle note...
+
+--
+
+## INTRO
+Queste slide intendono essere una panoramica concisa di autodifesa digitale.
+
+Rappresentano un'insieme di conoscenze e buone pratiche tratte da varie fonti
+ed esperienze.
+
+Sono pensate per essere usufruibili anche da web quindi abbiamo scritto tanto.
+
+--
+
+### Riservatezza, sicurezza, intimità digitali
+
+- Non sono proprietà.
+- Non si comprano, non è un programma che installi e bona.
+- E' un processo, bisogna provare, sbagliare, imparare, **metterci attenzione**, stacce.
+- E' un approccio mentale.
+- In generale, stai delegando, cerca di farlo il meno possibile e fallo almeno in rapporti di fiducia.
+
+--
+
+### Ma è sicuro?
+- La sicurezza non è mai 100%, dobbiamo attuare una politica di riduzione del danno, non abbiamo altro.
+- L'illusione della sicurezza è decisamente peggio della consapevolezza di essere vulnerabili.
+
+--
+
+Inoltre comportamenti e strumenti da adottare in alcuni casi,
+in altri non vanno bene.
+
+![](./img/pasta-e-forchetta.jpg)
+
+![](./img/brodino.jpg)
+
+
+--
+
+### Modello di rischio
+Bisogna che tu capisca il tuo modello di rischio
+rispondendo alle seguenti domande:
+
+ - **da chi voglio proteggermi?** (la mamma, il/la compagn*, facebook, il datore di lavoro, la digos, i rettiliani)
+
+
+ - **cosa voglio proteggere?** (l'identità, i contatti, le preferenze sessuali, le comunicazioni)
+
+
+ - **quali sono gli attacchi più probabili?** (sequestro, intercettazione, leak)
+
+
+--
+
+### Esempi
+
+ - il tempo cambia sia i rapporti di fiducia (es. un/una ex) ..
+ - sia i livelli di rischio
+ - perdiamo il telefono
+ - sequestro
+
+notes: proporre una riflessione collettiva su uno scenario
+
+---
+
+### E quindi?
+Che modello di rischio scegliamo noi?
+Siccome e' impossibile difendersi da un attaccante sufficientemente potente,
+ma soprattutto, la maggior parte di noi non deve avere a che fare con l'NSA o NSO,
+prendiamo come modello di rischio quello che vede un'autorita' locale voler
+in qualche modo indagare su di noi.
+
+--
+### Dai, ma chi mi caga?
+
+Guardando la spesa statale per le tecnologie di sorveglianza ad uso poliziesco, qualcuno ti considera.
+
+
+- [quanto spende il ministero dell'interno](https://motherboard.vice.com/it/article/padegg/quanto-spende-il-governo-italiano-per-le-tecnologie-di-sorveglianza)
+- [quanto spende il ministero della giustizia](https://www.vice.com/it/article/43ja4q/listino-prezzi-intercettazioni-dispositivi-procura-milano-mercato-malware)
+- [statistiche ministero della giustizia](https://archive.org/details/DeterminazioneDeiNuoviPrezziIntercettazioni/page/n3)
+- [filiera delle intercettazioni](https://www.ilsole24ore.com/art/notizie/2018-08-03/le-intercettazioni-costano-169-milioni-2017-oltre-127mila-bersagli-190839.shtml)
+- [prezzi intercettazioni](https://archive.org/details/DeterminazioneDeiNuoviPrezziIntercettazioni/page/n3)
+- [paranoia gratuita](https://motherboard.vice.com/it/article/evv3xp/i-video-che-metti-online-vengono-spiati-dalla-polizia-italiana)
+- [aggiornamenti legge italiana uso trojan](https://motherboard.vice.com/it/article/7xedna/la-legge-italiana-sulluso-dei-trojan-e-un-disastro)
diff --git a/slides/liberta.md b/slides/liberta.md
new file mode 100644
index 0000000..0c44222
--- /dev/null
+++ b/slides/liberta.md
@@ -0,0 +1,69 @@
+
+
+### Free
+### Software
+
+--
+
+### Free Software
+
+Per parlare del software libero (free non vuol dire gratuito) ci vorrebbero ore,
+ma qui ci interessa solo sottolineare quali sono le principali differenze,
+tra i sistemi operativi e le applicazioni dal punto di vista della **sicurezza**.
+
+--
+
+### Proprietario? No thanks
+
+I sistemi operativi e le applicazioni proprietarie (es. Windows, MacOS, iOS),
+sono sistemi chiusi.
+
+Significa che nessuno puo' conoscerne il contenuto.
+
+Svolgono delle funzioni, ma come lo fanno o se mentre svolgono le loro funzioni facciano anche altre cose noi non lo sappiamo.
+
+--
+
+### Se è Libero ... MEGLIO!
+
+Il software libero, invece è accessibile a tutti.
+
+Di qualsiasi programma o parte del sistema sono disponibili e pubblici,
+i sorgenti.
+
+Chiunque abbia la giusta competenza può controllare cosa e come svolgono
+le loro funzioni.
+
+--
+
+### Fiducia
+
+La comunità che collabora allo sviluppo del software libero è,
+essa stessa garanzia di controllo sui suoi contenuti.
+
+Su una comunità così numerosa si può essere confidenti che eventuali,
+problemi siano tempestivamente individuati e segnalati.
+
+--
+
+### Consigli
+
+- Sul computer installate [linux](http://www.linux.it/distro) (facile)
+- Se avete un telefono con android potete
+ installare [LineageOS](https://www.lineageos.org/) (meno facile)
+
+notes:
+parlare di fdroid (https://www.reddit.com/r/privacy/comments/3cjj2e/how_secure_is_fdroid/) https://f-droid.org/en/docs/Security_Model/
+
+--
+### Alcuni numeri
+
+dal 2005 ad oggi circa 13500 sviluppatori hanno contribuito al solo sviluppo del kernel linux.
+
+- [GitHub](https://github.com): conta quasi 5M di repositories.
+- [SourceForge](https://sourceforge.net) ospita 324000 progetti.
+- [Ohloh](https://www.openhub.net) ospita 550000 progetti.
+- [Queste slides](https://git.lattuga.net/cisti/autodifesa-digitale-parte-1/) sono libere (sono un fork bolognese).
+
+notes:
+vlc, android, gnome, arduino, open hardware
diff --git a/slides/metadata.md b/slides/metadata.md
new file mode 100644
index 0000000..da8ce86
--- /dev/null
+++ b/slides/metadata.md
@@ -0,0 +1,100 @@
+
+
+--
+
+## MetaDati
+
+> We kill people based on metadata
+
+Michael Hayden, former CIA and NSA director /
+[source](https://www.youtube.com/watch?v=UdQiz0Vavmc#t=27s)
+
+--
+
+## Metadati
+
+Sono dati che descrivono pezzi di informazione tranne l'informazione
+stessa. Il contenuto di un messaggio non è il metadato, ma chi l'ha
+mandato, a chi, da dove e quando sono tutti esempi di metadati.
+
+--
+
+## Metadati
+
+Ogni informazione digitalizzata si porta dietro dei metadati:
+- le comunicazioni (sms/telefonate/chat/WA)
+
+- immagini/pdf (autore, geolocalizzazione, etc..)
+
+- email (soggetto, destinatario, ora invio)
+
+
+--
+
+## A che servono i contenuti se...
+
+- so che hai chiamato una sex line alle 2.24 e hai parlato per 18 minuti
+
+- che alle 4 del pomeriggio hai chiamato un numero verde per la prevenzione
+ suicidi.
+
+- hai ricevuto una mail da un servizio di check HIV e poi hai chiamato il
+ tuo medico di base e visitato un forum di sieropositivi nella stessa ora.
+
+- hai chiamato la tua ginecologa, ci hai parlato per mezz'ora e poi hai
+ chiamato una clinica privata specializzata in aborti
+
+
+--
+
+## E quindi?
+
+In molti sistemi legali solitamente si progettono i contenuti molto meglio
+dei metadati, ad esempio in italia le telefonate vengono registrate
+solamente in caso di indagini in corso per reati di un certo livello,
+mentre gli operatori telefonici sono per legge obbligati a mantenere i
+metadati delle telefonate per 24 mesi, i famosi tabulati telefonici.
+
+--
+
+## METADATI vs CONTENUTI
+
+La narrazione riguardo questa distinzione, cioe' il trattamento differente
+dei contenuti rispetto a quello dei metadati, descrive i metadati come se
+non fossero un grande problema, come se fossero molto meno invasivi della
+persona rispetto al contenuto vero e proprio delle comunicazioni. In
+realtà è vero il contrario
+
+notes: per quanto riguarda il controllo massivo...
+
+--
+
+## issue
+
+I metadati sono in forma testuale ed e' quindi possibile fare delle
+ricerche massive su di essi, indicizzarli, categorizzarli, cosa impossibile
+da fare con le comunicazioni vere e proprie.
+
+Avendo i metadati e' possibile cercare tutte le telefonate effettuate verso
+un numero, o da un numero, o in un lasso di tempo, o da un luogo
+specificato, nessuna di queste ricerche risulta possibile invece avendo
+solo il contenuto delle comunicazioni.
+
+--
+
+## Aneddoto
+
+- [mcafee](https://www.npr.org/sections/thetwo-way/2012/12/04/166487197/betrayed-by-metadata-john-mcafee-admits-hes-really-in-guatemala?t=1543618516954)
+- [mcafee
+ 2](https://nakedsecurity.sophos.com/2012/12/03/john-mcafee-location-exif/)
+
+--
+
+## Come mi proteggo?
+
+La consapevolezza è già un grande passo avanti. Puoi usare alcuni
+strumenti per rimuovere i metadati dai file:
+
+- per android c'è [Scrambled
+ Exif](https://f-droid.org/en/packages/com.jarsilio.android.scrambledeggsif/)
+- su linux c'è [mat](https://0xacab.org/jvoisin/mat2)
\ No newline at end of file
diff --git a/slides/navigare.md b/slides/navigare.md
new file mode 100644
index 0000000..3897850
--- /dev/null
+++ b/slides/navigare.md
@@ -0,0 +1,87 @@
+
+
+## Navigazione nell'Internet
+
+--
+
+Finora non abbiamo parlato dei pericoli della rete, ma solo quelli del
+nostro dispositivo, considerandolo disconnesso.
+
+--
+
+### Come ci connettiamo?
+
+ - Wifi? Cambiate la password di default.
+ - [Disabilitate il WPS del
+ router](https://www.tomshw.it/sistema-wps-router-vulnerabile-meglio-spegnerlo-37486).
+ - Wifi pubbliche? usare VPN, vedi dopo.
+ - Dal telefono, disabilitare il wifi quando non lo usate.
+ - Preferite il cavo di rete quando potete.
+
+notes: i dispositivi wifi broadcastano i MAC ai router se non impostati per
+non farlo (esempio metro di londra)
+https://tfl.gov.uk/corporate/publications-and-reports/wifi-data-collection
+
+--
+
+## Buone pratiche
+
+ - Controlla la barra di navigazione (https? il sito è giusto?)
+ - Sui link sospetti, controlla prima di cliccarci sopra
+ - Cambiare motore di ricerca di default (usate
+ [duckduckgo](https://duckduckgo.com))
+ - Salvare le password? (meglio di no)
+ - Usate i Feed/RSS, ad esempio con [Brief](https://addons.mozilla.org/it/firefox/addon/brief/)
+ - Usate [Tor
+ Browser](https://www.torproject.org/download/download-easy.html.en)
+ - Usate profili differenti o containers per non condividere cookie
+ - Gli allegati delle mail sono un classico vettore di malware, occhio
+
+--
+
+## Ctrl+C... Ctrl+V
+### AKA: Attenzione al copia/incolla
+Se ti capita di copia-incollare comandi dall'internet al tuo terminale, il consiglio è di farci
+un po' di attenzione.
+Non sempre quello che si vede è esattamente quello che c'è.
+Dietro ad un comando apparententemente innocuo tipo "sudo apt update" si può [nascondere del codice](https://www.bleepingcomputer.com/news/security/dont-copy-paste-commands-from-webpages-you-can-get-hacked/) che può essere anche moooolto dannoso.
+
+Consiglio: prima di incollare un comando nel terminale, incollalo in un qualsiasi editor di testo;
+questo ti permetterà di verificare cosa, effettivamente, hai copiato.
+
+--
+
+## Estensioni utili
+
+ - [duckduckgo privacy
+ essentials](https://chrome.google.com/webstore/detail/duckduckgo-privacy-essent/bkdgflcldnnnapblkhphbgpggdiikppg)
+ - ublock/[adblock plus](https://adblockplus.org/)
+ - [disconnect](https://addons.mozilla.org/en-US/firefox/addon/disconnect/)
+ - [facebook
+ container](https://addons.mozilla.org/en-US/firefox/addon/facebook-container/)
+ - [decentraleyes](https://addons.mozilla.org/en-US/firefox/addon/decentraleyes/)
+ - [multi-account
+ containers](https://addons.mozilla.org/en-US/firefox/addon/multi-account-containers/)
+ - [adnauseam](https://adnauseam.io/)
+
+--
+
+### Navigazione in incognito
+
+Non c'entra niente con l'anonimato, vi protegge dagli attacchi del vostro
+coinquilino che vi guarda la cronologia mentre andate in bagno.
+
+E' una modalità di navigazione che, contrariamente a quanto avviene
+normalmente:
+- non salva la cronologia
+- i file scaricati non vengono mostrati nei download
+- niente cache
+- non salva i cookie (non sono loggato in sessioni successive)
+
+notes:
+https://blog.mozilla.org/security/2010/03/31/plugging-the-css-history-leak/
+https://www.ghacks.net/2018/11/04/browser-history-sniffing-is-still-a-thing/
+
+l'attacco permette attivamente a un sito web di provare diverse url e
+vedere se sono gia state visitate dal browser di chi lo visita, nell'ordine
+di migliaia di url al secondo.
diff --git a/slides/password.md b/slides/password.md
new file mode 100644
index 0000000..d69f094
--- /dev/null
+++ b/slides/password.md
@@ -0,0 +1,132 @@
+
+
+# Password
+
+--
+
+Le password sono la prima barriera di accesso a dati che vogliamo tenere
+per noi.
+
+
+Le usiamo leggere la posta, per ritirare al bancomat (pin), per entrare nel
+computer e nei mille servizi digitali a cui accediamo.
+
+--
+
+### Ma... Non siamo bravi a scegliere delle buone password
+
+ - E' la password di gmail? ➜
+ ci mettiamo `gmail` in mezzo
+ - Usiamo concetti ricordabili ➜
+ date di nascita, nomi di amic\*/compagn\*
+ - Riusiamo la stessa password in
+ molti posti.
+
+ In pratica scegliamo password facilmente indovinabili.
+
+--
+
+Spinti a migliorare le nostre password
+
+![img/passhint.png](./img/password-requisiti.png)
+
+--
+
+scegliamo le soluzioni piu' semplici e prevedibili
+- e' la password di facebook ➜
+ **facebookpassword**
+- inserisci almeno una maiuscola ➜
+ **Facebookpassword**
+- inserisci almeno un numero ➜
+ **Facebookpassword1**
+- inserisci almeno un simbolo ➜
+ **Facebookpassword1!**
+
+notes: Sono tutti schemi facilmente immaginabili.
+
+--
+
+### Ma soprattutto..
+
+Usiamo la stessa password per più siti/servizi
+
+![scimmia](./img/scimmia.jpg) notes:
+chiedere perche' e' un problema....
+
+--
+
+### Orrore!
+
+ i dipendenti di ogni servizio hanno
+accesso ad ogni altro servizio!
+
+ quando (non se) uno dei servizi viene
+bucato, gente a caso ha accesso ad ogni vostro servizio (succede un giorno
+si e l'altro pure).
+
+ E' talmente diffusa la cosa che mozilla
+ha un servizio per fare un check ➜
+[monitor.firefox.com](https://monitor.firefox.com)
+
+--
+
+### Leak
+
+Negli ultimi anni sono stati bucati tanti servizi e milioni di password
+sono diventate pubbliche (leak) permettendo di farci ricerca sopra e si, le
+password piu' usate sono `123456` e `password`, gli schemi usati sono
+drammaticamente ricorrenti e la maggior parte delle persone riusa le
+password in piu' servizi.
+
+Una lista di servizi la cui compromissione è pubblica è
+[qui](https://haveibeenpwned.com/PwnedWebsites). Un posto dove poter
+studiare le statistiche
+
+--
+
+### Password Cracking
+
+Esistono programmi e servizi che tentano ripetutamente password basandosi
+sulla nostra prevedibilità e si basano comunemente su dizionari a cui
+vengono applicate delle regole (permutazioni, aggiunte di
+prefissi/suffissi, cambio di caratteri comuni, maiuscole/minuscole).
+
+Considerate che i file dizionario in attacchi mirati vengono creati ad-hoc
+prendendo tutto il material digitale del target. notes: Mostrare un
+piccolo esempio di `hashcat` (da preparare)
+
+--
+
+### E quindi?
+
+Se non siamo capaci a fare qualcosa, cerchiamo qualcuno in grado di farlo.
+
+--
+
+### Password manager
+
+Usiamo i password manager.
+
+Sono dei programmi che generano e si ricordano delle password sicure, in
+cambio di una sola master password (passphrase).
+
+notes: spiegare master password, che e' possibile fare piu' liste di
+password, suggerire buone pratiche.
+
+--
+
+### E la master password? Per le poche passphrase che non possiamo salvare
+usiamo i seguenti accorgimenti:
+
+- mai riusare una passphrase (dai te ne devi ricordare massimo 4, stacce)
+- mai condividere una passphrase (no no no e no)
+- mai scrivere una passphrase (a parte se sai quello che stai facendo)
+- usa 4 parole a caso (veramente a caso) e costruiscici una storia sopra
+ per ricordarle.
+
+notes: il `4` del primo punto e' un numero a caso. esempio live di scelta
+passphrase.
diff --git a/slides/smartphone.md b/slides/smartphone.md
new file mode 100644
index 0000000..3447361
--- /dev/null
+++ b/slides/smartphone.md
@@ -0,0 +1,138 @@
+
+
+## Smartphone
+
+--
+
+## Smartphone
+
+- Sono ovunque, sono Lo strumento usato per comunicare
+- Telefonate, internet, chat, foto, video, etc..
+- Non sono stati progettati per essere sicuri
+
+--
+
+## Meno controllo
+
+Rispetto ad un computer è più complicato:
+- sostituire il sistema operativo (pensate a quanto vi abbiamo rotto con
+ linux)
+- investigare presenza di malware/virus
+- disinstallare programmi di default (telefoni brandizzati)
+- prevenire il monitoraggio
+
+--
+
+## Obsolescenza..
+
+Inoltre il produttore del telefono dichiarando lo stesso obsoleto smette di
+fornire aggiornamenti software (lasciando aperte vulnerabilità di pubblico
+dominio)
+
+--
+
+## Geolocalizzazione - Cell
+
+Un telefono acceso si collega ad una cella della rete telefonica, quale
+cella e quale telefono vengono segnati dall'operatore, che tiene per molto
+tempo questa informazione.
+
+--
+
+## Geolocalizzazione - Cell
+
+E' possibile triangolare un dispositivo stimando la potenza del segnale
+ricevuto da celle vicine, si attiva chiamando il 118 e tipo se siete sotto
+sorveglianza.
+
+Non c'è modo di evitare questo attacco se non lasciando il telefono a casa
+:)
+
+--
+
+## Geolocalizzazione - IMSI
+
+IMSI Catcher, un simulatore di antenne telefoniche sicuramente
+[usato](https://www.ilfattoquotidiano.it/2015/06/13/con-limsi-catcher-cellulari-a-rischio-attenzione-il-cacciatore-ti-ascolta/1770363/)
+[in
+Italia](https://duckduckgo.com/?q=capitolatotecnicoradiomobili+site%3Apoliziadistato.it).
+
+Può rispondere a domande del tipo: "dammi tutti i numeri di telefono
+presenti in questa zona, quel giorno" senza farne richiesta al magistrato.
+
+E'
+[diffuso](https://github.com/CellularPrivacy/Android-IMSI-Catcher-Detector/wiki/Unmasked-Spies),
+se volete divertirvi potete costruire un [imsi catcher
+detector](https://seaglass.cs.washington.edu/)
+
+notes: disabilitare 2g/3g e il roaming
+
+--
+
+## Geolocalizzazione
+
+- WIFI Il telefono va' in giro [urlando ai quattro venti un suo
+ identificativo
+ univoco](http://www.gizmodo.co.uk/2017/02/heres-what-tfl-learned-from-tracking-your-phone-on-the-tube/).
+
+notes: Disabilita il bluetooth e il wifi quando esci di casa.
+
+--
+
+## Geolocalizzazione
+
+- GPS Il vostro telefono non parla con i satelliti, avviene il contrario.
+ Ma quando conosce la sua posizione puo' comunicarla su altri canali.
+
+La geolocalizzazione usa anche la [lista delle reti
+wireless]((https://location.services.mozilla.com/map) che trova intorno a
+te. notes:
+- Il GPS riceve solamente (accuracy ~5 metri a scopo civile)
+- Si geolocalizza anche senza GPS ma col
+ [WIFI](https://location.services.mozilla.com/map#2/15.0/10.0) (~78 metri)
+ Faccio una lista delle reti wifi nel posto dove mi trovo e mi segno la
+ potenza del segnale di ognuna e/o il tempo di risposta.
+- O con il cellular positioning (~600 metri)
+
+--
+
+## Malware Vedi
+
+[qui](https://www.autistici.org/underscore/di-trojan-di-stato.html) e
+[qui](https://www.autistici.org/underscore/di-trojan-di-stato-details.html)
+che ne abbiamo parlato un sacco.
+
+Tenete aggiornati i vostri dispositivi, installate solo le app che vi
+servono, disinstallate le app di default, usate [software
+libero](https://lineageos.org/).
+
+--
+
+## Buone pratiche
+
+- Ma ascolta anche quando è spento?
+- Devo togliere la batteria?
+
+Per discorsi sensibili, lasciate i telefoni in un'altra stanza, se 20
+persone contemporaneamente spengono il telefono in uno stesso luogo
+l'operatore lo sa.
+
+--
+
+## Attacchi fisici
+
+- Inserite un pin, una passphrase o una sequenza per sbloccare lo schermo
+- No impronte digitali (stanno sul
+ [telefono](https://www.ccc.de/en/updates/2014/ursel) e sui
+ [server](https://apple.slashdot.org/story/19/03/24/0015213/how-the-fbi-easily-retrieved-michael-cohens-data-from-both-apple-and-google))
+- [Cifrate il
+ telefono](https://trovalost.it/come-cifrare-un-telefono-android/)
+
+notes: che sia il vostro coinquilino dell'altra stanza, un vostro ex, il
+vostro capo o la digos, se qualcuno prende il vostro telefono in mano e non
+c'e' protezione alcuna, non e' una bella cosa, Anche se non vi sequestrano
+il telefono, in poco tempo e' possibile installare malware o addirittura in
+alcuni casi reinstallare l'intero sistema operativo avendone accesso
+fisico. Altra cosa, cifrate il telefono, nelle impostazioni -> sicurezza
+potete mettere la stessa sequenza/pin/password per accendere il telefono e
+per abilitarlo
diff --git a/slides/strumenti-radicali.md b/slides/strumenti-radicali.md
new file mode 100644
index 0000000..fde97a2
--- /dev/null
+++ b/slides/strumenti-radicali.md
@@ -0,0 +1,53 @@
+
+
+## **Server Radicali**
+
+--
+
+## Fiducia
+
+È difficile fare tutto da sol*
+
+- mi faccio il mio server mail
+- il mio nodo jabber
+- la mia istanza mastodon
+- il mio server di backup
+
+tocca fidarsi di qualcuno...
+
+--
+
+## Autistici.org
+
+> Crediamo che questo non sia affatto il migliore dei mondi possibili. La
+> nostra risposta è offrire ad attivisti, gruppi e collettivi piattaforme
+> per una comunicazione più libera e strumenti digitali per l’autodifesa
+> della privacy, come per esempio email, blog, mailing list, instant
+> messaging e altro.
+
+--
+
+## Riseup.net
+
+> Riseup provides online communication tools for people and groups working
+> on liberatory social change. We are a project to create democratic
+> alternatives and practice self-determination by controlling our own
+> secure means of communications.
+
+--
+
+## Molti altri
+
+Cerca altri [server radicali](https://riseup.net/en/security/resources/radical-servers)
+
+--
+
+## Cisti.org
+
+> Uno spazio digitale liberato.
+>
+> Un server scapestrato e autogestito.
+>
+> Anticapitalista, antifascista, antirazzista, antisessista.
+>
+
diff --git a/test/examples/assets/image1.png b/test/examples/assets/image1.png
new file mode 100644
index 0000000..8747594
Binary files /dev/null and b/test/examples/assets/image1.png differ
diff --git a/test/examples/assets/image2.png b/test/examples/assets/image2.png
new file mode 100644
index 0000000..6c403a0
Binary files /dev/null and b/test/examples/assets/image2.png differ
diff --git a/test/examples/barebones.html b/test/examples/barebones.html
new file mode 100644
index 0000000..2bee3cb
--- /dev/null
+++ b/test/examples/barebones.html
@@ -0,0 +1,41 @@
+
+
+
+
+
+
+ reveal.js - Barebones
+
+
+
+
+
+
+
+
+
+
+
+
Barebones Presentation
+
This example contains the bare minimum includes and markup required to run a reveal.js presentation.
+
+
+
+
No Theme
+
There's no theme included, so it will fall back on browser defaults.
+
+
+
+
+
+
+
+
+
+
+
diff --git a/test/test-markdown-element-attributes.js b/test/test-markdown-element-attributes.js
new file mode 100644
index 0000000..10a2503
--- /dev/null
+++ b/test/test-markdown-element-attributes.js
@@ -0,0 +1,46 @@
+
+
+Reveal.addEventListener( 'ready', function() {
+
+ QUnit.module( 'Markdown' );
+
+ test( 'Vertical separator', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides>section>section' ).length, 4, 'found four slides' );
+ });
+
+
+ test( 'Attributes on element header in vertical slides', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section>section h2.fragment.fade-out' ).length, 1, 'found one vertical slide with class fragment.fade-out on header' );
+ strictEqual( document.querySelectorAll( '.reveal .slides section>section h2.fragment.shrink' ).length, 1, 'found one vertical slide with class fragment.shrink on header' );
+ });
+
+ test( 'Attributes on element paragraphs in vertical slides', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section>section p.fragment.grow' ).length, 2, 'found a vertical slide with two paragraphs with class fragment.grow' );
+ });
+
+ test( 'Attributes on element list items in vertical slides', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section>section li.fragment.grow' ).length, 3, 'found a vertical slide with three list items with class fragment.grow' );
+ });
+
+ test( 'Attributes on element paragraphs in horizontal slides', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section p.fragment.highlight-red' ).length, 4, 'found a horizontal slide with four paragraphs with class fragment.grow' );
+ });
+ test( 'Attributes on element list items in horizontal slides', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section li.fragment.highlight-green' ).length, 5, 'found a horizontal slide with five list items with class fragment.roll-in' );
+ });
+ test( 'Attributes on element list items in horizontal slides', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section img.reveal.stretch' ).length, 1, 'found a horizontal slide with stretched image, class img.reveal.stretch' );
+ });
+
+ test( 'Attributes on elements in vertical slides with default element attribute separator', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section h2.fragment.highlight-red' ).length, 2, 'found two h2 titles with fragment highlight-red in vertical slides with default element attribute separator' );
+ });
+
+ test( 'Attributes on elements in single slides with default element attribute separator', function() {
+ strictEqual( document.querySelectorAll( '.reveal .slides section p.fragment.highlight-blue' ).length, 3, 'found three elements with fragment highlight-blue in single slide with default element attribute separator' );
+ });
+
+} );
+
+Reveal.initialize();
+
diff --git a/test/test-markdown-external.html b/test/test-markdown-external.html
new file mode 100644
index 0000000..859d0a1
--- /dev/null
+++ b/test/test-markdown-external.html
@@ -0,0 +1,36 @@
+
+
+
+
+
+
+ reveal.js - Test Markdown
+
+
+
+
+
+
+
+
+
+
+