[React]Twittler Intro

이정원·2022년 7월 15일
0

dummyData.js

const getRandomNumber = (min, max) => {
  return parseInt(Math.random() * (Number(max) - Number(min) + 2));
};

const getParsedDate = (createdAt) => {
  return new Date(createdAt).toLocaleDateString('ko-KR');
}

const dummyTweets = [
  {
    id: 1,
    username: 'kimcoding',
    picture: `https://randomuser.me/api/portraits/women/${getRandomNumber(
      1,
      98
    )}.jpg`,
    content:
      '모든 국민은 인간으로서의 존엄과 가치를 가지며, 행복을 추구할 권리를 가진다. 모든 국민은 종교의 자유를 가진다. 국가는 농·어민과 중소기업의 자조조직을 육성하여야 하며, 그 자율적 활동과 발전을 보장한다. 모든 국민은 양심의 자유를 가진다. 누구든지 체포 또는 구속을 당한 때에는 즉시 변호인의 조력을 받을 권리를 가진다.',
    createdAt: getParsedDate('2019-02-24T16:17:47.000Z'),
    updatedAt: getParsedDate('2019-02-24T16:17:47.000Z'),
  },
  {
    id: 2,
    username: 'parkhacker',
    picture: `https://randomuser.me/api/portraits/men/${getRandomNumber(
      1,
      98
    )}.jpg`,
    content:
      '형사피고인은 유죄의 판결이 확정될 때까지는 무죄로 추정된다. 모든 국민은 행위시의 법률에 의하여 범죄를 구성하지 아니하는 행위로 소추되지 아니하며, 동일한 범죄에 대하여 거듭 처벌받지 아니한다. 모든 국민은 행위시의 법률에 의하여 범죄를 구성하지 아니하는 행위로 소추되지 아니하며, 동일한 범죄에 대하여 거듭 처벌받지 아니한다. 모든 국민은 고문을 받지 아니하며, 형사상 자기에게 불리한 진술을 강요당하지 아니한다.',
    createdAt: getParsedDate('2019-02-25T16:17:47.000Z'),
    updatedAt: getParsedDate('2019-02-25T16:17:47.000Z'),
  },
  {
    id: 3,
    username: 'leedesign',
    picture: `https://randomuser.me/api/portraits/women/${getRandomNumber(
      1,
      98
    )}.jpg`,
    content:
      '모든 국민은 고문을 받지 아니하며, 형사상 자기에게 불리한 진술을 강요당하지 아니한다. 모든 국민은 양심의 자유를 가진다. 모든 국민은 사생활의 비밀과 자유를 침해받지 아니한다. 연소자의 근로는 특별한 보호를 받는다. 형사피고인이 스스로 변호인을 구할 수 없을 때에는 법률이 정하는 바에 의하여 국가가 변호인을 붙인다.',
    createdAt: getParsedDate('2019-02-26T16:17:47.000Z'),
    updatedAt: getParsedDate('2019-02-26T16:17:47.000Z'),
  },
  {
    id: 4,
    username: 'songfront',
    picture: `https://randomuser.me/api/portraits/men/${getRandomNumber(
      1,
      98
    )}.jpg`,
    content:
      '형사피고인은 상당한 이유가 없는 한 지체없이 공개재판을 받을 권리를 가진다. 공무원은 국민전체에 대한 봉사자이며, 국민에 대하여 책임을 진다. 모든 국민은 고문을 받지 아니하며, 형사상 자기에게 불리한 진술을 강요당하지 아니한다. 누구든지 체포 또는 구속을 당한 때에는 적부의 심사를 법원에 청구할 권리를 가진다. 대한민국의 경제질서는 개인과 기업의 경제상의 자유와 창의를 존중함을 기본으로 한다.',
    createdAt: getParsedDate('2019-02-27T16:17:47.000Z'),
    updatedAt: getParsedDate('2019-02-27T16:17:47.000Z'),
  },
  {
    id: 5,
    username: 'choiback',
    picture: `https://randomuser.me/api/portraits/women/${getRandomNumber(
      1,
      98
    )}.jpg`,
    content:
      '주거에 대한 압수나 수색을 할 때에는 검사의 신청에 의하여 법관이 발부한 영장을 제시하여야 한다. 대한민국은 국제평화의 유지에 노력하고 침략적 전쟁을 부인한다. 국가유공자·상이군경 및 전몰군경의 유가족은 법률이 정하는 바에 의하여 우선적으로 근로의 기회를 부여받는다. 여자의 근로는 특별한 보호를 받으며, 고용·임금 및 근로조건에 있어서 부당한 차별을 받지 아니한다. 모든 국민은 주거의 자유를 침해받지 아니한다.',
    createdAt: getParsedDate('2019-02-28T16:17:47.000Z'),
    updatedAt: getParsedDate('2019-02-28T16:17:47.000Z'),
  },
];


