diff --git a/public/react/src/App.css b/public/react/src/App.css
index 50bccfb60..cb36f7d63 100644
--- a/public/react/src/App.css
+++ b/public/react/src/App.css
@@ -63,4 +63,14 @@ html, body {
   border-left: 1px solid rgb(221, 221, 221);
   /* 某些情况下,被cm盖住了 */
   z-index: 99;
+}
+
+
+
+/* antd扩展 */
+.formItemInline.ant-form-item {    
+  display: flex;
+}
+.formItemInline .ant-form-item-control-wrapper {
+  flex: 1;
 }
\ No newline at end of file
diff --git a/public/react/src/common/context/ThemeContext.js b/public/react/src/common/context/ThemeContext.js
index db639729e..2a922b58b 100644
--- a/public/react/src/common/context/ThemeContext.js
+++ b/public/react/src/common/context/ThemeContext.js
@@ -5,7 +5,8 @@ export const themes = {
     foreground: '#000000',
     background: '#eeeeee',
     foreground_select: '#4CACFF',
-    foreground_tip: '#333'
+    foreground_orange1: '#FF6800',
+    foreground_tip: '#333',
 
   },
   dark: {
diff --git a/public/react/src/modules/user/usersInfo/common/HeadlessModal.js b/public/react/src/modules/user/usersInfo/common/HeadlessModal.js
new file mode 100644
index 000000000..c58157722
--- /dev/null
+++ b/public/react/src/modules/user/usersInfo/common/HeadlessModal.js
@@ -0,0 +1,46 @@
+import React, { useState, useEffect, useContext, useRef, memo } from 'react';
+import {Link} from 'react-router-dom';
+
+import { getUrl2, isDev, ThemeContext } from 'educoder'
+import { Modal } from 'antd'
+
+
+function HeadlessModal (props) { 
+    // const [ visible, setVisible ] = useState(false)
+    const theme = useContext(ThemeContext);
+    const { category, visible, setVisible, className, width } = props;
+    
+    
+    useEffect(() => {
+
+    }, [])
+
+    return (
+        <Modal 
+            visible={visible}
+            className={`headless ${className}`}
+            title={null}
+            footer={null}
+            width={width}
+        >
+            <style>{`
+                .headless .ant-modal-close {
+                    display:none;
+                }
+                .headless .ant-modal-body {
+                    padding: 0px;
+                }
+                .headless .closeBtn {
+                    position: absolute;
+                    top: -15px;
+                    right: -9px;
+                    color: ${theme.foreground_select}
+                }
+            `}</style>
+            <i className="iconfont icon-htmal5icon19 closeBtn" onClick={ () => setVisible(false) }></i>
+            {props.children}
+        </Modal>
+    )
+}
+
+export default HeadlessModal
diff --git a/public/react/src/modules/user/usersInfo/common/InfoTab.js b/public/react/src/modules/user/usersInfo/common/InfoTab.js
new file mode 100644
index 000000000..615f84ea5
--- /dev/null
+++ b/public/react/src/modules/user/usersInfo/common/InfoTab.js
@@ -0,0 +1,32 @@
+import React, { useState, useEffect, useContext, useRef, memo } from 'react';
+import {Link} from 'react-router-dom';
+
+import { getUrl2, isDev, ThemeContext } from 'educoder'
+import axios from 'axios'
+
+
+function InfoTab (props) { 
+
+    const theme = useContext(ThemeContext);
+    const { category, changeCategory, categories } = props;
+    const username = props.match.params.username
+    
+    useEffect(() => {
+
+    }, [])
+
+    return (
+        <div className="white-panel edu-back-white pt25 pb25 clearfix ">
+          {categories && categories.map(item => {
+            return (
+              <li key={item.key} className={category == item.key ? "active" : ''}><a href="javascript:void(0)" onClick={()=>changeCategory(item.key)}>{item.name}</a></li>
+            )
+          })}
+          {/* <li className={category ? "" : "active"}><a href="javascript:void(0)" onClick={()=>this.changeCategory()}>全部</a></li>
+          <li className={category=="manage" ? "active" : ""}><a href="javascript:void(0)" onClick={()=>this.changeCategory("manage")}>{is_current ? "我":"TA"}管理的</a></li>
+          <li className={category=="study" ? "active" : ""}><a href="javascript:void(0)" onClick={()=>this.changeCategory("study")}>{is_current ? "我":"TA"}学习的</a></li> */}
+        </div>
+    )
+}
+
+export default InfoTab
diff --git a/public/react/src/modules/user/usersInfo/video/EditVideoModal.js b/public/react/src/modules/user/usersInfo/video/EditVideoModal.js
index 44d21d09c..01b0eb92d 100644
--- a/public/react/src/modules/user/usersInfo/video/EditVideoModal.js
+++ b/public/react/src/modules/user/usersInfo/video/EditVideoModal.js
@@ -6,10 +6,12 @@ import axios from 'axios'
 function EditVideoModal (props) {
     const modalEl = useRef(null);
     const theme = useContext(ThemeContext);
-    const { history, id, cover_url, title, created_at, isReview, onEditVideo, visible, setVisible,
-            form } = props;
+    const { history, videoId, cover_url, title, created_at, isReview, onEditVideo, visible, setVisible,
+            form, editSuccess } = props;
     const getFieldDecorator = form.getFieldDecorator
     const username = props.match.params.username
+    const _title = form.getFieldsValue().title;
+
     function toList() {
         history.push(`/users/${username}/videoes`)
     }
@@ -20,8 +22,17 @@ function EditVideoModal (props) {
         form.validateFieldsAndScroll((err, values) => {
             
             if (!err) {
-                
-            
+                const url = `/users/${username}/videos/${videoId}.json`
+                axios.put(url, {
+                    title: _title
+                }).then((response) => {
+                    if (response.data) {
+                        onCancel()
+                        editSuccess()
+                    }
+                }).catch((e) => {
+
+                })
             } else {
                 // $("html").animate({ scrollTop: $('html').scrollTop() - 100 })
             }
@@ -36,7 +47,11 @@ function EditVideoModal (props) {
     useEffect(() => {
         modalEl.current.setVisible(visible)
     }, [visible])
-    const _title = form.getFieldsValue().title;
+    useEffect(() => {
+        visible && form.setFieldsValue({
+            title,
+        })
+    }, [visible])
     return (
         <ModalWrapper 
             ref={modalEl}
@@ -49,7 +64,7 @@ function EditVideoModal (props) {
         >
             <Form.Item
                 label="视频标题"
-                className="title "
+                className="title formItemInline"
             >
                 
                 {getFieldDecorator('title', {
diff --git a/public/react/src/modules/user/usersInfo/video/InfosVideo.js b/public/react/src/modules/user/usersInfo/video/InfosVideo.js
index ac20d86ff..262d127f4 100644
--- a/public/react/src/modules/user/usersInfo/video/InfosVideo.js
+++ b/public/react/src/modules/user/usersInfo/video/InfosVideo.js
@@ -1,11 +1,13 @@
 import React, { useState, useEffect, useContext, useRef, memo } from 'react';
 import {Link} from 'react-router-dom';
-
+import { Pagination } from 'antd'
 import { getUrl2, isDev, ThemeContext } from 'educoder'
 import axios from 'axios'
 import VideoInReviewItem from './VideoInReviewItem'
 import EditVideoModal from './EditVideoModal'
 import './InfosVideo.css'
+import InfoTab from '../common/InfoTab'
+import HeadlessModal from '../common/HeadlessModal'
 
 function useModal(initValue) {
     const [visible, setVisible] = useState(initValue)
@@ -15,30 +17,59 @@ function useModal(initValue) {
         setVisible
     }
 }
+function useCategory(initValue) {
+    const [category, setCategory] = useState(initValue)
+    function changeCategory(key) {
+        setCategory(key)
+    }
+    return {
+        category,
+        changeCategory
+    }
+}
+function usePagination() {
+    const [page, setPage] = useState(1)
+    function onPageChange(page) {
+        setPage(page)
+    }
+    return {
+        current: page,
+        onChange: onPageChange
+    }
+}
+const PAGE_SIZE = 3
+let videoId = {};
 
-const PAGE_SIZE = 12
 function InfoVideo (props) {
     const [videoes, setVideoes] = useState([])
     const [reviewVideoes, setReviewVideoes] = useState([])
+    const [count, setCount] = useState(0)
     const editModalObj = useModal(false)
+    const videoModalObj = useModal(false)
+    const categoryObj = useCategory('all')
+    const pageObj = usePagination()
 
     const theme = useContext(ThemeContext);
     const editModalEl = useRef(null);
+    const videoEl = useRef(null);
 
 
     const username = props.match.params.username
-    let cVideo = {};
 
     function fetchVideoes() {
         const fetchUrl = `/users/${username}/videos.json`
         axios.get(fetchUrl, { 
             params: {
-                per_page: PAGE_SIZE
+                page: pageObj.current,
+                per_page: PAGE_SIZE,
+                // sort_by
+                // sort_direction
             }
         })
         .then((response) => {
             if (response.data.videos) {
                 setVideoes(response.data.videos)
+                setCount(response.data.count)
             }
         }).catch(() => {
 
@@ -62,20 +93,68 @@ function InfoVideo (props) {
     
     useEffect(() => {
         fetchVideoes()
-        fetchReviewVideoes()
-    }, [])
+    }, [pageObj.current])
 
-    function onEditVideo(video) {
-        cVideo = video
+    useEffect(() => {
+        if (categoryObj.category == 'all') {
+            fetchVideoes()
+        } else {
+            fetchReviewVideoes()
+        }
+    }, [categoryObj.category])
+
+    useEffect(() => {
+        if (videoModalObj.visible == false) {
+            // 关闭视频
+            videoEl.current && videoEl.current.pause()
+        } else {
+        }
+    }, [videoModalObj.visible])
+
+    function editSuccess() {
+        fetchVideoes()
+    }
+    
+    function onEditVideo(item) {
+        videoId = { 
+            videoId: item.id,
+            title: item.title
+        }
         editModalObj.setVisible(true)
         // editModalEl.current.toList(true, video);
         // this.refs['editVideoModal'].setVisible(true, video);
     }
-
+    function onMaskClick(item) {
+        videoId = { 
+            videoId: item.id,
+            title: item.title,
+            file_url: item.file_url
+        }
+        videoModalObj.setVisible(true)
+    }
     return (
         <div className="educontent infoVideo">
-            <EditVideoModal ref={editModalEl} {...props} {...cVideo} {...editModalObj}></EditVideoModal>
+            <EditVideoModal {...props} {...editModalObj}
+                editSuccess={editSuccess}
+                {...videoId}
+            ></EditVideoModal>
+            
+            <HeadlessModal
+                {...videoModalObj}
+                className="showVideoModal"
+                width={800 - 1}
+            >
+                <video 
+                    ref="videoEl"
+                    src={videoId.file_url} controls="true" controlslist="nodownload">
+                    您的浏览器不支持 video 标签。
+                </video>
+            </HeadlessModal>
             <style>{`
+                .showVideoModal video{
+                    width: 800px;
+                    height: 450px;
+                }
                 
                 /* item */
                 .videoPublishSuccess .section {
@@ -96,33 +175,69 @@ function InfoVideo (props) {
                     }
             `}</style>
 
+            <InfoTab
+                {...props}
+                categories={[{
+                    key: 'all',
+                    name: '全部视频'
+                }, {
+                    key: 'review',
+                    name: '待审核视频'
+                }]}
+                {...categoryObj}
+            ></InfoTab>
+
+            <div className="toolbarRow mt20">
+                <span>
+                    共
+                    <span style={{color: theme.foreground_orange1}}> {count} </span>
+                    个视频
+                </span>
 
-            <div className="itemWrap">
-                {reviewVideoes.map((item, index) => {
+                
+            </div>
+
+            {categoryObj.category == 'all' ?
+             <div className="itemWrap">
+                {videoes.map((item, index) => {
                     return (<VideoInReviewItem
                         {...props}
 
                         {...item}
                         key={item.id}
-                        isReview={true}
+                        onEditVideo={onEditVideo}
+                        onMaskClick={onMaskClick}
+                        
                     >
                     </VideoInReviewItem>)
                 })}
             </div>
-
-            gogogo
+            :
             <div className="itemWrap">
-                {videoes.map((item, index) => {
+                {reviewVideoes.map((item, index) => {
                     return (<VideoInReviewItem
                         {...props}
 
                         {...item}
                         key={item.id}
-                        onEditVideo={onEditVideo}
+                        isReview={true}
                     >
                     </VideoInReviewItem>)
                 })}
             </div>
+            }
+
+            
+
+            {
+                categoryObj.category == 'all' && count > PAGE_SIZE && 
+                <div className="mt30 mb50 edu-txt-center">
+                    <Pagination showQuickJumper total={count} pageSize={PAGE_SIZE} 
+                        {...pageObj}
+                    />
+                </div>
+            }
+           
             <Link to={`/users/${username}/videoes/upload`}>to upload</Link>
         </div>
     )
diff --git a/public/react/src/modules/user/usersInfo/video/VideoInReviewItem.js b/public/react/src/modules/user/usersInfo/video/VideoInReviewItem.js
index 7c2af5070..27035c341 100644
--- a/public/react/src/modules/user/usersInfo/video/VideoInReviewItem.js
+++ b/public/react/src/modules/user/usersInfo/video/VideoInReviewItem.js
@@ -16,7 +16,8 @@ updated_at: "2019-08-12 17:17:09"
  */
 function VideoInReviewItem (props) {
     const theme = useContext(ThemeContext);
-    const { history, cover_url, title, created_at, isReview, onEditVideo } = props;
+    const { history, cover_url, title, created_at, isReview
+        , onEditVideo, onMaskClick } = props;
     
     const username = props.match.params.username
     function toList() {
@@ -30,7 +31,7 @@ function VideoInReviewItem (props) {
             
             <img className="cover" src={cover_url || "http://video.educoder.net/e7d18970482a46d2a6f0e951b504256c/snapshots/491e113950d74f1dab276097dae287dd-00005.jpg"}
             ></img>
-            {!isReview && <div className="mask">
+            {!isReview && <div className="mask" onClick={() => onMaskClick(props)}>
                 <img className="play" src={playIcon}></img>
             </div>}
             <div className="square-main">