Untracked Config File

This commit is contained in:
Luke Vella 2015-01-27 17:56:21 +01:00
parent c74b397836
commit aaf75b4402
17 changed files with 234 additions and 147 deletions

View file

@ -1,138 +1,170 @@
var express = require('express'); var express = require('express');
var Event = require('./event.model'); var Event = require('./event.model');
var debug = require('debug')('eventapi'); var debug = require('debug')('rallly');
var communicator = require('../../communicator'); var communicator = require('../../communicator');
var getRandomString = function(){ var getRandomString = function(){
return require('crypto').randomBytes(16).toString('hex'); return require('crypto').randomBytes(16).toString('hex');
} }
exports.model = Event;
exports.verifyEmail = function(req, res, next){ exports.verifyEmail = function(req, res, next){
var id = req.params.id, var id = req.params.id,
code = req.params.code; code = req.params.code;
Event.update({
'_id' : id, Event
'__private.verificationCode' : code .update({
}, { '_id' : id,
'creator.isVerified' : true , '__private.verificationCode' : code
'__private.verificationCode' : getRandomString() }, {
}, function(err, num){ 'creator.isVerified' : true ,
if (err) return handleError(res, err); '__private.verificationCode' : getRandomString()
if (num == 0) return res.status(498).end(); })
next(); .exec(function(err, num){
}); if (err) return handleError(res, err);
if (num == 0) return res.status(498).end();
next();
});
} }
exports.create = function(req, res, next){ exports.create = function(req, res, next){
var event = req.body; var event = req.body;
event.__private = { event.__private = {
'verificationCode' : getRandomString(), 'verificationCode' : getRandomString(),
'unsubscribeCode' : getRandomString(), 'unsubscribeCode' : getRandomString(),
'deleteCode' : getRandomString() 'deleteCode' : getRandomString()
} }
Event.create(req.body, function(err, event){
if (err) return handleError(res, err); return Event
if (!event) return res.status(404); .create(req.body, function(err, event){
communicator.emit('event:create', event); if (err) return handleError(res, err);
req.event = event; if (!event) return res.status(404);
next(); communicator.emit('event:create', event);
}); req.event = event;
next();
});
} }
exports.show = function(req, res, next){ exports.show = function(req, res, next){
Event.findById(req.params.id, function(err, event){ Event
if (err) return handleError(res, err); .findById(req.params.id)
if (!event) return res.status(404).end(); .exec(function(err, event){
req.event = event; if (err) return handleError(res, err);
next(); if (!event) return res.status(404).end();
}); req.event = event;
next();
});
} }
exports.update = function(req, res){ exports.update = function(req, res){
var updatedEvent = req.body; var updatedEvent = req.body;
updatedEvent.updated = Date.now(); updatedEvent.updated = Date.now();
Event.findById(req.params.id, function(err, event){
if (err) return handleError(res, err); Event
if (!event) return res.status(404).end(); .findById(req.params.id)
// If the creator's email has changed OR the notifications setting has changed - start a new email confirmation transaction .exec(function(err, event){
if (event.creator.email != updatedEvent.creator.email || if (err) return handleError(res, err);
(!event.creator.allowNotifications && updatedEvent.creator.allowNotifications)) { if (!event) return res.status(404).end();
updatedEvent.creator.isVerified = false; // If the creator's email has changed OR the notifications setting has changed - start a new email confirmation transaction
updatedEvent.creator.allowNotifications = true; if (event.creator.email != updatedEvent.creator.email ||
updatedEvent.__private = event.__private; (!event.creator.allowNotifications && updatedEvent.creator.allowNotifications)) {
communicator.emit('event:update:creator.email', updatedEvent, event); updatedEvent.creator.isVerified = false;
} updatedEvent.creator.allowNotifications = true;
Event.update({ '_id' : req.params.id }, updatedEvent, function(){ updatedEvent.__private = event.__private;
communicator.emit('event:update', updatedEvent, event); communicator.emit('event:update:creator.email', updatedEvent, event);
return res.status(204).end(); }
Event
.update({ '_id' : req.params.id }, updatedEvent)
.exec(function(){
communicator.emit('event:update', updatedEvent, event);
return res.status(204).end();
});
}); });
});
} }
exports.delete = function(req, res, next){ exports.delete = function(req, res, next){
var eventId = req.params.id, var eventId = req.params.id,
code = req.params.code; code = req.params.code;
if (code){ if (code){
Event.update({
'_id' : eventId, Event
'__private.deleteCode' : code .update({
}, { '_id' : eventId,
'isDeleted' : true , '__private.deleteCode' : code
'__private.deleteCode' : getRandomString() }, {
}, function(err, num){ 'isDeleted' : true ,
if (err) return handleError(res, err); '__private.deleteCode' : getRandomString()
if (num == 0) return res.status(498).end(); })
next(); .exec(function(err, num){
}); if (err) return handleError(res, err);
if (num == 0) return res.status(498).end();
next();
});
} else { } else {
Event.findById(eventId, function(err, event){
if (err) return handleError(res, err); Event
if (!event) return res.status(404).end(); .findById(eventId)
communicator.emit('event:delete', event); .exec(function(err, event){
next(); if (err) return handleError(res, err);
}); if (!event) return res.status(404).end();
communicator.emit('event:delete', event);
next();
});
} }
} }
exports.createComment = function(req, res, next){ exports.createComment = function(req, res, next){
var eventId = req.params.id, var eventId = req.params.id,
comment = req.body; comment = req.body;
Event.findById(eventId, function(err, event){
if (err) return handleError(res, err); Event
event.comments.push(comment); .findById(eventId)
event.save(function(err, event){ .exec(function(err, event){
if (err) return next(err); if (err) return handleError(res, err);
req.event = event; event.comments.push(comment);
next(); event.save(function(err, event){
if (err) return next(err);
req.event = event;
next();
});
}); });
});
} }
exports.deleteComment = function(req, res, next){ exports.deleteComment = function(req, res, next){
var eventId = req.params.id, var eventId = req.params.id,
commentId = req.params.cid; commentId = req.params.cid;
Event.findById(eventId, function(err, event){
if (err) return handleError(res, err); Event
event.comments.pull({ '_id' : commentId }); .findById(eventId)
event.save(function(err, event){ .exec(function(err, event){
req.event = event; if (err) return handleError(res, err);
next(); event.comments.pull({ '_id' : commentId });
}) event.save(function(err, event){
}); req.event = event;
next();
})
});
} }
exports.createParticipant = function(req, res, next){ exports.createParticipant = function(req, res, next){
var eventId = req.params.id, var eventId = req.params.id,
participant = req.body; participant = req.body;
Event.findById(eventId, function(err, event){
if (err) return handleError(res, err); Event
event.updated = Date.now(); .findById(eventId)
event.participants.push(participant); .exec(function(err, event){
event.save(function(err, event){ if (err) return handleError(res, err);
if (err) return next(err); event.updated = Date.now();
req.event = event; event.participants.push(participant);
next(); event.save(function(err, event){
if (err) return next(err);
req.event = event;
next();
}); });
}); });
} }
@ -140,35 +172,42 @@ exports.createParticipant = function(req, res, next){
exports.updateParticipant = function(req, res, next){ exports.updateParticipant = function(req, res, next){
var eventId = req.params.id, var eventId = req.params.id,
participantId = req.params.pid; participantId = req.params.pid;
Event.update({
'_id' : eventId, Event
'participants._id': participantId .update({
}, { '_id' : eventId,
'$set': { 'participants._id': participantId
'updated' : Date.now(), }, {
'participants.$' : req.body '$set': {
} 'updated' : Date.now(),
}, function(err, num){ 'participants.$' : req.body
if (err) return handleError(res, err); }
res.status(204).end(); })
}); .exec(function(err, num){
if (err) return handleError(res, err);
res.status(204).end();
});
} }
exports.deleteParticipant = function(req, res, next){ exports.deleteParticipant = function(req, res, next){
var eventId = req.params.id, var eventId = req.params.id,
participantId = req.params.pid; participantId = req.params.pid;
Event.findById(eventId, function(err, event){
if (err) return handleError(res, err); Event
event.updated = Date.now(); .findById(eventId)
event.participants.pull({ '_id' : participantId }); .exec(function(err, event){
event.save(function(err, event){ if (err) return handleError(res, err);
req.event = event; event.updated = Date.now();
next(); event.participants.pull({ '_id' : participantId });
}) event.save(function(err, event){
}); req.event = event;
next();
})
});
} }
function handleError(res, err) { function handleError(res, err) {
debug("ERROR: " + err);
return res.status(500).send(err); return res.status(500).send(err);
} }

View file

@ -1,6 +1,6 @@
var mongoose = require('mongoose'); var mongoose = require('mongoose');
var Schema = mongoose.Schema; var Schema = mongoose.Schema;
var debug = require('debug')('event.model'); var debug = require('debug')('rallly');
var ShortId = require('mongoose-shortid'); var ShortId = require('mongoose-shortid');
var EventSchema = new Schema({ var EventSchema = new Schema({
@ -72,7 +72,6 @@ model.schema
.path('creator.email') .path('creator.email')
.required('You need to type in your email') .required('You need to type in your email')
.validate(function(email) { .validate(function(email) {
debug("email: " + email);
var emailRegex = /^([\w-\.]+@([\w-]+\.)+[\w-]{2,4})?$/; var emailRegex = /^([\w-\.]+@([\w-]+\.)+[\w-]{2,4})?$/;
return emailRegex.test(email); return emailRegex.test(email);
}, 'You need to type in a valid email') }, 'You need to type in a valid email')
@ -91,4 +90,5 @@ model.schema
} }
return true; return true;
}, 'Participants must have a name') }, 'Participants must have a name')
module.exports = model module.exports = model