const dummyNotice = [
  {
    id: 1,
    content:
      'Elon Mask님이 트윗을 전송했습니다. : Don’t want to blow your mind, but I’m pretty weird. It’s time the world knew.',
    createdAt: '2019-02-24T16:17:51.000Z',
    updatedAt: '2019-02-24T16:17:51.000Z',
    username: 'Elon Mask',
  },
  {
    id: 2,
    content: 'Steve Jubs님이 Codestates님을 팔로우했습니다.',
    createdAt: '2019-02-24T16:17:51.000Z',
    updatedAt: '2019-02-24T16:17:51.000Z',
    username: 'Steve Jubs',
  },
  {
    id: 3,
    content:
      "Linkun Perk님이 트윗을 전송했습니다. : In the end, it doesn't even matter.",
    createdAt: '2019-02-24T16:17:51.000Z',
    updatedAt: '2019-02-24T16:17:51.000Z',
    username: 'Linkun Perk',
  },
  {
    id: 4,
    content:
      'Cute Cobain 님이 트윗을 전송했습니다. : Wanting to be someone else is a waste of the person you are.',
    createdAt: '2019-02-24T16:17:51.000Z',
    updatedAt: '2019-02-24T16:17:51.000Z',
    username: 'Cute Cobain',
  },
  {
    id: 5,
    content:
      'Ma Yun 님이 트윗을 전송했습니다. : Forget about your competitors, just focus on your customers.',
    createdAt: '2019-02-24T16:17:51.000Z',
    updatedAt: '2019-02-24T16:17:51.000Z',
    username: 'Ma Yun',
  },
];

export { dummyTweets, dummyNotice };

App.js

import React from 'react';
import './App.css';
import { dummyTweets } from './static/dummyData';

console.log(dummyTweets) 

const Sidebar = () => {
  return (
    <section className="sidebar">
    <script src="https://kit.fontawesome.com/14d687cae1.js" crossOrigin="anonymous">
    </script>
    <i className="far fa-comment-dots"></i>
    </section>
  );
};

const Counter = () => {
  return (
    <div className="tweetForm__input">
      <div className="tweetForm__inputWrapper">
        <div className="tweetForm__count" role="status">
          {'total: ' + dummyTweets.length}
        </div>
      </div>
    </div>
  );
};

const Footer = () => {
  return <div>
    <footer>Copyright @ 2022 Code States</footer>
  </div>;
};


const Tweets = () => {
  return (
    <ul className="tweets">
      {dummyTweets.map((tweet) => {
        return (
          <li className="tweet" key={tweet.id}>
            <div className="tweet__profile">
              <img src = {tweet.picture}></img>
            </div>
            <div className="tweet__content">
              <div className="tweet__userInfo">
                {tweet.username === "parkhacker" ? 
                <span className = "tweet__username tweet__username--purple">
                  {tweet.username}</span> : <span className = "tweet__username">{tweet.username}</span>}
                <span className = "tweet__createdAt">{tweet.createdAt}</span>
              </div>
              <div className = "tweet__message">{tweet.content}</div>
            </div>
          </li>
        );
      })}
    </ul>
  );
};

const Features = () => {
  return (
    <section className="features">
      <div className="tweetForm__container">
        <div className="tweetForm__wrapper">
          <div className="tweetForm__profile"></div>
          <Counter />
        </div>
      </div>
      <Tweets />
      <Footer />
    </section>
  );
};

const App = () => {
  return (
    <div className="App">
      <main>
        <Sidebar />
        <section className = "sidebar"></section>
        <Features />
      </main>
    </div>
  );
};


export { App, Sidebar, Counter, Tweets, Features, Footer };

index.js

import React from 'react';
import ReactDOM from 'react-dom';
import { App } from './App';

ReactDOM.render(<App />, document.getElementById('root'));

App.css

* {
  box-sizing: border-box;
  font-size: 16px;
  margin: 0;
  padding: 0;
}

