User can select Night and Day Moods

headline method on post

extract headline and body from post, at first newline

Night Mood
This commit is contained in:
Dennis Collinson 2012-03-27 18:04:21 -07:00
parent f25effcafe
commit 78a2ed28b9
11 changed files with 127 additions and 44 deletions

View file

@ -89,11 +89,25 @@ app.models.Post = Backbone.Model.extend({
self.set(resp);
self.trigger('interacted', this)
}});
},
headline : function() {
var headline = this.get("text").trim()
, newlineIdx = headline.lastIndexOf("\n")
return (newlineIdx > 0 ) ? headline.substr(0, newlineIdx) : headline
},
body : function(){
var body = this.get("text").trim()
, newlineIdx = body.lastIndexOf("\n")
return (newlineIdx > 0 ) ? body.substr(newlineIdx+1, body.length) : ""
}
}, {
headlineLimit : 118,
frameMoods : [
"Day"
"Day",
"Night"
],
legacyTemplateNames : [

View file

@ -1,17 +0,0 @@
//= require ../post_view
app.views.Post.Day = app.views.Post.extend({
templateName : "day",
className : "day post loaded",
subviews : { "section.photo_viewer" : "photoViewer" },
photoViewer : function(){
return new app.views.PhotoViewer({ model : this.model })
},
postRenderTemplate : function(){
if(this.model.get("text").length < 140){
this.$('section.text').addClass('headline');
}
}
});

View file

@ -0,0 +1,36 @@
app.views.Post.Mood = app.views.Post.extend({
templateName : "mood",
className : "post loaded",
tagName : "article",
subviews : { "section.photo_viewer" : "photoViewer" },
initialize : function(){
$(this.el).addClass(this.mood)
},
presenter : function(){
var model = this.model
return _.extend(this.defaultPresenter(), {
headline : model.headline(),
body : model.body()
})
},
photoViewer : function(){
return new app.views.PhotoViewer({ model : this.model })
},
postRenderTemplate : function(){
if(this.model.body().length < 200){
this.$('section.body').addClass('short_body');
}
}
});
app.views.Post.Day = app.views.Post.Mood.extend({
mood : "day"
})
app.views.Post.Night = app.views.Post.Mood.extend({
mood : "night"
})

View file

@ -2,7 +2,7 @@ app.views.TemplatePicker = app.views.Base.extend({
templateName : "template-picker",
initialize : function(){
this.model.set({frame_name : 'status'})
this.model.set({frame_name : 'Day'})
},
events : {
@ -19,7 +19,7 @@ app.views.TemplatePicker = app.views.Base.extend({
presenter : function() {
return _.extend(this.defaultPresenter(), {
templates : _.union(app.models.Post.frameMoods, app.models.Post.legacyTemplateNames)
templates : _.union(app.models.Post.frameMoods, _.without(app.models.Post.legacyTemplateNames, ["status"]))
})
}
})

View file

@ -3,6 +3,9 @@
$light-grey: #999;
$pane-width: 420px;
$night-background-color : #333;
$night-text-color : #999;
/* mixins */
@mixin center($orient:vertical) {
@ -259,7 +262,7 @@ $pane-width: 420px;
left: 0;
text-align: center;
background-color: #333;
background-color: $night-background-color;
p {
@include media-text();
@ -807,6 +810,27 @@ text-rendering: optimizelegibility;
}
}
.headline p{
@include media-text();
article { //mood posts
$big-text-size : 3em;
$medium-text-size : 2em;
$small-text-size: 1.5em;
header, header p{
//big text
@include media-text();
font-size: $big-text-size;
}
section.body{
font-size: $small-text-size;
&.short_body{
font-size: $medium-text-size;
}
}
&.night{
background-color : $night-background-color;
color : $night-text-color;
}
}

View file

@ -1,2 +0,0 @@
<section class="text">{{{text}}}</section>
<section class="photo_viewer"></section>

View file

@ -0,0 +1,3 @@
<header>{{headline}}</header>
<section class="photo_viewer"></section>
<section class="body">{{{body}}}</section>

View file

@ -3,15 +3,30 @@ describe("app.models.Post", function() {
this.post = new app.models.Post();
})
describe("url", function(){
it("should be /posts when it doesn't have an id", function(){
expect(new app.models.Post().url()).toBe("/posts")
describe("headline and body", function(){
describe("headline", function(){
beforeEach(function(){
this.post.set({text :" yes "})
})
it("the headline is the entirety of the post", function(){
expect(this.post.headline()).toBe("yes")
})
it("takes up until the new line", function(){
this.post.set({text : "love\nis avery powerful force"})
expect(this.post.headline()).toBe("love")
})
})
it("should be /posts/id when it doesn't have an id", function(){
expect(new app.models.Post({id: 5}).url()).toBe("/posts/5")
describe("body", function(){
it("takes after the new line", function(){
this.post.set({text : "Inflamatory Title\nwith text that substantiates a less absolutist view of the title."})
expect(this.post.body()).toBe("with text that substantiates a less absolutist view of the title.")
})
})
})
describe("createdAt", function() {
it("returns the post's created_at as an integer", function() {
var date = new Date;
@ -99,6 +114,4 @@ describe("app.models.Post", function() {
expect(app.models.Participation.prototype.destroy).toHaveBeenCalled();
})
})
});

View file

@ -9,17 +9,17 @@ describe("app.views.Post.Day", function(){
this.view.render()
})
describe("when the text is under 140 characters", function(){
it("has class headline", function(){
this.post.set({text : "Lol this is a short headline"})
describe("when the body is under 200 characters", function(){
it("has class shortBody", function(){
this.post.set({text : "Headline\nLol this is a short body"})
this.view.render()
expect(this.view.$("section.text")).toHaveClass("headline")
expect(this.view.$("section.body")).toHaveClass("short_body")
})
})
describe("when the text is over 140 characters", function(){
describe("when the body is over 200 characters", function(){
it("has doesn't have headline", function(){
this.post.set({text :"Vegan bushwick tempor labore. Nulla seitan anim, aesthetic ex gluten-free viral" +
this.post.set({text :"HEADLINE\nVegan bushwick tempor labore. Nulla seitan anim, aesthetic ex gluten-free viral" +
"thundercats street art. Occaecat carles deserunt lomo messenger bag wes anderson. Narwhal cray selvage " +
"dolor. Mixtape wes anderson american apparel, mustache readymade cred nulla squid veniam small batch id " +
"cupidatat. Pork belly high life consequat, raw denim sint terry richardson seitan single-origin coffee " +
@ -27,8 +27,8 @@ describe("app.views.Post.Day", function(){
})
this.view.render()
expect(this.view.$("section.text")).not.toHaveClass("headline")
expect(this.view.$("section.body")).not.toHaveClass("short_body")
})
})
})
})
})

View file

@ -0,0 +1,12 @@
describe("app.views.Post.Night", function(){
beforeEach(function(){
this.post = factory.post()
this.view = new app.views.Post.Night({model : this.post})
})
describe("rendering", function(){
it("is happy", function(){
this.view.render()
})
})
})

View file

@ -6,7 +6,7 @@ describe("app.views.TemplatePicker", function(){
describe("initialization", function(){
it("sets the frame_name of the model to 'status' by default", function(){
expect(this.view.model.get("frame_name")).toBe("status")
expect(this.view.model.get("frame_name")).toBe("Day")
})
})
@ -16,13 +16,13 @@ describe("app.views.TemplatePicker", function(){
})
it("selects the model's frame_name from the dropdown", function(){
expect(this.view.$("select[name=template]").val()).toBe("status")
expect(this.view.$("select[name=template]").val()).toBe("Day")
})
it("changes the frame_name on the model when is is selected", function(){
this.view.$("select[name=template]").val("note")
this.view.$("select[name=template]").val("Night")
this.view.$("select[name=template]").trigger("change")
expect(this.model.get("frame_name")).toBe('note')
expect(this.model.get("frame_name")).toBe('Night')
})
})
})