View file

@ -1,24 +1,10 @@
var express = require('express'); var express = require('express');
var router = express.Router(); var router = express.Router();
var controller = require('./event.controller'); var controller = require('./event.controller');
var debug = require('debug')('api/event/index'); var debug = require('debug')('rallly');
/* GET home page. */ /* GET home page. */
router.post('/', controller.create); var after = function(req, res) {
router.get('/:id', controller.show);
router.put('/:id', controller.update);
router.delete('/:id', controller.delete);
router.delete('/:id/code/:code', controller.delete);
router.get('/:id/code/:code', controller.verifyEmail);
router.post('/:id/comment', controller.createComment);
router.delete('/:id/comment/:cid', controller.deleteComment);
router.post('/:id/participant', controller.createParticipant);
router.delete('/:id/participant/:pid', controller.deleteParticipant);
router.put('/:id/participant/:pid', controller.updateParticipant);
router.all('/*', function(req, res){
if (req.event){ if (req.event){
var event = req.event.toObject(); var event = req.event.toObject();
delete event['__private']; delete event['__private'];
@ -26,6 +12,23 @@ router.all('/*', function(req, res){
} else { } else {
res.status(204).end(); res.status(204).end();
} }
}); }
router.post('/', controller.create, after);
router.get('/:id', controller.show, after);
router.put('/:id', controller.update, after);
router.delete('/:id', controller.delete, after);
router.delete('/:id/code/:code', controller.delete, after);
router.get('/:id/code/:code', controller.verifyEmail, after);
router.post('/:id/comment', controller.createComment, after);
router.delete('/:id/comment/:cid', controller.deleteComment, after);
router.post('/:id/participant', controller.createParticipant, after);
router.delete('/:id/participant/:pid', controller.deleteParticipant, after);
router.put('/:id/participant/:pid', controller.updateParticipant, after);
module.exports = router; module.exports = router;

9
app.js
View file

@ -3,7 +3,7 @@ var path = require('path');
var logger = require('morgan'); var logger = require('morgan');
var cookieParser = require('cookie-parser'); var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser'); var bodyParser = require('body-parser');
var debug = require('debug')('app'); var debug = require('debug')('rallly');
var mongoose = require('mongoose'); var mongoose = require('mongoose');
var app = module.exports = express(); var app = module.exports = express();
@ -23,8 +23,11 @@ app.use(express.static(path.join(__dirname, 'public')));
require('./config/routes')(app); require('./config/routes')(app);
var dbname = 'myapp'; var dbname = app.get('dbname');
mongoose.connect('mongodb://localhost/' + dbname); mongoose.connect('mongodb://localhost/' + dbname, {
user : app.get('dbuser'),
pass : app.get('dbpwd'),
});
var db = mongoose.connection; var db = mongoose.connection;
db.on('error', debug.bind(debug, 'connection error')); db.on('error', debug.bind(debug, 'connection error'));
db.once('open', function(){ db.once('open', function(){

View file

@ -1,5 +1,5 @@
#!/usr/bin/env node #!/usr/bin/env node
var debug = require('debug')('www'); var debug = require('debug')('rallly');
var app = require('../app'); var app = require('../app');
var server = app.listen(app.get('port'), function() { var server = app.listen(app.get('port'), function() {

View file

@ -1,8 +0,0 @@
module.exports = function(app){
app.set('port', 3000);
app.set('siteUrl', 'http://localhost');
app.set('absoluteUrl', function(path){
return app.get('siteUrl') + ':' + app.get('port') + '/' + path;
});
app.set('mandrillAPIKey','suEKoTkjRDeYie0Wd16Knw');
};

View file

@ -1,8 +1,11 @@
module.exports = function(app){ module.exports = function(app){
app.set('port', 3000); app.set('port', 3000);
app.set('siteUrl', 'http://localhost'); app.set('siteUrl', '');
app.set('absoluteUrl', function(path){ app.set('absoluteUrl', function(path){
return app.get('siteUrl') + ':' + app.get('port') + '/' + path; return app.get('siteUrl') + ':' + app.get('port') + '/' + path;
}); });
app.set('mandrillAPIKey',''); // Put your Mandrill API Key Here. app.set('dbname', '');
app.set('dbuser', '');
app.set('dbpwd', '');
app.set('mandrillAPIKey','');
}; };

View file

@ -4,7 +4,7 @@
var app = require('../app'); var app = require('../app');
var communicator = require('../communicator'); var communicator = require('../communicator');
var debug = require('debug')('notification'); var debug = require('debug')('rallly');
var mandrill = require('mandrill-api'); var mandrill = require('mandrill-api');
var mandrill_client = new mandrill.Mandrill(app.get('mandrillAPIKey')); var mandrill_client = new mandrill.Mandrill(app.get('mandrillAPIKey'));

View file

@ -3,7 +3,7 @@
"version": "1.0.0", "version": "1.0.0",
"private": true, "private": true,
"scripts": { "scripts": {
"start": "DEBUG=eventapi nodemon ./bin/www" "start": "DEBUG=rallly nodemon ./bin/www"
}, },
"dependencies": { "dependencies": {
"amdefine": "^0.1.0", "amdefine": "^0.1.0",
@ -21,6 +21,7 @@
"serve-favicon": "^2.1.7" "serve-favicon": "^2.1.7"
}, },
"devDependencies": { "devDependencies": {
"chai": "^1.10.0",
"gulp": "^3.8.10", "gulp": "^3.8.10",
"gulp-angular-templatecache": "^1.5.0", "gulp-angular-templatecache": "^1.5.0",
"gulp-concat": "^2.4.2", "gulp-concat": "^2.4.2",
@ -28,6 +29,8 @@
"gulp-notify": "^2.0.1", "gulp-notify": "^2.0.1",
"gulp-sass": "^1.2.4", "gulp-sass": "^1.2.4",
"gulp-sourcemaps": "^1.2.8", "gulp-sourcemaps": "^1.2.8",
"gulp-uglify": "^1.0.1" "gulp-uglify": "^1.0.1",
"mocha": "^2.1.0",
"node-mocks-http": "^1.2.4"
} }
} }

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -1,13 +1,27 @@
angular.module('rallly') angular.module('rallly')
.controller('EventCtrl', function($scope, $http, $state, Title, Event, ConfirmModal){ .controller('EventCtrl', function($scope, $http, $state, Title, Event, ConfirmModal){
var id = $state.params.id; var id = $state.params.id;
// Get Event
$scope.event = Event.get({id:id}, function(data){ $scope.event = Event.get({id:id}, function(data){
// Set the page title to the event title
Title.set($scope.event.title); Title.set($scope.event.title);
// Generate event url - i.e. http://rallly.co/jF9F_Fd
$scope.eventUrl = $state.href('event', { $scope.eventUrl = $state.href('event', {
id: $scope.event._id id: $scope.event._id
}, { }, {
absolute : true absolute : true
}); });
var examplesNames = ['John Example', 'Jane Specimen','Mark Instance', 'Mary Case'];
$scope.event.examples = [];
for (var i = 0; i < examplesNames.length; i++){
var example = { name : examplesNames[i] };
example.dates = [];
for (var j = 0; j < $scope.event.dates.length; j++){
var answer = Math.random()<.5;
example.dates[j] = answer;
}
$scope.event.examples.push(example);
}
}, function(e){ }, function(e){
$state.go('notfound'); $state.go('notfound');
}); });

View file

@ -7,7 +7,7 @@ $templateCache.put("templates/newevent.html","<div ng-hide=\"eventUrl\">\n <d
$templateCache.put("templates/notfound.html","<h1>Error 404</h1>\n<h2>Not Found</h2>\n"); $templateCache.put("templates/notfound.html","<h1>Error 404</h1>\n<h2>Not Found</h2>\n");
$templateCache.put("templates/notification.html","<div class=\"notification {{notification.type}}\" ng-click=\"notification.close()\">\n <div class=\"title\">\n {{notification.title}}\n </div>\n <div class=\"message\">\n {{notification.message}}\n </div>\n</div>\n"); $templateCache.put("templates/notification.html","<div class=\"notification {{notification.type}}\" ng-click=\"notification.close()\">\n <div class=\"title\">\n {{notification.title}}\n </div>\n <div class=\"message\">\n {{notification.message}}\n </div>\n</div>\n");
$templateCache.put("templates/directives/discussion.html","<ul class=\"comment-thread\" ng-show=\"event.comments.length\">\n <li ng-repeat=\"comment in event.comments\" class=\"comment\">\n <div class=\"avatar-section\">\n <img src=\"/images/avatar.png\" />\n </div>\n <div class=\"comment-section\">\n <a href=\"#\" class=\"comment-delete\" ng-click=\"deleteComment(comment)\">&times;</a>\n <div class=\"meta\">\n <span class=\"name\">{{comment.author.name}}</span>\n <span class=\"time\">{{comment.created | elapsed}}</span>\n </div>\n <div class=\"content\">{{comment.content}}</div>\n </div>\n </li>\n</ul>\n<form novalidate ng-submit=\"postComment()\" name=\"commentForm\" class=\"comment-form\">\n <div class=\"avatar-section\">\n <img src=\"/images/avatar.png\" />\n </div>\n <div class=\"input-section form-group\">\n <div class=\"content-section\">\n <textarea class=\"form-control\" required ng-model=\"comment.content\" placeholder=\"Write a comment...\"></textarea>\n </div>\n <div class=\"name-section\">\n <div class=\"name-container\">\n <input type=\"text\" class=\"form-control\" required placeholder=\"Your Name\" ng-model=\"comment.author.name\" />\n <button type=\"submit\" class=\"btn\">Post Comment</button>\n <span class=\"form-error\" ng-show=\"commentForm.$submitted && commentForm.$error\">\n <img src=\"/images/error.png\" width=\"14\" /> Make sure you fill in all the fields.\n </span>\n </div>\n </div>\n </div>\n</form>\n"); $templateCache.put("templates/directives/discussion.html","<ul class=\"comment-thread\" ng-show=\"event.comments.length\">\n <li ng-repeat=\"comment in event.comments\" class=\"comment\">\n <div class=\"avatar-section\">\n <img src=\"/images/avatar.png\" />\n </div>\n <div class=\"comment-section\">\n <a href=\"#\" class=\"comment-delete\" ng-click=\"deleteComment(comment)\">&times;</a>\n <div class=\"meta\">\n <span class=\"name\">{{comment.author.name}}</span>\n <span class=\"time\">{{comment.created | elapsed}}</span>\n </div>\n <div class=\"content\">{{comment.content}}</div>\n </div>\n </li>\n</ul>\n<form novalidate ng-submit=\"postComment()\" name=\"commentForm\" class=\"comment-form\">\n <div class=\"avatar-section\">\n <img src=\"/images/avatar.png\" />\n </div>\n <div class=\"input-section form-group\">\n <div class=\"content-section\">\n <textarea class=\"form-control\" required ng-model=\"comment.content\" placeholder=\"Write a comment...\"></textarea>\n </div>\n <div class=\"name-section\">\n <div class=\"name-container\">\n <input type=\"text\" class=\"form-control\" required placeholder=\"Your Name\" ng-model=\"comment.author.name\" />\n <button type=\"submit\" class=\"btn\">Post Comment</button>\n <span class=\"form-error\" ng-show=\"commentForm.$submitted && commentForm.$error\">\n <img src=\"/images/error.png\" width=\"14\" /> Make sure you fill in all the fields.\n </span>\n </div>\n </div>\n </div>\n</form>\n");
$templateCache.put("templates/directives/poll.html","<div class=\"poll-header\">\n <div class=\"header participants-header\">\n {{event.participants.length}} participants\n </div>\n <div class=\"header date-header\" ng-repeat=\"date in event.dates\">\n <div class=\"daticon\">\n <div class=\"dow\">\n {{date | date: \'EEE\'}}\n </div>\n <div class=\"day\">\n {{date | date: \'d\'}}\n </div>\n <div class=\"month\">\n {{date | date : \'MMM\'}}\n </div>\n <span class=\"count\" ng-show=\"selectedDate($index)\" ng-class={top:isTopDate($index)}>{{selectedDate($index)}}</span>\n </div>\n </div>\n <div class=\"header actions-header\">\n\n </div>\n</div>\n<div class=\"poll-body\">\n <div class=\"poll-entry\" ng-repeat=\"participant in event.participants\">\n <form novalidate ng-submit=\"update(participant); editMode = false\">\n <div class=\"cell name-cell\">\n <span class=\"avatar style-{{$index + 1}}\">\n <img src=\"/images/user.png\" width=\"11\" />\n </span>\n <input required autocomplete=\"off\" type=\"text\" class=\"form-control\" ng-model=\"participant.name\" ng-show=\"editMode\" value=\"participant.name\"/>\n <span ng-hide=\"editMode\" class=\"name\" ng-click=\"editMode = true && !event.isClosed; edit(participant)\">{{participant.name}}</span>\n </div>\n <div class=\"cell vote-cell\" ng-repeat=\"date in event.dates\">\n <img src=\"/images/tick@2x.png\" width=\"16\" ng-hide=\"editMode\" ng-if=\"participant.dates[$index]\" />\n <img src=\"/images/nope@2x.png\" width=\"8\" ng-hide=\"editMode\" ng-if=\"!participant.dates[$index]\" />\n <input ng-model=\"participant.dates[$index]\" ng-show=\"editMode\" ng-false-value=\"false\" type=\"checkbox\" />\n <div class=\"overlay\" ng-show=\"editMode\" ng-click=\"participant.dates[$index] = !participant.dates[$index]\"></div>\n </div>\n <div class=\"cell action-cell\" ng-hide=\"event.isClosed\">\n <button type=\"button\" ng-hide=\"editMode\" ng-click=\"editMode = true; edit(participant)\" class=\"btn hover\">Edit</button>\n <button type=\"button\" ng-hide=\"editMode\" ng-click=\"delete(participant)\" class=\"btn danger hover\">Delete</button>\n <button type=\"submit\" ng-show=\"editMode\" class=\"btn\">Save</button>\n <button type=\"button\" ng-show=\"editMode\" ng-click=\"editMode = false; cancel($index)\" class=\"btn\">Cancel</button>\n </div>\n </form>\n </div>\n <div ng-hide=\"event.isClosed\" class=\"poll-entry highlight\">\n <form novalidate name=\"formnew\" ng-submit=\"save()\">\n <div class=\"cell name-cell\">\n <span class=\"avatar style-{{participant.style}}\">\n <img src=\"/images/user.png\" width=\"11\" />\n </span>\n <input autocomplete=\"off\" name=\"username\" type=\"text\" class=\"form-control\" placeholder=\"Your name...\" ng-model=\"participant.name\" required value=\"participant.name\"/>\n </div>\n <div class=\"cell vote-cell\" ng-repeat=\"date in event.dates\">\n <input ng-model=\"participant.dates[$index]\" ng-false-value=\"false\" type=\"checkbox\" />\n <div class=\"overlay\" ng-click=\"participant.dates[$index] = !participant.dates[$index]\"></div>\n </div>\n <div class=\"cell action-cell\">\n <button type=\"submit\" ng-class=\"{ \'animated shake\' : formnew.$submitted && formnew.$invalid }\" class=\"btn\">Save</button>\n </div>\n </form>\n </div>\n</div>\n"); $templateCache.put("templates/directives/poll.html","<div class=\"poll-header\">\n <div class=\"header participants-header\">\n {{event.participants.length}} participants\n </div>\n <div class=\"header date-header\" ng-repeat=\"date in event.dates\">\n <div class=\"daticon\">\n <div class=\"dow\">\n {{date | date: \'EEE\'}}\n </div>\n <div class=\"day\">\n {{date | date: \'d\'}}\n </div>\n <div class=\"month\">\n {{date | date : \'MMM\'}}\n </div>\n <span class=\"count\" ng-show=\"selectedDate($index)\" ng-class={top:isTopDate($index)}>{{selectedDate($index)}}</span>\n </div>\n </div>\n <div class=\"header actions-header\">\n\n </div>\n</div>\n<div class=\"poll-body\">\n <div class=\"poll-entry\" ng-repeat=\"participant in event.participants\">\n <form novalidate ng-submit=\"update(participant); editMode = false\">\n <div class=\"cell name-cell\">\n <span class=\"avatar style-{{$index + 1}}\">\n <img src=\"/images/user.png\" width=\"11\" />\n </span>\n <input required autocomplete=\"off\" type=\"text\" class=\"form-control\" ng-model=\"participant.name\" ng-show=\"editMode\" value=\"participant.name\"/>\n <span ng-hide=\"editMode\" class=\"name editable\" ng-click=\"editMode = true && !event.isClosed; edit(participant)\">{{participant.name}}</span>\n </div>\n <div class=\"cell vote-cell\" ng-repeat=\"date in event.dates\">\n <img src=\"/images/tick@2x.png\" width=\"16\" ng-hide=\"editMode\" ng-if=\"participant.dates[$index]\" />\n <img src=\"/images/nope@2x.png\" width=\"8\" ng-hide=\"editMode\" ng-if=\"!participant.dates[$index]\" />\n <input ng-model=\"participant.dates[$index]\" ng-show=\"editMode\" ng-false-value=\"false\" type=\"checkbox\" />\n <div class=\"overlay\" ng-show=\"editMode\" ng-click=\"participant.dates[$index] = !participant.dates[$index]\"></div>\n </div>\n <div class=\"cell action-cell\" ng-hide=\"event.isClosed\">\n <button type=\"button\" ng-hide=\"editMode\" ng-click=\"editMode = true; edit(participant)\" class=\"btn hover\">Edit</button>\n <button type=\"button\" ng-hide=\"editMode\" ng-click=\"delete(participant)\" class=\"btn danger hover\">Delete</button>\n <button type=\"submit\" ng-show=\"editMode\" class=\"btn\">Save</button>\n <button type=\"button\" ng-show=\"editMode\" ng-click=\"editMode = false; cancel($index)\" class=\"btn\">Cancel</button>\n </div>\n </form>\n </div>\n <div class=\"poll-example\" ng-show=\"event.participants.length == 0\">\n <div class=\"poll-entry\" ng-repeat=\"example in event.examples\">\n <div class=\"cell name-cell\">\n <span class=\"avatar style-{{$index + 1}}\">\n <img src=\"/images/user.png\" width=\"11\" />\n </span>\n <span class=\"name\">{{example.name}}</span>\n </div>\n <div class=\"cell vote-cell\" ng-repeat=\"date in event.dates\">\n <img src=\"/images/tick@2x.png\" width=\"16\" ng-if=\"example.dates[$index]\" />\n <img src=\"/images/nope@2x.png\" width=\"8\" ng-if=\"!example.dates[$index]\" />\n </div>\n <div class=\"cell action-cell\">\n\n </div>\n </div>\n <div class=\"overlay\">\n\n </div>\n </div>\n <div ng-hide=\"event.isClosed\" class=\"poll-entry highlight\">\n <form novalidate name=\"formnew\" ng-submit=\"save()\">\n <div class=\"cell name-cell\">\n <span class=\"avatar style-{{participant.style}}\">\n <img src=\"/images/user.png\" width=\"11\" />\n </span>\n <input autocomplete=\"off\" name=\"username\" type=\"text\" class=\"form-control\" placeholder=\"Your name...\" ng-model=\"participant.name\" required value=\"participant.name\"/>\n </div>\n <div class=\"cell vote-cell\" ng-repeat=\"date in event.dates\">\n <input ng-model=\"participant.dates[$index]\" ng-false-value=\"false\" type=\"checkbox\" />\n <div class=\"overlay\" ng-click=\"participant.dates[$index] = !participant.dates[$index]\"></div>\n </div>\n <div class=\"cell action-cell\">\n <button type=\"submit\" ng-class=\"{ \'animated shake\' : formnew.$submitted && formnew.$invalid }\" class=\"btn\">Save</button>\n </div>\n </form>\n </div>\n</div>\n");
$templateCache.put("templates/directives/eventForm/dateForm.html","<div class=\"section-details\">\n <div class=\"section-title\">Choose Dates</div>\n <ul class=\"daticon-list\">\n <li ng-repeat=\"date in event.dates\">\n <div class=\"daticon\">\n <div class=\"dow\">\n {{date | date: \'EEE\'}}\n </div>\n <div class=\"day\">\n {{date | date: \'d\'}}\n </div>\n <div class=\"month\">\n {{date | date : \'MMM\'}}\n </div>\n <span class=\"delete\" ng-click=\"datepicker.unsetDate(date)\"></span>\n </div>\n </li>\n </ul>\n</div>\n<div class=\"section-main\">\n <div class=\"form-row\">\n <div class=\"form-group\">\n <label for=\"email\">Calendar</label>\n <span class=\"form-error\" ng-show=\"(form.datepicker.$dirty || form.$submitted) && form.datepicker.$error.required\">\n <img src=\"/images/error.png\" width=\"14\" /> You need to select a few dates\n </span>\n <div datepicker required name=\"datepicker\" control=\"datepicker\" ng-model=\"event.dates\">\n\n </div>\n </div>\n </div>\n</div>\n"); $templateCache.put("templates/directives/eventForm/dateForm.html","<div class=\"section-details\">\n <div class=\"section-title\">Choose Dates</div>\n <ul class=\"daticon-list\">\n <li ng-repeat=\"date in event.dates\">\n <div class=\"daticon\">\n <div class=\"dow\">\n {{date | date: \'EEE\'}}\n </div>\n <div class=\"day\">\n {{date | date: \'d\'}}\n </div>\n <div class=\"month\">\n {{date | date : \'MMM\'}}\n </div>\n <span class=\"delete\" ng-click=\"datepicker.unsetDate(date)\"></span>\n </div>\n </li>\n </ul>\n</div>\n<div class=\"section-main\">\n <div class=\"form-row\">\n <div class=\"form-group\">\n <label for=\"email\">Calendar</label>\n <span class=\"form-error\" ng-show=\"(form.datepicker.$dirty || form.$submitted) && form.datepicker.$error.required\">\n <img src=\"/images/error.png\" width=\"14\" /> You need to select a few dates\n </span>\n <div datepicker required name=\"datepicker\" control=\"datepicker\" ng-model=\"event.dates\">\n\n </div>\n </div>\n </div>\n</div>\n");
$templateCache.put("templates/directives/eventForm/eventForm.html","<div class=\"section-details\">\n <div class=\"section-title\">Event Details</div>\n</div>\n<div class=\"section-main\">\n <div class=\"form-row\">\n <div class=\"form-col\">\n <div class=\"form-group\">\n <label for=\"title\">Title</label>\n <span class=\"form-error\" ng-show=\"(form.title.$touched || form.$submitted) && errors.title\">\n <img src=\"/images/error.png\" width=\"14\" /> {{errors.title}}\n </span>\n <input id=\"title\" name=\"title\" ng-maxlength=\"30\" required ng-model=\"event.title\" type=\"text\" placeholder=\"Monthly Meetup...\" class=\"form-control extend\"/>\n </div>\n </div>\n <div class=\"form-col\">\n <div class=\"form-group optional\">\n <label for=\"location\">Location</label>\n <span class=\"form-error\" ng-show=\"(form.location.$touched || form.$submitted) && errors.location\">\n <img src=\"/images/error.png\" width=\"14\" /> {{errors.location}}\n </span>\n <input id=\"location\" name=\"location\" ng-model=\"event.location\" ng-maxlength=\"50\" type=\"text\" placeholder=\"Rick\'s Cafe...\" class=\"form-control extend\"/>\n </div>\n </div>\n </div>\n <div class=\"form-row\">\n <div class=\"form-group optional\">\n <label for=\"description\" >Description</label>\n <textarea id=\"description\" name=\"description\" ng-model=\"event.description\" placeholder=\"Enter Description...\" class=\"form-control extend\"></textarea>\n </div>\n </div>\n</div>\n"); $templateCache.put("templates/directives/eventForm/eventForm.html","<div class=\"section-details\">\n <div class=\"section-title\">Event Details</div>\n</div>\n<div class=\"section-main\">\n <div class=\"form-row\">\n <div class=\"form-col\">\n <div class=\"form-group\">\n <label for=\"title\">Title</label>\n <span class=\"form-error\" ng-show=\"(form.title.$touched || form.$submitted) && errors.title\">\n <img src=\"/images/error.png\" width=\"14\" /> {{errors.title}}\n </span>\n <input id=\"title\" name=\"title\" ng-maxlength=\"30\" required ng-model=\"event.title\" type=\"text\" placeholder=\"Monthly Meetup...\" class=\"form-control extend\"/>\n </div>\n </div>\n <div class=\"form-col\">\n <div class=\"form-group optional\">\n <label for=\"location\">Location</label>\n <span class=\"form-error\" ng-show=\"(form.location.$touched || form.$submitted) && errors.location\">\n <img src=\"/images/error.png\" width=\"14\" /> {{errors.location}}\n </span>\n <input id=\"location\" name=\"location\" ng-model=\"event.location\" ng-maxlength=\"50\" type=\"text\" placeholder=\"Rick\'s Cafe...\" class=\"form-control extend\"/>\n </div>\n </div>\n </div>\n <div class=\"form-row\">\n <div class=\"form-group optional\">\n <label for=\"description\" >Description</label>\n <textarea id=\"description\" name=\"description\" ng-model=\"event.description\" placeholder=\"Enter Description...\" class=\"form-control extend\"></textarea>\n </div>\n </div>\n</div>\n");
$templateCache.put("templates/directives/eventForm/participantsForm.html","<div class=\"section-details\">\n <div class=\"section-title\">Invite Participants</div>\n</div>\n<div class=\"section-main\">\n <div class=\"form-row\">\n <div class=\"form-group optional\">\n <label>Participant\'s Emails</label>\n <tags-input max-length=\"50\" allowed-tags-pattern=\"{{emailRegex}}\" display-property=\"email\" ng-model=\"event.emails\" placeholder=\"Add an Email\" type=\"email\" autocomplete=\"off\"></tags-input>\n </div>\n </div>\n</div>\n</section>\n"); $templateCache.put("templates/directives/eventForm/participantsForm.html","<div class=\"section-details\">\n <div class=\"section-title\">Invite Participants</div>\n</div>\n<div class=\"section-main\">\n <div class=\"form-row\">\n <div class=\"form-group optional\">\n <label>Participant\'s Emails</label>\n <tags-input max-length=\"50\" allowed-tags-pattern=\"{{emailRegex}}\" display-property=\"email\" ng-model=\"event.emails\" placeholder=\"Add an Email\" type=\"email\" autocomplete=\"off\"></tags-input>\n </div>\n </div>\n</div>\n</section>\n");

View file

@ -36,7 +36,18 @@ $name-col-width: 235px;
.poll-body { .poll-body {
min-width:100%; min-width:100%;
.poll-example {
position:relative;
.overlay {
position:absolute;
top:0;
left:0;
width:100%;
height: 100%;
background: rgba(white, 0.5);
text-align: center;
}
}
.poll-entry.highlight { .poll-entry.highlight {
background: lighten($border-clr,10%); background: lighten($border-clr,10%);
} }
@ -77,7 +88,7 @@ $name-col-width: 235px;
padding: 5px 3px; padding: 5px 3px;
margin-left: 2px; margin-left: 2px;
border-radius: 2px; border-radius: 2px;
&:hover { &.editable:hover {
background: $background-clr; background: $background-clr;
cursor: pointer; cursor: pointer;
} }

View file

@ -28,7 +28,7 @@
<img src="/images/user.png" width="11" /> <img src="/images/user.png" width="11" />
</span> </span>
<input required autocomplete="off" type="text" class="form-control" ng-model="participant.name" ng-show="editMode" value="participant.name"/> <input required autocomplete="off" type="text" class="form-control" ng-model="participant.name" ng-show="editMode" value="participant.name"/>
<span ng-hide="editMode" class="name" ng-click="editMode = true && !event.isClosed; edit(participant)">{{participant.name}}</span> <span ng-hide="editMode" class="name editable" ng-click="editMode = true && !event.isClosed; edit(participant)">{{participant.name}}</span>
</div> </div>
<div class="cell vote-cell" ng-repeat="date in event.dates"> <div class="cell vote-cell" ng-repeat="date in event.dates">
<img src="/images/tick@2x.png" width="16" ng-hide="editMode" ng-if="participant.dates[$index]" /> <img src="/images/tick@2x.png" width="16" ng-hide="editMode" ng-if="participant.dates[$index]" />
@ -44,6 +44,26 @@
</div> </div>
</form> </form>
</div> </div>
<div class="poll-example" ng-show="event.participants.length == 0">
<div class="poll-entry" ng-repeat="example in event.examples">
<div class="cell name-cell">
<span class="avatar style-{{$index + 1}}">
<img src="/images/user.png" width="11" />
</span>
<span class="name">{{example.name}}</span>
</div>
<div class="cell vote-cell" ng-repeat="date in event.dates">
<img src="/images/tick@2x.png" width="16" ng-if="example.dates[$index]" />
<img src="/images/nope@2x.png" width="8" ng-if="!example.dates[$index]" />
</div>
<div class="cell action-cell">
</div>
</div>
<div class="overlay">
</div>
</div>
<div ng-hide="event.isClosed" class="poll-entry highlight"> <div ng-hide="event.isClosed" class="poll-entry highlight">
<form novalidate name="formnew" ng-submit="save()"> <form novalidate name="formnew" ng-submit="save()">
<div class="cell name-cell"> <div class="cell name-cell">

View file

@ -26,7 +26,6 @@
<script type="text/javascript" src="/vendor/angular/angular.min.js"></script> <script type="text/javascript" src="/vendor/angular/angular.min.js"></script>
<script type="text/javascript" src="/vendor/angular-resource/angular-resource.min.js"></script> <script type="text/javascript" src="/vendor/angular-resource/angular-resource.min.js"></script>
<script type="text/javascript" src="/vendor/angular-ui-router/release/angular-ui-router.min.js"></script> <script type="text/javascript" src="/vendor/angular-ui-router/release/angular-ui-router.min.js"></script>
<script type="text/javascript" src="/vendor/ngFx/dist/ngFx.min.js"></script>
<script type="text/javascript" src="/vendor/angular-modal/modal.min.js"></script> <script type="text/javascript" src="/vendor/angular-modal/modal.min.js"></script>
<script type="text/javascript" src="/vendor/ng-tags-input/ng-tags-input.min.js"></script> <script type="text/javascript" src="/vendor/ng-tags-input/ng-tags-input.min.js"></script>
<script type="text/javascript" src="/vendor/angular-animate/angular-animate.min.js"></script> <script type="text/javascript" src="/vendor/angular-animate/angular-animate.min.js"></script>