:root {
  --main-border-color: rgb(235, 238, 240);
  --point-color: rgb(64, 0, 199);
  --point-color-tint: rgb(159, 127, 227);
  --point-color-tint-2: rgb(235, 229, 249);
  --default-text-color: rgb(0, 0, 0);
  --sub-text-color: rgb(91, 112, 131);
  --bold-text-color: rgb(15, 20, 25);
  --button-text-color: rgb(255, 255, 255);
  --shade-color: rgb(229, 229, 229);
  --sidebar-component-color: #ff577f;
  --count-component-color: #ffc764;
  --footer-component-color: #ff884b;
  --tweets-component-color: #cdfffc;
  --tweet-component-color: #007580;
}

body {
  display: flex;
  justify-content: center;
  min-height: 100vh;
}

button,
input,
optgroup,
select,
textarea {
  font-family: inherit; /* 1 */
  font-size: 100%; /* 1 */
  line-height: 1.15; /* 1 */
  margin: 0; /* 2 */
  border: 0;
}

button,
input {
  overflow: visible; /* 1 */
}

button {
  color: var(--button-text-color);
}

button:hover,
button:focus {
  background: var(--point-color);
}

button:focus {
  outline: 1px solid #fff;
  outline-offset: -4px;
}

button:active {
  transform: scale(0.99);
}

textarea {
  overflow: auto;
  resize: none;
}

.App {
  display: flex;
  flex-direction: column;
  min-height: 100%;
}

footer {
  flex: 0 0 1rem;
  padding: 0.3rem;
  text-align: right;
  border: 2px solid var(--footer-component-color);
}

main {
  display: flex;
  flex-direction: row;
  max-width: 640px;
  flex: 1 0 0;
}

.sidebar {
  display: flex;
  flex-direction: column;
  border: 2px solid var(--sidebar-component-color);
}

.far,
.fas {
  font-size: 2rem;
  color: var(--default-text-color);
  padding: 1.3rem;
  cursor: pointer;
}

.features {
  display: flex;
  flex-direction: column;
  border: 1px solid var(--main-border-color);
  flex: 1 0 0;
}

.tweetForm__container,
.notificationBar__container {
  border: 2px solid var(--count-component-color);
  margin-bottom: 0.5rem;
}

.tweetForm__wrapper,
.notificationBar__wrapper {
  display: flex;
  flex-direction: row;
  padding: 0.5rem 1rem;
}

.tweetForm__profile,
.notificationBar__icon {
  padding: 0.2rem;
  flex: 0 0 0;
}

.tweetForm__profile > img {
  display: inline-block;
  width: 50px;
  border-radius: 100%;
}

.tweetForm__input,
.notificationBar__message {
  display: flex;
  justify-content: center;
  align-content: center;
  flex-direction: column;
  flex: 1 0 0;
}

.tweetForm__inputWrapper {
  display: flex;
  margin: 0.5rem;
  flex: 0 0 4rem;
}

.tweetForm__textarea {
  flex: 1 0 0;
  border: 0;
}

.tweetForm__count {
  margin: 0.5rem;
  display: flex;
  justify-content: center;
  align-items: center;
}

.tweetForm__count__text {
  color: var(--sub-text-color);
}

.tweetForm__submit {
  display: flex;
  flex-direction: row;
  justify-content: space-between;
  flex: 1 0 0;
}

.tweetForm__submitIcons {
  flex: 1 0 0;
}

.tweetForm__submitButton {
  background-color: var(--point-color-tint);
  margin: 0.5rem;
  padding: 0.5rem 1rem;
  border-radius: 1rem;
}

.tweets,
.notifications {
  flex: 1 0 80vh;
  overflow-y: scroll;
  border: 2px solid var(--tweets-component-color);
}

.tweet,
.notification {
  display: flex;
  list-style: none;
  padding: 0.5rem 1rem;
  border: 2px solid var(--tweet-component-color);
}

.tweet:hover,
.notification:hover {
  background-color: var(--shade-color);
}

.tweet__profile,
.notification__sign {
  padding: 0.2rem;
}

.tweet__profile > img {
  display: inline-block;
  width: 50px;
  border-radius: 100%;
}

.notification__sign > .fas {
  display: initial;
  cursor: initial;
}

.tweet__content 
.notification__content {
  flex: 1 0 0;
}

.tweet__userInfo > .tweet__username {
  color: var(--bold-text-color);
  font-weight: 700;
  margin-left: 0.5rem;
}

.tweet__userInfo > .tweet__username.tweet__username--purple {
  background-color: var(--point-color-tint-2);
}

.tweet__userInfo > .tweet__createdAt {
  color: var(--sub-text-color);
  margin-left: 0.5rem;
}

.tweet__message {
  padding: 0.5rem;
}
.tweet__username--purple{
  background-color: rgb(235, 229, 249);
}
profile
Study.log

0개의 댓글