Skip to content

Instantly share code, notes, and snippets.

@Rio517
Created May 18, 2015 01:48
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Rio517/b241acf9137173a5ff3e to your computer and use it in GitHub Desktop.
Save Rio517/b241acf9137173a5ff3e to your computer and use it in GitHub Desktop.
Ember Chat App
<!DOCTYPE html>
<html>
<head>
<title>Chatapp</title>
<link rel="stylesheet" href="//cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.3.4/css/bootstrap.min.css">
<script src="//cdnjs.cloudflare.com/ajax/libs/modernizr/2.8.3/modernizr.min.js"></script>
</head>
<body>
<style>
#chat-app{
position:absolute;
bottom:0;
right:10px;
}
#chat-app > li{
float:left;
padding:10px;
border:2px solid #666;
width:240px;
margin-right:10px;
max-height:280px;
overflow-y:scroll;
}
#chat-app input{
margin:10px auto;
}
#chat-app > li{
-webkit-transition: background 0.5s linear;
-moz-transition: background 0.5s linear;
-ms-transition: background 0.5s linear;
-o-transition: background 0.5s linear;
transition: background 0.5s linear;
}
#chat-app > li.flashed { background-color: #d1d1d1; color:#fff; }
</style>
<script type="text/x-handlebars" data-template-name="components/chat-holder">
<button {{action "markInactive"}}>close</button>
<h3>Profile: {{conversation.profile}} Conversation: {{conversation.id}}</h3>
<ul class="list-unstyled">
{{#each message in conversation.messages}}
<li><strong>{{message.type}}</strong> {{message.body}}</li>
{{/each}}
<li>
<form class="form-inline" {{action "createMessage" on="submit"}}>
{{input class="message_body" placeholder="Start typing a message..." value=conversation.new_message_body type="text"}}
{{input class="btn" type="submit" value="Send"}}
</form>
</li>
</ul>
</script>
<script type="text/x-handlebars" data-template-name="conversations">
<section id="todoapp">
<header id="header">
<h1>Chat Messaging</h1>
</header>
</section>
<section id="main">
<p>Open a new chat with profile id #1 <a href="#" {{action "openChat" 1 1}} >Open w/ profile 1</a> | <a href="#" {{action "openChat" 1 6}} >open profile already in convo</a></p>
<ul id="chat-app" class="list-unstyled clearfix">
{{#each conversation in model}}
<li>{{chat-holder conversation=conversation}}</li>
{{/each}}
</ul>
</section>
</script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.3.4/js/bootstrap.min.js"></script>
<script scr="https://cdnjs.cloudflare.com/ajax/libs/handlebars.js/3.0.1/handlebars.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/ember.js/1.11.3/ember.min.js"></script>
<script src="http://builds.emberjs.com/release/ember-template-compiler.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/ember-data.js/1.0.0-beta.16.1/ember-data.min.js"></script>
<script>
window.ChatApp = Ember.Application.create({
server_host: 'http://localhost:3000'
});
ChatApp.ApplicationAdapter = DS.RESTAdapter.extend({
host: ChatApp.server_host,
});
ChatApp.Router.map(function () {
this.resource('conversations', { path: '/' });
});
ChatApp.ConversationsRoute = Ember.Route.extend({
model: function () {
this.store.find('conversation');
return this.store.filter('conversation', function (conversation){
return conversation.get('status') == 'active';
});
},
activate: function() { //listens to event stream
if (! this.eventSource) {
this.eventSource = new EventSource(ChatApp.server_host + '/conversations/events');
var self = this;
this.eventSource.addEventListener('message', function(e) {
var data = $.parseJSON(e.data);
if(data['type'] == 'MO'){
var target_conversation = self.store.all('conversation').findBy('id',data['conversation_id'])
// var target_conversation = self.store.find('conversation',data['conversation_id']); < This should have worked
message = self.store.createRecord('message', {
body: data['body'],
created_at: data['created_at'],
conversation: target_conversation,
type: data['type'],
id: data['type'] + data['id'],
});
}
});
}
}
});
ChatApp.ConversationsController = Ember.Controller.extend({
actions: {
openChat: function(user_id, profile_id){
if(this.existingChat(profile_id)){
new_chat = this.get('content').findBy('profile_id', profile_id).get('firstObject');
}else{
this.removeExcessChats();
new_chat = this.store.createRecord('conversation', {
profile_id: profile_id,
status: 'active',
user_id: user_id
});
new_chat.save();
}
// new_chat.set('isFlashed', true);
var needingVisibilityChange = this.get('content').filterBy('profile_id', profile_id);
needingVisibilityChange.setEach('isFlashed', true);
}
},
eachChatWidth: 240,
maxChats: function(){
output = window.innerWidth/this.get('eachChatWidth');
return Math.floor(output);
},
removeExcessChats: function(){
if(this.get('content').get('length') >= this.maxChats()){
conversation_to_remove = this.get('content').get('firstObject');
conversation_to_remove.markInactive();
}
},
existingChat: function(profile_id){
return this.get('content').filterBy('profile_id', profile_id).get('length') > 0;
}
});
ChatApp.ChatHolderComponent = Ember.Component.extend({
actions: {
markInactive: function(){
console.log('markingInactive');
this.get('conversation').markInactive();
},
createMessage: function(){
parentModel = this.get('conversation');
var body = parentModel.get('new_message_body');
if(Ember.isBlank(body.trim())){ return; }
var newMessageAttributes = {
body: body,
type: 'MT',
created_at: Date.now()//used locally
}
message = parentModel.store.createRecord('message', newMessageAttributes);
parentModel.get('messages').pushObject(message)
message.save();
parentModel.set('new_message_body', '');
}
},
isFlashed: false
});
ChatApp.Profile = DS.Model.extend({
first_name: DS.attr('string'),
last_name: DS.attr('string'),
first_name: DS.attr('string'),
})
ChatApp.Conversation = DS.Model.extend({
profile: DS.attr('string'),
profile_id: DS.attr('number'),
phone: DS.attr('string'),
status: DS.attr('string'),
messages: DS.hasMany('Message', {async: true}),
user_id: DS.attr('number'),
markInactive: function(){
this.set('status','archived');
this.save();
}
});
ChatApp.Message = DS.Model.extend({
body: DS.attr('string'),
type: DS.attr('string'),
conversation: DS.belongsTo('Conversation', {async: true}),
created_at: DS.attr('date')
});
</script>
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment