Re-style Blog, Add Newsletter Signup Form
Summary: The goal of this PR is to place greater emphasis on the blog as a destination. The dark Hero from the landing page is now present in the blog as well, and the content is front and center. The sidebar has been removed. It is not necessary to show a list of recent blog posts in the sidebar when the blog landing page shows the same number of posts along with short excerpts. The prev/next links have swapped positions, and will now display "Older posts" and "Newer posts". The excerpts have been stripped of formatting and they are now consistent across the blog landing page and the OpenGraph metatags. Fixes #10597. A signup form for the new React Native newsletter has been added to the footer. Newsletter signup form in footer: ![screencapture-localhost-8079-react-native-1477944030909](https://cloud.githubusercontent.com/assets/165856/19869614/4bb035aa-9f6a-11e6-9b8e-e0333417f423.png) Blog landing page: ![screencapture-localhost-8079-r Closes https://github.com/facebook/react-native/pull/10660 Differential Revision: D4117034 Pulled By: bestander fbshipit-source-id: 215f966008fdf5c8870ed28d92384034a0d23c39
This commit is contained in:
parent
680df8900b
commit
bdbadd1142
|
@ -20,36 +20,14 @@ var ExcerptLink = require('ExcerptLink');
|
|||
var BlogPost = React.createClass({
|
||||
render: function() {
|
||||
var post = this.props.post;
|
||||
var content = this.props.content;
|
||||
|
||||
var match = post.publishedAt.match(/([0-9]+)-([0-9]+)-([0-9]+)/);
|
||||
// Because JavaScript sucks at date handling :(
|
||||
var year = match[1];
|
||||
var month = [
|
||||
'January', 'February', 'March', 'April', 'May', 'June', 'July',
|
||||
'August', 'September', 'October', 'November', 'December'
|
||||
][parseInt(match[2], 10) - 1];
|
||||
var day = parseInt(match[3], 10);
|
||||
|
||||
var postedOnDate = month + ' ' + day + ', ' + year;
|
||||
|
||||
var footer = <BlogPostFooter post={post} postedOnDate={postedOnDate} />;
|
||||
|
||||
if (this.props.excerpt) {
|
||||
content = content.trim().split('\n')[0];
|
||||
footer = <ExcerptLink href={'/react-native/blog/' + post.path} category={post.category} />;
|
||||
}
|
||||
|
||||
return (
|
||||
<article>
|
||||
<BlogPostHeader
|
||||
post={post}
|
||||
postedOnDate={postedOnDate}
|
||||
excerpt={this.props.excerpt} />
|
||||
<article className="entry-body">
|
||||
<BlogPostHeader post={post} />
|
||||
<div className="entry-content">
|
||||
<Marked>{content}</Marked>
|
||||
<Marked>{this.props.content}</Marked>
|
||||
</div>
|
||||
{footer}
|
||||
<BlogPostFooter post={post} />
|
||||
</article>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
/**
|
||||
* Copyright (c) 2015-present, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
* @providesModule BlogPostDate
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
|
||||
var React = require('React');
|
||||
|
||||
var BlogPostDate = React.createClass({
|
||||
render: function() {
|
||||
var post = this.props.post;
|
||||
|
||||
var match = post.publishedAt.match(/([0-9]+)-([0-9]+)-([0-9]+)/);
|
||||
// Because JavaScript sucks at date handling :(
|
||||
var year = match[1];
|
||||
var month = [
|
||||
'January', 'February', 'March', 'April', 'May', 'June', 'July',
|
||||
'August', 'September', 'October', 'November', 'December'
|
||||
][parseInt(match[2], 10) - 1];
|
||||
var day = parseInt(match[3], 10);
|
||||
|
||||
var postedOnDate = month + ' ' + day + ', ' + year;
|
||||
|
||||
return (
|
||||
<time className="date" datetime={post.publishedAt}>{postedOnDate}</time>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
module.exports = BlogPostDate;
|
|
@ -0,0 +1,38 @@
|
|||
/**
|
||||
* Copyright (c) 2015-present, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
* @providesModule BlogPostExcerpt
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
|
||||
var React = require('React');
|
||||
var BlogPostHeader = require('BlogPostHeader');
|
||||
var Marked = require('Marked');
|
||||
var ExcerptLink = require('ExcerptLink');
|
||||
|
||||
var BlogPostExcerpt = React.createClass({
|
||||
render: function() {
|
||||
var post = this.props.post;
|
||||
return (
|
||||
<article className="entry-excerpt">
|
||||
<BlogPostHeader
|
||||
post={post}
|
||||
excerpt={true} />
|
||||
<div className="entry-content">
|
||||
<Marked>{post.excerpt}</Marked>
|
||||
</div>
|
||||
<ExcerptLink
|
||||
href={'/react-native/blog/' + post.path}
|
||||
category={post.category} />
|
||||
</article>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
module.exports = BlogPostExcerpt;
|
|
@ -12,6 +12,7 @@
|
|||
'use strict';
|
||||
|
||||
var React = require('React');
|
||||
var BlogPostDate = require('BlogPostDate');
|
||||
|
||||
var BlogPostFooter = React.createClass({
|
||||
render: function() {
|
||||
|
@ -32,7 +33,7 @@ var BlogPostFooter = React.createClass({
|
|||
<div className="author-image">
|
||||
<span className="the-image" style={{backgroundImage: "url(" + authorImage + ")"}}></span>
|
||||
</div>
|
||||
<p className="posted-on">Posted on {this.props.postedOnDate}</p>
|
||||
<p className="posted-on">Posted on <BlogPostDate post={post} /></p>
|
||||
<p className="name-title">
|
||||
<a href={post.authorURL} target="_blank">
|
||||
{post.author}
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
'use strict';
|
||||
|
||||
var React = require('React');
|
||||
var BlogPostDate = require('BlogPostDate');
|
||||
|
||||
var BlogPostHeader = React.createClass({
|
||||
render: function() {
|
||||
|
@ -47,7 +48,7 @@ var BlogPostHeader = React.createClass({
|
|||
{post.author}
|
||||
</a>
|
||||
{' — '}
|
||||
<span className="date">{this.props.postedOnDate}</span>
|
||||
<BlogPostDate post={post} />
|
||||
</h4>
|
||||
<h1 className="entry-title">{title}</h1>
|
||||
</header>
|
||||
|
|
|
@ -1,42 +0,0 @@
|
|||
/**
|
||||
* Copyright (c) 2015-present, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
* @providesModule BlogSidebar
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
|
||||
var MetadataBlog = require('MetadataBlog');
|
||||
var React = require('React');
|
||||
|
||||
var BlogSidebar = React.createClass({
|
||||
render: function() {
|
||||
return (
|
||||
<div className="nav-docs">
|
||||
<div className="nav-docs-section">
|
||||
<h3>Recent Posts</h3>
|
||||
<ul>
|
||||
{MetadataBlog.files.slice(0,10).map(function(post) {
|
||||
return (
|
||||
<li key={post.path}>
|
||||
<a
|
||||
className={this.props.title === post.title ? 'active' : ''}
|
||||
href={'/react-native/blog/' + post.path}>
|
||||
{post.title}
|
||||
</a>
|
||||
</li>
|
||||
);
|
||||
}.bind(this))}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
module.exports = BlogSidebar;
|
|
@ -0,0 +1,30 @@
|
|||
/**
|
||||
* Copyright (c) 2015-present, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
* @providesModule Hero
|
||||
*/
|
||||
|
||||
var React = require('React');
|
||||
|
||||
var Hero = React.createClass({
|
||||
render: function() {
|
||||
return (
|
||||
<div className="hero">
|
||||
<div className="wrap">
|
||||
<div className="text"><strong>{this.props.title}</strong></div>
|
||||
<div className="minitext">
|
||||
{this.props.subtitle}
|
||||
</div>
|
||||
</div>
|
||||
{this.props.children}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
module.exports = Hero;
|
|
@ -106,6 +106,9 @@ var Site = React.createClass({
|
|||
<link rel="shortcut icon" href="img/favicon.png?2" />
|
||||
<link rel="stylesheet" href="css/react-native.css" />
|
||||
|
||||
<link rel="alternate" type="application/rss+xml" title="React Native Blog" href="https://facebook.github.io/react-native/blog/feed.xml" />
|
||||
<link href="//cdn-images.mailchimp.com/embedcode/horizontal-slim-10_7.css" rel="stylesheet" type="text/css" />
|
||||
|
||||
<script type="text/javascript" src="//use.typekit.net/vqa1hcx.js"></script>
|
||||
<script type="text/javascript">{'try{Typekit.load();}catch(e){}'}</script>
|
||||
</head>
|
||||
|
@ -141,7 +144,7 @@ var Site = React.createClass({
|
|||
<a href="docs/more-resources.html">More Resources</a>
|
||||
</div>
|
||||
<div>
|
||||
<h5><a href="/react-native/support.html">Community</a></h5>
|
||||
<h5><a href="/react-native/support.html">Community</a></h5>
|
||||
<a href="/react-native/showcase.html">Showcase</a>
|
||||
<a href="http://www.meetup.com/topics/react-native/" target="_blank">Upcoming Events</a>
|
||||
<a href="https://www.facebook.com/groups/react.native.community" target="_blank">Facebook Group</a>
|
||||
|
@ -161,6 +164,25 @@ var Site = React.createClass({
|
|||
<a href="http://facebook.github.io/react/" target="_blank">React</a>
|
||||
</div>
|
||||
</section>
|
||||
<section className="newsletter">
|
||||
<div id="mc_embed_signup">
|
||||
<form action="//github.us14.list-manage.com/subscribe/post?u=bb5453b13c3abce440d274dc7&id=60de5624cd" method="post" id="mc-embedded-subscribe-form" name="mc-embedded-subscribe-form" className="validate" target="_blank" noValidate>
|
||||
<div id="mc_embed_signup_scroll">
|
||||
<label for="mce-EMAIL">
|
||||
<h5>Get the React Native Newsletter</h5>
|
||||
</label>
|
||||
<input type="email" value="" name="EMAIL" className="email" id="mce-EMAIL" placeholder="email address" required />
|
||||
<div style={{ position: "absolute", left: "-5000px"}} aria-hidden="true">
|
||||
<input type="text" name="b_bb5453b13c3abce440d274dc7_60de5624cd" tabIndex="-1" value="" />
|
||||
</div>
|
||||
<div className="clear">
|
||||
<input type="submit" value="Sign up" name="subscribe" id="mc-embedded-subscribe" className="button" />
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<a href="https://code.facebook.com/projects/" target="_blank" className="fbOpenSource">
|
||||
<img src="img/oss_logo.png" alt="Facebook Open Source" width="170" height="45"/>
|
||||
</a>
|
||||
|
@ -192,6 +214,9 @@ var Site = React.createClass({
|
|||
});
|
||||
`}} />
|
||||
<script src="js/scripts.js" />
|
||||
{/* Mailchimp Inline form-submission script for the React Native newsletter sign up form */}
|
||||
<script type='text/javascript' src='//s3.amazonaws.com/downloads.mailchimp.com/js/mc-validate.js'></script>
|
||||
<script type='text/javascript' dangerouslySetInnerHTML={{__html: `(function($) {window.fnames = new Array(); window.ftypes = new Array();fnames[0]='EMAIL';ftypes[0]='email';fnames[1]='FNAME';ftypes[1]='text';fnames[2]='LNAME';ftypes[2]='text';}(jQuery));var $mcj = jQuery.noConflict(true);`}} />
|
||||
</body>
|
||||
</html>
|
||||
);
|
||||
|
|
|
@ -11,11 +11,12 @@
|
|||
|
||||
'use strict';
|
||||
|
||||
var BlogPost = require('BlogPost');
|
||||
var BlogSidebar = require('BlogSidebar');
|
||||
var MetadataBlog = require('MetadataBlog');
|
||||
var React = require('React');
|
||||
var Site = require('Site');
|
||||
var Hero = require('Hero');
|
||||
var MetadataBlog = require('MetadataBlog');
|
||||
var BlogPost = require('BlogPost');
|
||||
var BlogPostExcerpt = require('BlogPostExcerpt');
|
||||
|
||||
var BlogPageLayout = React.createClass({
|
||||
getPageURL: function(page) {
|
||||
|
@ -34,27 +35,22 @@ var BlogPageLayout = React.createClass({
|
|||
section="blog"
|
||||
title="React Native Blog"
|
||||
description="The best place to stay up-to-date with the latest React Native news and events.">
|
||||
<Hero title="React Native Blog" subtitle="Stay up-to-date with the latest React Native news and events." />
|
||||
<section className="content wrap documentationContent">
|
||||
<BlogSidebar />
|
||||
<div className="inner-content">
|
||||
{MetadataBlog.files
|
||||
.slice(page * perPage, (page + 1) * perPage)
|
||||
.map((post) => {
|
||||
return (
|
||||
<div>
|
||||
<BlogPost post={post} content={post.content} excerpt={true} />
|
||||
<hr />
|
||||
</div>
|
||||
<BlogPostExcerpt post={post} />
|
||||
)
|
||||
})
|
||||
}
|
||||
<div className="docs-prevnext">
|
||||
{page > 0 &&
|
||||
<a className="docs-prev" href={this.getPageURL(page - 1)}>← Prev</a>}
|
||||
{MetadataBlog.files.length > (page + 1) * perPage &&
|
||||
<a className="docs-next" href={this.getPageURL(page + 1)}>Next →</a>}
|
||||
<a className="docs-next" href={this.getPageURL(page + 1)}>← Older posts</a>}
|
||||
{page > 0 &&
|
||||
<a className="docs-prev" href={this.getPageURL(page - 1)}>Newer posts →</a>}
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</Site>
|
||||
);
|
||||
|
|
|
@ -11,12 +11,13 @@
|
|||
|
||||
'use strict';
|
||||
|
||||
var BlogPost = require('BlogPost');
|
||||
var BlogSidebar = require('BlogSidebar');
|
||||
var Marked = require('Marked');
|
||||
var MetadataBlog = require('MetadataBlog');
|
||||
var React = require('React');
|
||||
var Site = require('Site');
|
||||
var Hero = require('Hero');
|
||||
var MetadataBlog = require('MetadataBlog');
|
||||
var BlogPost = require('BlogPost');
|
||||
var BlogPostHeader = require('BlogPostHeader');
|
||||
var Marked = require('Marked');
|
||||
|
||||
var BlogPostLayout = React.createClass({
|
||||
render: function() {
|
||||
|
@ -24,19 +25,17 @@ var BlogPostLayout = React.createClass({
|
|||
<Site
|
||||
section="blog"
|
||||
title={this.props.metadata.title}
|
||||
description={this.props.children.trim().split('\n')[0]}
|
||||
description={this.props.metadata.excerpt}
|
||||
path={'blog/' + this.props.metadata.path}
|
||||
author={this.props.metadata.author}
|
||||
authorTwitter={this.props.metadata.authorTwitter}
|
||||
image={this.props.metadata.hero ? 'http://facebook.github.io' + this.props.metadata.hero : 'http://facebook.github.io/react-native/img/opengraph.png' }
|
||||
image={this.props.metadata.hero ? 'https://facebook.github.io' + this.props.metadata.hero : 'https://facebook.github.io/react-native/img/opengraph.png' }
|
||||
>
|
||||
<Hero title="React Native Blog" subtitle="Stay up-to-date with the latest React Native news and events." />
|
||||
<section className="content wrap documentationContent">
|
||||
<BlogSidebar title={this.props.metadata.title} />
|
||||
<div className="inner-content">
|
||||
<BlogPost
|
||||
post={this.props.metadata}
|
||||
content={this.props.children} />
|
||||
</div>
|
||||
<BlogPost
|
||||
post={this.props.metadata}
|
||||
content={this.props.children} />
|
||||
</section>
|
||||
</Site>
|
||||
);
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
"react": "~0.13.0",
|
||||
"react-docgen": "^2.9.0",
|
||||
"react-page-middleware": "git://github.com/facebook/react-page-middleware.git",
|
||||
"remove-markdown": "^0.1.0",
|
||||
"request": "^2.69.0",
|
||||
"semver-compare": "^1.0.0"
|
||||
},
|
||||
|
|
|
@ -14,6 +14,7 @@ var glob = require('glob');
|
|||
var mkdirp = require('mkdirp');
|
||||
var optimist = require('optimist');
|
||||
var path = require('path');
|
||||
var removeMd = require('remove-markdown');
|
||||
var extractDocs = require('./extractDocs');
|
||||
var argv = optimist.argv;
|
||||
|
||||
|
@ -200,7 +201,8 @@ function execute() {
|
|||
|
||||
var res = extractMetadata(fs.readFileSync(file, {encoding: 'utf8'}));
|
||||
var rawContent = res.rawContent;
|
||||
var metadata = Object.assign({path: filePath, content: rawContent, publishedAt: publishedAt}, res.metadata);
|
||||
var excerpt = removeMd(rawContent).trim().split('\n')[0];
|
||||
var metadata = Object.assign({path: filePath, content: rawContent, publishedAt: publishedAt, excerpt: excerpt}, res.metadata);
|
||||
|
||||
metadatasBlog.files.push(metadata);
|
||||
|
||||
|
@ -210,7 +212,7 @@ function execute() {
|
|||
);
|
||||
});
|
||||
|
||||
var perPage = 5;
|
||||
var perPage = 15;
|
||||
for (var page = 0; page < Math.ceil(metadatasBlog.files.length / perPage); ++page) {
|
||||
writeFileAndCreateFolder(
|
||||
'src/react-native/blog' + (page > 0 ? '/page' + (page + 1) : '') + '/index.js',
|
||||
|
|
|
@ -55,7 +55,7 @@ queue = queue.then(function() {
|
|||
name: post.author,
|
||||
link: post.authorURL
|
||||
}],
|
||||
description: post.content.trim().split('\n')[0],
|
||||
description: post.excerpt,
|
||||
});
|
||||
});
|
||||
|
||||
|
|
|
@ -625,10 +625,6 @@ h1:hover .hash-link, h2:hover .hash-link, h3:hover .hash-link, h4:hover .hash-li
|
|||
}
|
||||
}
|
||||
|
||||
.nav-blog li {
|
||||
margin-bottom: 5px;
|
||||
}
|
||||
|
||||
.home-section {
|
||||
margin: 50px 0;
|
||||
}
|
||||
|
@ -749,11 +745,11 @@ h1:hover .hash-link, h2:hover .hash-link, h3:hover .hash-link, h4:hover .hash-li
|
|||
}
|
||||
|
||||
.docs-prev {
|
||||
float: left;
|
||||
float: right;
|
||||
}
|
||||
|
||||
.docs-next {
|
||||
float: right;
|
||||
float: left;
|
||||
}
|
||||
|
||||
section.black content {
|
||||
|
@ -827,7 +823,9 @@ h2 {
|
|||
}
|
||||
|
||||
.docs-prevnext {
|
||||
padding-top: 20px;
|
||||
min-width: 320px;
|
||||
max-width: 640px;
|
||||
margin: 0 auto 40px;
|
||||
padding-bottom: 20px;
|
||||
}
|
||||
|
||||
|
@ -1656,7 +1654,7 @@ input#algolia-doc-search:focus {
|
|||
/** Blog **/
|
||||
|
||||
.entry-header {
|
||||
margin: 40px 0 0 0;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.entry-header h1 {
|
||||
|
@ -1667,16 +1665,17 @@ input#algolia-doc-search:focus {
|
|||
|
||||
.entry-header h4 {
|
||||
margin: 0 0 10px;
|
||||
font-size: 12px;
|
||||
line-height: 16px;
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
.entry-header .author {
|
||||
color: #5A6b77;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
.entry-header .date {
|
||||
color: #66637A;
|
||||
color: rgba(102,99,122,.5);
|
||||
}
|
||||
|
||||
.entry-readmore {
|
||||
|
@ -1689,6 +1688,20 @@ input#algolia-doc-search:focus {
|
|||
text-align: left;
|
||||
}
|
||||
|
||||
.entry-excerpt {
|
||||
min-width: 320px;
|
||||
max-width: 640px;
|
||||
margin: 0 auto 40px;
|
||||
padding-bottom: 40px;
|
||||
border-bottom: 1px solid #EDEDED;
|
||||
}
|
||||
|
||||
.entry-body {
|
||||
min-width: 320px;
|
||||
max-width: 640px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
.small-title {
|
||||
font-size: 10px;
|
||||
color: #66637A;
|
||||
|
@ -1819,6 +1832,11 @@ article li {
|
|||
}
|
||||
}
|
||||
|
||||
#mc_embed_signup {
|
||||
clear:left;
|
||||
width:100%;
|
||||
}
|
||||
|
||||
/** Help **/
|
||||
.helpSection h2 {
|
||||
font-size: 24px;
|
||||
|
@ -1896,7 +1914,7 @@ footer .sitemap {
|
|||
display: flex;
|
||||
justify-content: space-between;
|
||||
max-width: 1080px;
|
||||
margin: 0 auto 3em;
|
||||
margin: 0 auto 1em;
|
||||
}
|
||||
footer .sitemap div {
|
||||
flex: 1;
|
||||
|
@ -1914,10 +1932,18 @@ footer .sitemap .nav-home:hover,
|
|||
footer .sitemap .nav-home:focus {
|
||||
opacity: 1.0;
|
||||
}
|
||||
@media screen and (max-width: 740px) {
|
||||
@media screen and (max-width: 768px) {
|
||||
footer .sitemap {
|
||||
display: none;
|
||||
}
|
||||
|
||||
footer .newsletter {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#mc_embed_signup {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
footer .sitemap a {
|
||||
|
@ -1964,3 +1990,15 @@ footer .copyright {
|
|||
color: rgba(255, 255, 255, 0.4);
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
footer .newsletter {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
max-width: 640px;
|
||||
margin: 0 auto 1em;
|
||||
}
|
||||
|
||||
footer .newsletter h5 {
|
||||
color: #05A5D1;
|
||||
margin: 0 0 10px;
|
||||
}
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
var Prism = require('Prism');
|
||||
var React = require('React');
|
||||
var Site = require('Site');
|
||||
var Hero = require('Hero');
|
||||
|
||||
var apps = [
|
||||
{
|
||||
|
@ -112,18 +113,11 @@ var index = React.createClass({
|
|||
render: function() {
|
||||
return (
|
||||
<Site>
|
||||
<div className="hero">
|
||||
<div className="wrap">
|
||||
<div className="text"><strong>React Native</strong></div>
|
||||
<div className="minitext">
|
||||
Learn once, write anywhere: Build mobile apps with React
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<Hero title="React Native" subtitle="Learn once, write anywhere: Build mobile apps with React">
|
||||
<div className="buttons-unit">
|
||||
<a href="docs/getting-started.html#content" className="button">Get started with React Native</a>
|
||||
</div>
|
||||
</div>
|
||||
</Hero>
|
||||
|
||||
<section className="content wrap">
|
||||
|
||||
|
|
Loading…
Reference in New Issue