ソースを参照

next track prev track

mfdok43 2 年 前
コミット
5ee62687e6

+ 38 - 6
src/App.scss

@@ -1,6 +1,9 @@
+$breakpoint-mobile: 720px;
+$breakpoint-tablet: 1540px;
+
 .App {
   height: auto;
-  text-align: center;
+ text-align: center;
   background: black;
 
 }
@@ -20,10 +23,19 @@ a:hover {
   text-decoration: none;
 }
 
-h2 {
+h3 {
   color: white;
+  @media(max-width: $breakpoint-tablet) {
+    font-size: 20px;
+  }
 }
 
+h2 {
+  color: white;
+  @media(max-width: $breakpoint-tablet) {
+    font-size: 20px;
+  }
+}
 
 button {
   color: white;
@@ -50,6 +62,10 @@ input {
 
 .logo-large {
   height: 600px;
+  @media (max-width: $breakpoint-tablet) {
+    height: 300px;
+    margin-left: -100px;
+  }
 }
 
 .Header {
@@ -63,10 +79,10 @@ input {
   box-shadow: 0.2em 0.2em 5px rgba(122, 122, 122, 0.376);
 
 
-  h2 {
+  h3 {
     margin-top: 30px;
   }
-  h2:hover {
+  h3:hover {
     color: lawngreen;
   }
 
@@ -86,11 +102,14 @@ main {
 }
 
 .Aside {
-  min-height: 1000px;
+  min-height: 900px;
   top: 114px;
-  //position: fixed;
+  position: fixed;
   width: 430px;
   background-color: red;
+  @media (max-width: $breakpoint-tablet) {
+    width: 320px;;
+  }
 }
 
 .Content {
@@ -202,3 +221,16 @@ footer {
      color: rgba(124, 252, 0, 0.76);
    }
 }
+
+.Users {
+  display: flex;
+  flex-wrap: wrap;
+  .user-beauty {
+
+  }
+
+}
+
+.hello-column {
+  display: flex;
+}

+ 5 - 3
src/pages/header/header-build.js

@@ -52,9 +52,11 @@ export const CChangePasswordForm = connect(null,{onChangePassword:actionSetUserP
 export const Header = () =>
     <header className="Header">
         <Logo />
-        <Link to={`/music`}><h2>Все песни</h2></Link>
-        <Link to={`/mymusic`}> <h2>Моя музыка</h2></Link>
-        <h2><CTrackSearch /></h2>
+        <Link to={`/music`}><h3>Все песни</h3></Link>
+        <Link to={`/myMusic`}> <h3>Моя музыка</h3></Link>
+        <h3><CTrackSearch /></h3>
+
+
         <Switch>
             <CProtectedRoute roles={["anon", "user"]} path="/login" component={CLoginForm}/>
             <CProtectedRoute roles={["anon", "user"]} path="/registration" component={CRegForm}/>

+ 8 - 8
src/pages/main.js

@@ -7,7 +7,7 @@ import {CMyPlaylists} from "./my-tracks";
 import {CProtectedRoute} from "../reducers";
 import {CSearchResult} from "./tools/search";
 import {HelloUserPage,MyPlaylistTracks} from "./my-tracks";
-import {UserPlaylistById} from "./user-tracks/user-playlists";
+import {CUserPlaylists} from "./user-tracks/user-playlists";
 import {UserPlaylistTracks} from "./user-tracks";
 
 export const Aside = ({children}) =>
@@ -24,11 +24,11 @@ export const Main = () =>
     <main>
         <Aside>
             <Switch>
-            <CProtectedRoute roles={["anon", "user"]} path="/music" component={CAllUsers}/>
-            <CProtectedRoute roles={["anon", "user"]} path="/user/:_id" component={CAllUsers}/>
-            <CProtectedRoute roles={["anon", "user"]} path="/mymusic" component={CMyPlaylists}/>
-            <CProtectedRoute roles={["anon", "user"]} path="/myplaylist/:_id" component={CMyPlaylists}/>
-            <CProtectedRoute roles={["anon", "user"]} path='/' component={CAllUsers} exact/>
+            {/*<CProtectedRoute roles={["anon", "user"]} path="/music" component={CAllUsers}/>*/}
+            <CProtectedRoute roles={["anon", "user"]} path="/user/:_id" component={CUserPlaylists}/>
+            <CProtectedRoute roles={["anon", "user"]} path="/userPlaylist/:_id" component={CUserPlaylists}/>
+            <CProtectedRoute roles={["anon", "user"]} path="/myMusic" component={CMyPlaylists}/>
+            <CProtectedRoute roles={["anon", "user"]} path="/myPlaylist/:_id" component={CMyPlaylists}/>
             </Switch>
         </Aside>
         <Content>
@@ -37,10 +37,10 @@ export const Main = () =>
                 <CProtectedRoute roles={["anon", "user"]} path="/search" component={CSearchResult}/>
                 <CProtectedRoute roles={["anon", "user"]} path="/myPlaylist/:_id" component={MyPlaylistTracks}/>
                 <CProtectedRoute roles={["anon", "user"]} path="/userPlaylist/:_id" component={UserPlaylistTracks}/>
-                <CProtectedRoute roles={["anon", "user"]} path="/user/:_id" component={UserPlaylistById}/>
+                <CProtectedRoute roles={["anon", "user"]} path="/user/:_id" component={HelloPage}/>
                 <CProtectedRoute roles={["anon", "user"]} path="/music" component={HelloPage}/>
                 <CProtectedRoute roles={["anon", "user"]} path='/' component={HelloPage} exact/>
-                <CProtectedRoute roles={["anon", "user"]} path='/mymusic' component={HelloUserPage}/>
+                <CProtectedRoute roles={["anon", "user"]} path='/myMusic' component={HelloUserPage}/>
             </Switch>
         </Content>
    </main>

+ 1 - 1
src/pages/my-tracks/hello-user-page.js

@@ -2,6 +2,6 @@ import {LogoLarge} from "../header";
 
 export const HelloUserPage = () =>
     <div>
-        <h2>Загрузите музыку в плейлисты и слушайте любимые композиции</h2>
+        <h3>Загрузите музыку в плейлисты и слушайте любимые композиции</h3>
         <LogoLarge/>
     </div>

+ 5 - 6
src/pages/my-tracks/my-playlists.js

@@ -5,22 +5,21 @@ import {actionCreatePlaylist, actionPlaylistFindByOwner} from "../../actions";
 import {store} from "../../reducers";
 
 const Playlist = ({playlist:{_id, name}={}}) =>
-    <li><Link to={`/myplaylist/${_id}`}>{name}</Link></li>
+    <li><Link to={`/myPlaylist/${_id}`}>{name}</Link></li>
 
-const MyPlaylists =  ({playlists={},onCreatePlaylist}) => {
+const MyPlaylists =  ({playlists={}}) => {
     const [p, setP] = useState ('')
     return (
         <div className='my-playlists'>
             <input placeholder='Название' onChange={e => setP(e.target.value)}/>
-            <button disabled={p.length >= 6  && p !== "" ? false : true} onClick={() => {onCreatePlaylist(p)}}>Создать плейлист</button>
-            <ul className='Users'>
+            <button disabled={p.length >= 6  && p !== "" ? false : true}>Создать плейлист</button>
+            <ul className='Playlists'>
                 {playlists.map((playlist,playlistIndex) =>  <Playlist key={`playlist-${playlistIndex}`} playlist={playlist}/> )}
             </ul>
         </div>
     )
 }
 
-export const CMyPlaylists = connect(state => ({playlists: state.promise.playlistFindByOwner?.payload || []}),
-    {onCreatePlaylist:actionCreatePlaylist})(MyPlaylists)
+export const CMyPlaylists = connect(state => ({playlists: state.promise.playlistFindByOwner?.payload || []}))(MyPlaylists)
 
 store.dispatch(actionPlaylistFindByOwner())

+ 2 - 4
src/pages/my-tracks/my-tracks.js

@@ -6,7 +6,6 @@ import {connect} from "react-redux";
 import {CTrack} from "../track";
 import {CPlaylistDropZone} from "../tools";
 import {CPreloaded} from "../preloader";
-import {actionSetPlaylist} from "../../reducers";
 
 
 const MyTracks = ({playlist={}}) => {
@@ -15,15 +14,14 @@ const MyTracks = ({playlist={}}) => {
         <div className='Category'>
             <h2>{name}</h2>
             <CPreloaded promiseName='playlistById'>
-                {(tracks || []).map((track,index) => <CTrack key={`item-${index}`} trackIndex={index} playlist={playlist} track={track}/>)}
+                {(tracks || []).map((track,index) => <CTrack trackIndex={index} playlist={playlist} track={track}/>)}
             </CPreloaded>
         </div>
     )
 }
 
 
-const CMyTracks = connect(state => ({playlist: state.promise.playlistById?.payload || []}),
-    {setPlaylist: actionSetPlaylist})(MyTracks)
+const CMyTracks = connect(state => ({playlist: state.promise.playlistById?.payload || []}),)(MyTracks)
 
 
 export const MyPlaylistTracks = ({match:{params:{_id}}}) =>

+ 7 - 5
src/pages/player.js

@@ -3,11 +3,11 @@ import pause from '../pause.svg'
 import next from '../next.svg'
 import prev from '../prev.svg'
 import {connect} from "react-redux";
-import {actionTrackPlay, actionTrackStop,actionTrackVolume,actionTrackCurrentTime} from "../reducers";
+import {actionTrackPlay, actionTrackStop,actionTrackVolume,actionTrackCurrentTime,actionNextTrack,actionPreviousTrack} from "../reducers";
 
 
 export const Player = ({player:{volume,duration,currentTime,isPlaying},
-                                trackPlay, trackStop,trackVolume,trackCurrentTime}) => {
+                                trackPlay, trackStop,trackVolume,trackCurrentTime,trackNext,trackPrevious}) => {
     return (
         <div className='Player'>
 
@@ -19,7 +19,7 @@ export const Player = ({player:{volume,duration,currentTime,isPlaying},
                 onChange={(e) => trackCurrentTime(e.target.value)}
                 value={currentTime}/>
 
-            <button><img src={prev}/></button>
+            <button onClick={() => trackPrevious()}><img src={prev}/></button>
             {!isPlaying ? (   <button onClick={() => trackPlay()}>
                 <img src={play}/></button>) : (     <button onClick={() => trackStop()}>
                 <img src={pause}/></button>)}
@@ -27,7 +27,7 @@ export const Player = ({player:{volume,duration,currentTime,isPlaying},
 
 
 
-            <button><img src={next}/></button>
+            <button onClick={()=>trackNext()}><img src={next}/></button>
             <input
                 type="range"
                 min={0}
@@ -43,4 +43,6 @@ export const CPlayer = connect(state => ({player: state.player}),
     {trackPlay: actionTrackPlay,
                      trackStop: actionTrackStop,
                      trackVolume:actionTrackVolume,
-                     trackCurrentTime:actionTrackCurrentTime})(Player)
+                     trackCurrentTime:actionTrackCurrentTime,
+                      trackNext:actionNextTrack,
+                      trackPrevious:actionPreviousTrack,})(Player)

+ 4 - 4
src/pages/track.js

@@ -4,10 +4,9 @@ import {actionTrackPlay,actionTrackStop,actionSetPlaylist} from "../reducers";
 import {connect} from "react-redux";
 
 
-export const Track = ({playlist,track:{_id,url,originalFileName},trackIndex,
-                          trackPlay,trackStop,setPlaylist}) => {
-    // let audioSrc = backURL + '/'+ url
-// console.log(playlist,'iz track')
+export const Track = ({playlist,track:{originalFileName},trackIndex,
+                          trackStop,setPlaylist}) => {
+
     return (
         <div className='Tracks'>
                 <button onClick={() => {
@@ -15,6 +14,7 @@ export const Track = ({playlist,track:{_id,url,originalFileName},trackIndex,
                 }}>
                     <img src={play} alt='play'/>
                 </button>
+
                 <button onClick={() => trackStop()}>
                     <img src={pause} alt='pause'/>
                 </button>

+ 8 - 5
src/pages/user-tracks/allUsers.js

@@ -7,17 +7,20 @@ import {store} from "../../reducers";
 
 
 const User = ({user:{_id, login}={}}) =>
-<li><Link to={`/user/${_id}`}>{login}</Link></li>
+<Link to={`/user/${_id}`}>
+    <div className="box-3">
+        <div className="btn btn-three">
+            <span>{login}</span>
+        </div>
+    </div>
+</Link>
 
 
 const AllUsers = ({users={}}) =>{
 
         return (
-            <div>
-                <h3>Плейлисты ползователя</h3>
-            <ul className='Users'>
+            <div className='Users'>
                     {users.map(user =>  <User key={Math.random()} user={user}/> )}
-            </ul>
             </div>
         )
 

+ 6 - 1
src/pages/user-tracks/hellopage.js

@@ -1,7 +1,12 @@
 import {LogoLarge} from "../header";
+import {CAllUsers} from "./allUsers";
+import './user-button.scss'
 
 export const HelloPage = () =>
     <div>
-        <h2>Слушайте музыку пользователей нашего сервиса</h2>
+        <h3>Слушайте музыку пользователей нашего сервиса</h3>
+        <div className='hello-column'>
         <LogoLarge />
+        <CAllUsers />
+        </div>
     </div>

+ 2 - 1
src/pages/user-tracks/index.js

@@ -1,4 +1,5 @@
 export {UserPlaylistTracks} from "./userTracks";
 export {CAllUsers} from "./allUsers";
 export {HelloPage} from "./hellopage";
-export {UserPlaylistById} from "./user-playlists";
+export {UserPlaylistById} from "./user-playlists";
+export {CUserPlaylists} from "./user-playlists";

+ 46 - 0
src/pages/user-tracks/user-button.scss

@@ -0,0 +1,46 @@
+$breakpoint-mobile: 720px;
+$breakpoint-tablet: 1640px;
+
+.btn-three {
+    margin: 5px;
+    font-size: 16px;
+    color: #FFF;
+    transition: all 0.5s;
+    position: relative;
+    @media (max-width: $breakpoint-tablet)  {
+        margin: 3px;
+        font-size: 12px;
+    }
+}
+.btn-three::before {
+    content: '';
+    position: absolute;
+    top: 0;
+    left: 0;
+    width: 100%;
+    height: 100%;
+    z-index: 1;
+    background-color: rgba(255,255,255,0.1);
+    transition: all 0.3s;
+}
+.btn-three:hover::before {
+    opacity: 0 ;
+    transform: scale(0.5,0.5);
+}
+.btn-three::after {
+    content: '';
+    position: absolute;
+    top: 0;
+    left: 0;
+    width: 100%;
+    height: 100%;
+    z-index: 1;
+    opacity: 0;
+    transition: all 0.3s;
+    border: 1px solid rgba(255,255,255,0.5);
+    transform: scale(1.2,1.2);
+}
+.btn-three:hover::after {
+    opacity: 1;
+    transform: scale(1,1);
+}

+ 6 - 3
src/pages/user-tracks/user-playlists.js

@@ -1,6 +1,8 @@
 import {connect} from "react-redux";
 import {CPlaylistDropZone} from "../tools";
 import {Link} from "react-router-dom";
+import {store} from "../../reducers";
+import {actionPlaylistFindByOwner} from "../../actions";
 
 const Playlist = ({playlist:{_id, name}={}}) =>
     <li><Link to={`/userPlaylist/${_id}`}>{name}</Link></li>
@@ -8,8 +10,8 @@ const Playlist = ({playlist:{_id, name}={}}) =>
 const UserPlaylists =  ({playlists={}}) => {
     return (
         <div className='my-playlists'>
-
-            <ul className='Users'>
+            <h2>Плейлиты пользователя</h2>
+            <ul className='Playlists'>
                 {playlists.map((playlist) =>  <Playlist playlist={playlist}/> )}
             </ul>
         </div>
@@ -23,4 +25,5 @@ export const CUserPlaylists = connect(state => ({playlists: state.promise.playli
 export const UserPlaylistById = ({match:{params:{_id}}}) =>
     <>
         <CUserPlaylists />
-    </>
+    </>
+

+ 3 - 4
src/pages/user-tracks/userTracks.js

@@ -16,19 +16,18 @@ const UserTracks = ({playlist={}}) => {
         <div className='Category'>
             <h2>{name}</h2>
             <CPreloaded promiseName='playlistById'>
-                {(tracks || []).map((track,index) => <CTrack key={`item-${index}`} trackIndex={index} playlist={playlist} track={track}/>)}
+                {(tracks || []).map((track,index) => <CTrack trackIndex={index} playlist={playlist} track={track}/>)}
             </CPreloaded>
         </div>
     )
 }
 
 
-const CUserTracks = connect(state => ({playlist: state.promise.playlistById?.payload || []}),
-    {setPlaylist: actionSetPlaylist})(UserTracks)
+const CUserTracks = connect(state => ({playlist: state.promise.playlistById?.payload || []}))(UserTracks)
 
 
 export const UserPlaylistTracks = ({match:{params:{_id}}}) =>
     <>
             <CUserTracks />
-
     </>
+

+ 2 - 1
src/reducers/index.js

@@ -2,7 +2,8 @@ export {store} from './store'
 export {actionPromise} from './promiseReducer'
 
 export {actionTrackPlay,actionTrackStop,actionSetPlaylist,actionTrackCurrentTime,actionTrackVolume,
-    trackPlayWatcher,trackStopWatcher,setPlaylistWatcher,trackVolumeWatcher,
+    trackPlayWatcher,trackStopWatcher,setPlaylistWatcher,trackVolumeWatcher, trackLoadWatcher,nextTrackWatcher,
+    actionNextTrack,previousTrackWatcher,actionPreviousTrack,
 } from "./playerReducer";
 
 export {actionAuthLogin, actionAuthLogout} from './authReducer'

+ 88 - 9
src/reducers/playerReducer.js

@@ -5,9 +5,34 @@ import {store} from "./store";
 
 export const playerReducer = (
     state = {},
-    {type,track,trackIndex,isPlaying=false,isPaused,duration,
+    {type,track,isPlaying=false,isPaused,duration,
         playlist,playlistIndex,currentTime=0,volume=1,}) => {
 
+    if (type === "NEXT_TRACK") {
+        return {
+            ...state,
+            playlistIndex,
+        }
+
+    }
+
+    if (type === "PREVIOUS_TRACK") {
+        return {
+            ...state,
+            playlistIndex,
+        }
+
+    }
+
+
+    if (type === "TRACK_LOAD") {
+        return {
+            ...state,
+            playlistIndex,
+        }
+
+    }
+
     if (type === "TRACK_PLAY") {
         return {
             ...state,
@@ -57,22 +82,39 @@ export const playerReducer = (
 
 
 const audio = new Audio()
+audio.onended = function(){actionNextTrack()}
 
+export const actionTrackLoad = (trackIndex) =>
+    ({type:'ACTION_TRACK_LOAD', trackIndex})
 
-export const actionTrackPlay = (trackIndex) =>
-    ({type:'ACTION_TRACK_PLAY', trackIndex})
-export function* trackPlayWorker (action) {
+export function* trackLoadWorker (action) {
     let {trackIndex} = action
     let {player:{playlist}} = yield select ()
     //  if (playlistIndex !== trackIndex) {
     audio.src = backURL + '/'+ playlist[trackIndex].url
     audio.load()
+    console.log(trackIndex)
     audio.ondurationchange = function(){actionSetDuration()}
     audio.ontimeupdate = function(){actionTrackCurrentTime()}
-    // }
+    yield put({type:"TRACK_LOAD",playlistIndex:trackIndex})
+    yield put (actionTrackPlay())
+
+}
+export function* trackLoadWatcher() {
+    yield takeEvery ('ACTION_TRACK_LOAD',trackLoadWorker)
+}
+
+
+
+
+
+
+export const actionTrackPlay = () =>
+    ({type:'ACTION_TRACK_PLAY'})
+export function* trackPlayWorker () {
     yield audio.play()
-    console.log(trackIndex,'uuuuu')
-    yield put({type:"TRACK_PLAY",isPlaying:true,isPaused:false,trackIndex})
+    yield put({type:"TRACK_PLAY",isPlaying:true,isPaused:false})
+    console.log('play')
 }
 export function* trackPlayWatcher() {
     yield takeEvery ('ACTION_TRACK_PLAY',trackPlayWorker)
@@ -80,6 +122,44 @@ export function* trackPlayWatcher() {
 
 
 
+export const actionNextTrack = () =>
+    ({type:'ACTION_NEXT_TRACK'})
+
+export function* nextTrackWorker () {
+    let {player} = yield select ()
+    let p = player.playlistIndex
+    yield put({type:"NEXT_TRACK",playlistIndex:p+1})
+    audio.src = backURL + '/'+ player.playlist[p+1].url
+    audio.load()
+    audio.ondurationchange = function(){actionSetDuration()}
+    audio.ontimeupdate = function(){actionTrackCurrentTime()}
+    audio.play()
+}
+export function* nextTrackWatcher() {
+    yield takeEvery ('ACTION_NEXT_TRACK',nextTrackWorker)
+}
+
+
+export const actionPreviousTrack = () =>
+    ({type:'ACTION_PREVIOUS_TRACK'})
+
+export function* previousTrackWorker () {
+    let {player} = yield select ()
+    let p = player.playlistIndex
+    yield put({type:"PREVIOUS_TRACK",playlistIndex:p-1})
+    audio.src = backURL + '/'+ player.playlist[p-1].url
+    audio.load()
+    audio.ondurationchange = function(){actionSetDuration()}
+    audio.ontimeupdate = function(){actionTrackCurrentTime()}
+    audio.play()
+}
+export function* previousTrackWatcher() {
+    yield takeEvery ('ACTION_PREVIOUS_TRACK',previousTrackWorker)
+}
+
+
+
+
 
 
 export const actionTrackStop = () =>
@@ -131,9 +211,8 @@ export const actionSetPlaylist = (playlist,trackIndex) =>
 
 export function* setPlaylistWorker(action) {
     let {playlist, trackIndex} = action
-    console.log (playlist,'trackplay')
     yield put ({type:"SET_PLAYLIST", playlist:playlist})
-    yield put (actionTrackPlay(trackIndex))
+    yield put (actionTrackLoad(trackIndex))
 }
 
 export function* setPlaylistWatcher() {

+ 5 - 1
src/reducers/store.js

@@ -8,7 +8,8 @@ import {findMyTracksWatcher,playlistFindByOwnerWatcher} from "../actions/find-ac
 import {setAvatarWatcher} from "../actions/set-avatar-actions";
 import {fullUploadPlaylistsWatcher,setTrackToPlaylistWatcher} from "../actions/my-playlist-tracks-actions";
 import {aboutMeWatcher,actionAboutMe} from "../actions/about-me-actions";
-import {trackPlayWatcher,trackStopWatcher,setPlaylistWatcher,trackVolumeWatcher,
+import {trackPlayWatcher,trackStopWatcher,setPlaylistWatcher,trackVolumeWatcher,trackLoadWatcher,
+    nextTrackWatcher,previousTrackWatcher,
 } from "./playerReducer";
 
 
@@ -47,6 +48,9 @@ function* rootSaga(){
          trackPlayWatcher(),
         trackStopWatcher(),
         trackVolumeWatcher(),
+        trackLoadWatcher(),
+        nextTrackWatcher(),
+        previousTrackWatcher(),
          // setUserPasswordWatcher(),
     ])
 }