From 733343545f2be35f192011f2741dc8c41948cac8 Mon Sep 17 00:00:00 2001 From: Vitaly Takmazov Date: Sat, 9 Jun 2018 15:50:47 +0300 Subject: many updates --- vnext/src/app.js | 62 ---------------------------- vnext/src/components/Discover.js | 35 +++++++--------- vnext/src/components/Icon.js | 41 +++++++++++++++++++ vnext/src/components/LoginButton.js | 18 +++++---- vnext/src/components/Message.js | 20 ++++----- vnext/src/components/Post.js | 33 +++++++-------- vnext/src/components/Thread.js | 10 ++--- vnext/src/index.js | 70 ++++++++++++++++++++++++++++++++ vnext/src/style/main.css | 81 +++++++++++++++++++++++++------------ vnext/src/views/index.html | 5 ++- 10 files changed, 228 insertions(+), 147 deletions(-) delete mode 100644 vnext/src/app.js create mode 100644 vnext/src/components/Icon.js create mode 100644 vnext/src/index.js (limited to 'vnext/src') diff --git a/vnext/src/app.js b/vnext/src/app.js deleted file mode 100644 index 1f323b51..00000000 --- a/vnext/src/app.js +++ /dev/null @@ -1,62 +0,0 @@ -import React from "react" -import ReactDOM from "react-dom" -import { BrowserRouter as Router, Route, Link } from "react-router-dom" - -import Discover from "./components/Discover" -import Post from "./components/Post" -import Thread from "./components/Thread" -import LoginButton from "./components/LoginButton" - -class App extends React.Component { - constructor(props) { - super(props); - this.state = { - visitor: { uid: 0 } - } - } - render() { - return ( - -
-
-
- - - -
-
- - - -
-
- ) - } - auth(data) { - console.log(data) - } -} - - -ReactDOM.render(, document.getElementById("wrapper")); diff --git a/vnext/src/components/Discover.js b/vnext/src/components/Discover.js index 7fde3d88..63a0cad0 100644 --- a/vnext/src/components/Discover.js +++ b/vnext/src/components/Discover.js @@ -1,30 +1,25 @@ -import "whatwg-fetch" -import React from "react" -import PropTypes from "prop-types" -import queryString from "query-string" +import 'whatwg-fetch'; +import React from 'react'; +import PropTypes from 'prop-types'; +import queryString from 'query-string'; -import Message from "./Message" +import Message from './Message'; export default class Discover extends React.Component { constructor(props) { - super(props) + super(props); this.state = { msgs: [], loading: false, search: this.props.location.search - } + }; this.loadMessages = this.loadMessages.bind(this); } componentDidMount() { this.loadMessages(); } - componentWillReceiveProps(props) { - if (props.params != this.props.params) { - this.loadMessages(); - } - } loadMessages() { - const url = "https://api.juick.com/messages" + this.state.search; + const url = 'https://api.juick.com/messages' + this.state.search; fetch(url) .then(response => { return response.json() @@ -32,20 +27,20 @@ export default class Discover extends React.Component { .then(data => this.setState({ msgs: data }) ).catch(ex => { - console.log(ex) + console.log(ex); }); } - render() { + render() { var nodes = this.state.msgs.map(msg => { - return () - }); + return (); + }); return (
{nodes}
- ) + ); } -}; +} Discover.propTypes = { msgs: PropTypes.array -} +}; diff --git a/vnext/src/components/Icon.js b/vnext/src/components/Icon.js new file mode 100644 index 00000000..b4e8804c --- /dev/null +++ b/vnext/src/components/Icon.js @@ -0,0 +1,41 @@ +import React from 'react'; +import PropTypes from 'prop-types'; + +export default class Icon extends React.Component { + constructor(props) { + super(props); + } + + render() { + var size = this.props.size ? ' icon--' + this.props.size : ''; + var className = this.props.className ? ' ' + this.props.className : ''; + var klass = 'icon icon--' + this.props.name + size + className; + + var name = '#' + this.props.name + '-icon'; + var useTag = ''; + var Icon = React.createElement('svg', { className: 'icon__cnt', dangerouslySetInnerHTML: { __html: useTag } }); + return React.createElement( + 'div', + { className: klass }, + this.wrapSpinner(Icon, klass) + ); + } + + wrapSpinner(Html, klass) { + if (klass.indexOf('spinner') > -1) { + return React.createElement( + 'div', + { className: 'icon__spinner' }, + Html + ); + } else { + return Html; + } + } +} + +Icon.propTypes = { + size: PropTypes.string.isRequired, + name: PropTypes.string.isRequired, + className: PropTypes.string +} diff --git a/vnext/src/components/LoginButton.js b/vnext/src/components/LoginButton.js index 8d298fa2..f35a932d 100644 --- a/vnext/src/components/LoginButton.js +++ b/vnext/src/components/LoginButton.js @@ -1,27 +1,29 @@ -import React from 'react' -import PropTypes from 'prop-types' +import React from 'react'; +import PropTypes from 'prop-types'; +import Icon from './Icon'; + export default class LoginButton extends React.Component { constructor(props) { super(props); - window.addEventListener("message", (event) => { + window.addEventListener('message', (event) => { this.props.onAuth(event.data); }, false); } login(event) { event.preventDefault(); - let loginWindow = window.open("https://juick.com/login?redirect=false", "Login to Juick", "width=400,height=300,resizeable=no,menubar=no,toolbar=no,scrollbars=no"); + let loginWindow = window.open('https://juick.com/login?redirect=false', 'Login to Juick', 'width=400,height=300,resizeable=no,menubar=no,toolbar=no,scrollbars=no'); loginWindow.window.focus(); } render() { return ( - {this.props.title} - ) + {this.props.title} + ); } -}; +} LoginButton.propTypes = { title: PropTypes.string.isRequired, onAuth: PropTypes.func.isRequired -} \ No newline at end of file +}; diff --git a/vnext/src/components/Message.js b/vnext/src/components/Message.js index ba853f5c..d3148141 100644 --- a/vnext/src/components/Message.js +++ b/vnext/src/components/Message.js @@ -1,9 +1,9 @@ -import React from 'react' -import PropTypes from 'prop-types' -import ReactMarkdown from 'react-markdown' +import React from 'react'; +import PropTypes from 'prop-types'; +import ReactMarkdown from 'react-markdown'; export default class Message extends React.Component { - render() { + render() { const msg = this.props.data; return (
@@ -27,21 +27,22 @@ export default class Message extends React.Component { - { msg.photo && + { msg.photo &&

}
- )} -}; + ); + } +} function Tags(props) { return props.data && props.data.map(tag => { return ({ tag }) }) } Message.propTypes = { - msg: PropTypes.shape({ + data: PropTypes.shape({ mid: PropTypes.number.isRequired, user: PropTypes.shape({ uid: PropTypes.number.isRequired, @@ -50,4 +51,5 @@ Message.propTypes = { timestamp: PropTypes.string.isRequired, body: PropTypes.string }) -} +}; + diff --git a/vnext/src/components/Post.js b/vnext/src/components/Post.js index 54be77df..3256bbf6 100644 --- a/vnext/src/components/Post.js +++ b/vnext/src/components/Post.js @@ -1,20 +1,21 @@ -import React from 'react' +import React from 'react'; export default class Post extends React.Component { - render() { + render() { return (
-
-

- Фото: - (JPG/PNG) -

-

- -
- -

-
-
- )} -}; \ No newline at end of file +
+

+ Фото: + (JPG/PNG) +

+

+ +
+ +

+
+ + ); + } +} diff --git a/vnext/src/components/Thread.js b/vnext/src/components/Thread.js index 49d9ea4d..a17a2022 100644 --- a/vnext/src/components/Thread.js +++ b/vnext/src/components/Thread.js @@ -1,5 +1,5 @@ -import "whatwg-fetch" -import React from "react" +import 'whatwg-fetch'; +import React from 'react'; export default class Thread extends React.Component { constructor(props) { @@ -7,7 +7,7 @@ export default class Thread extends React.Component { this.state = { replies: [], loading: false - } + }; } componentDidMount() { } @@ -18,6 +18,6 @@ export default class Thread extends React.Component {

{user}

{mid}

- ) + ); } -} \ No newline at end of file +} diff --git a/vnext/src/index.js b/vnext/src/index.js new file mode 100644 index 00000000..97431188 --- /dev/null +++ b/vnext/src/index.js @@ -0,0 +1,70 @@ +import React from 'react'; +import ReactDOM from 'react-dom'; +import { BrowserRouter as Router, Route, Link } from 'react-router-dom'; +import Icon from './components/Icon'; +import Discover from './components/Discover'; +import Post from './components/Post'; +import Thread from './components/Thread'; +import LoginButton from './components/LoginButton'; + +class App extends React.Component { + constructor(props) { + super(props); + this.state = { + visitor: { uid: 0 } + }; + } + render() { + return ( + +
+
+
+ {this.state.visitor.uid > 0 ? + + : + + } + + +
+
+ + + +
+
+ ) + } + auth(data) { + console.log(data) + } +} + + +ReactDOM.render(, document.getElementById('wrapper')); diff --git a/vnext/src/style/main.css b/vnext/src/style/main.css index 24108030..69c29f07 100644 --- a/vnext/src/style/main.css +++ b/vnext/src/style/main.css @@ -85,6 +85,11 @@ html { margin: 12px 0 0 0; width: 728px; } +#minimal_content { + margin: 0 auto; + min-width: 310px; + width: auto; +} body > header { box-shadow: 0 0 3px rgba(0, 0, 0, 0.28); background: #fff; @@ -92,11 +97,26 @@ body > header { top: 0; width: 100%; z-index: 10; + -webkit-transition-duration: 0.5s; + transition-duration: 0.5s; + -webkit-transition-timing-function: cubic-bezier(0.215, 0.61, 0.355, 1); + transition-timing-function: cubic-bezier(0.215, 0.61, 0.355, 1); + -webkit-transition-property: -webkit-transform; + transition-property: transform; } #header_wrapper { margin: 0 auto; width: 1000px; display: flex; + justify-content: space-between; + align-items: center; + flex-wrap: wrap; + padding: 4px; +} +.header--hidden { + -webkit-transform: translateY(-100%); + -ms-transform: translateY(-100%); + transform: translateY(-100%); } #footer { clear: both; @@ -142,7 +162,6 @@ body > header { #logo { height: 36px; - margin: 7px 25px 0 20px; width: 110px; } #logo a { @@ -157,7 +176,6 @@ body > header { width: 110px; } #global { - flex-grow: 1; display: flex; } #global a { @@ -169,31 +187,24 @@ body > header { #global li { display: inline-block; } +#ctitle a { + padding: 14px; +} #global li:hover, +#ctitle a:hover, .l a:hover { background-color: #fff; box-shadow: 0 0 3px rgba(0, 0, 0, 0.16); cursor: pointer; transition: box-shadow 0.2s ease-in; } -#search { - margin: 12px 20px 12px 0; -} #search input { background: #FFF; - border: 1px solid #DDDDD5; + border: 1px solid #ccc; outline: none !important; padding: 4px; -} -@media screen and (max-width: 850px) { - #logo { - display: none; - } - #search { - display: inline-block; - float: none; - margin: 10px 10px; - } + -webkit-appearance: none; + border-radius: 0; } /* #endregion */ @@ -262,10 +273,12 @@ body > header { /* #endregion */ /* #region main content */ - #content > p, #content > h1, -#content > h2 { +#content > h2, +#minimal_content > p, +#minimal_content > h1, +#minimal_content > h2 { margin: 1em 0; } .page { @@ -331,10 +344,11 @@ article .tags { margin-top: 3px; } .msg-tags { - margin-top: 5px; - min-height: 30px; + margin-top: 12px; + min-height: 1px; } article .tags > a, +.badge, .msg-tags > a { background: #eee; border: 1px solid #eee; @@ -382,7 +396,6 @@ article .tags > a, border-right: 5px solid #0C0; } .msg-ts { - float: right; font-size: small; vertical-align: top; } @@ -478,6 +491,16 @@ article .tags > a, } @media screen and (max-width: 850px) { + #header_wrapper { + width: auto; + } + #global { + justify-content: space-around; + flex-grow: 1; + } + #search { + padding: 4px; + } article { overflow: auto; } @@ -509,12 +532,18 @@ article .tags > a, } @media screen and (max-width: 480px) { - .msg-ts { - float: none; + #wrapper { + margin-top: 104px; + } + #search { + display: none; + } + #global a { + padding: 14px 2px; } - .msg-tags { - margin-top: 10px; - min-height: 1px; + .msg-cont > nav.l, + article > nav.l { + font-size: 9pt; } .msg-txt { padding-top: 5px; diff --git a/vnext/src/views/index.html b/vnext/src/views/index.html index 661634d6..74583a13 100644 --- a/vnext/src/views/index.html +++ b/vnext/src/views/index.html @@ -13,6 +13,9 @@ + + + @@ -40,6 +43,6 @@
- + -- cgit v1.2.3