Commit 5a8ff13b by talequale

merge

parents 7de55a5e dbe6dd03
const Action = function(fn) {
this.fn = fn;
};
Action.prototype = {
execute: function() {
this.fn.apply(this, arguments);
}
};
const ACTION = {
CARD: {
LEARN_MORE: new Action((item)=>{
store.set({
'navigation.current': 'InfoPage',
'navigation.data': item
});
})
},
Action
};
export default ACTION
export {ACTION};
......@@ -30,8 +30,8 @@ store.sub(['navigation.current', 'loaded.cards'], async function(page, loaded) {
});
tmpStore.sub([
'isMobile', 'navigation.current'
], (is, page)=>{
if(!is && page === 'Profile')
'isMobile', 'navigation.current', 'loaded'
], (is, page, loaded)=>{
if(!is && page === 'Profile' && loaded)
store.set('navigation.current', 'Account');
});
\ No newline at end of file
......@@ -27,6 +27,15 @@ Observable.prototype = {
const listener = listeners[ i ];
listener.apply(this, [].slice.call(arguments, 1));
}
},
once: function(k, v) {
var _self = this,
wrap = function() {
v.apply(this, arguments);
_self.un(k, wrap)
};
this.on(k, wrap);
}
};
typeof module === 'object' && (module.exports = Observable);
\ No newline at end of file
......@@ -168,7 +168,13 @@ Store.prototype = {
valEqual: function(key, val) {
const me = this;
return function backwardCallback(update) {
me.equal(key, val, compareResult => update(compareResult));
me.equal(key, val, compareResult => {update(compareResult)});
}
},
valEqualOnly: function(key, val) {
const me = this;
return function backwardCallback(update) {
me.equal(key, val, compareResult => {compareResult && update(compareResult)});
}
},
valTrue: function(key) {
......
......@@ -203,7 +203,7 @@ const Consts = {
MONTH_YEAR: "LLLL yyyy",
DAY_MONTH: "dd.MM",
},
}
};
Consts.LOCAL_STORAGE.TOKEN.GET_TOKEN = (token) => `Bearer ${token}`
......@@ -219,4 +219,6 @@ for(let key in Consts.API.ENDPOINTS){
}
export default Consts
export const API = Consts.API;
const API = Consts.API;
export {API};
export {Consts};
......@@ -16,7 +16,12 @@ export default function() {
let dom = <div renderTo={document.body} cls="page-content">
<view.block.Header/>
{Switch({cls: 'page-content__inner', key: 'navigation.current'},
{Switch({
cls: 'page-content__inner',
key: 'navigation.current',
beforeSwitch: (val, old)=>{tmpStore.set('beforeNavigation', {from:old, to: val});},
afterSwitch: (val, old)=>{tmpStore.set('afterNavigation', {from:old, to: val});}
},
Object.keys(Page).reduce((store, pageName)=>{
store[pageName] = new Page[pageName]();
return store;
......
......@@ -81,3 +81,8 @@ const tmpStore = new Store({
width: window.innerWidth
});
let lastNav = null;
store.sub('navigation.current', function(val) {
console.log('APP:navigation', lastNav,'→', val);
lastNav = val;
});
\ No newline at end of file
......@@ -2,8 +2,10 @@ import './card.scss';
import Eye from '/svg/eye.svg';
import Button from "../button/Button";
import Format from "../format/Format";
import ACTION from "../../../controller/Action";
const noFn = ()=>{};
const Card = D.declare('view.cmp.Card', (cfg) => {
const action = cfg.action || noFn;
return <div className={D.cls('card card--'+
(cfg.disabled?'disabled':
cfg.seen?'seen':cfg.type))}>
......@@ -19,7 +21,7 @@ const Card = D.declare('view.cmp.Card', (cfg) => {
<Eye width="20" height="13"/>
</div>
:
<Button class={"button card__button"} onclick={cfg.onclick}>
<Button class={"button card__button"} onclick={()=>cfg.action(ACTION.CARD.LEARN_MORE)}>
<span>Изучить</span>
</Button>
)
......
......@@ -3,7 +3,11 @@ import ArrPrev from '/svg/arrow_active.svg';
import ArrNext from '/svg/arrow_active-back.svg';
import './CardSlider.scss';
const CardSlider = D.declare('view.cmp.CardSlider', (cfg) => {
const CardSlider = (function(){
const Slider = function(cfg){
this.cfg = cfg;
this.name = this.cfg.name || (Math.random()+'').substr(2);
let itemClick = cfg.itemClick || (()=>{});
let current = [],
hash = {},
items = [],
......@@ -15,14 +19,17 @@ const CardSlider = D.declare('view.cmp.CardSlider', (cfg) => {
fullCardsCount,
padding,
updateSize = function () {
if(dom.clientWidth){
width = dom.clientWidth - paddingLeft - paddingRight;
fullCardsCount = width / (cardWidth + minPadding) | 0;
padding = mobile ? mobilePadding: (width - fullCardsCount * cardWidth) / (fullCardsCount - 1);
wrap.style.width = (items.length * (padding + cardWidth) - padding) + 'px';
fullCardsCount = width / ( cardWidth + minPadding ) | 0;
padding = mobile ? mobilePadding : ( width - fullCardsCount * cardWidth ) / ( fullCardsCount - 1 );
wrap.style.width = ( items.length * ( padding + cardWidth ) - padding ) + 'px';
return true;
}
return false;
},
update = function () {
updateSize();
updateVisibleDom();
updateSize() && updateVisibleDom();
};
let paddingLeft = 30, paddingRight = 30, mobile = false;
......@@ -132,7 +139,7 @@ const CardSlider = D.declare('view.cmp.CardSlider', (cfg) => {
aria-label="Показать следующую карточку">
<ArrNext width="14" height="12"/>
</button>
{dom = <div class='card-slider__scroller'>
{dom = this.scroller = <div class='card-slider__scroller'>
{wrap = <div class='card-slider__wrapper'>{' '}</div>}
</div>}
</div>;
......@@ -159,6 +166,7 @@ const CardSlider = D.declare('view.cmp.CardSlider', (cfg) => {
seen={n % 4 === 0}
title={item.name}
image={item.image}
action={action => itemClick(item, action)}
/>
</div>
})(items[i], i),
......@@ -195,7 +203,7 @@ const CardSlider = D.declare('view.cmp.CardSlider', (cfg) => {
updateButtonsState();
};
dom.addEventListener('scroll', Store.debounce(function () {
dom.addEventListener('scroll', Store.debounce(function (e) {
requestAnimationFrame(updateVisibleDom);
waitUntilDoNotTouchScroll();
}, 1000 / 60));
......@@ -219,9 +227,19 @@ const CardSlider = D.declare('view.cmp.CardSlider', (cfg) => {
update();
});
return theDOM;
});
this.dom = theDOM;
};
Slider.prototype = {
save: function() {
tmpStore.set(this.name, {left: this.scroller.scrollLeft});
},
restore: function() {
this.scroller.scrollLeft = tmpStore.get([this.name, 'left'].join('.'));
}
};
Slider.prototype.constructor = Slider;
return Slider;
})();
export default CardSlider;
export {CardSlider};
......@@ -3,6 +3,8 @@ const Switch = D.declare('Switch', (cfg, contentHash) => {
if(cfg.content){
contentHash = cfg.content;
}
let {beforeSwitch, afterSwitch} = cfg;
if(Array.isArray(contentHash)){
if(contentHash.length === 0){
if(cfg.content)
......@@ -23,12 +25,15 @@ const Switch = D.declare('Switch', (cfg, contentHash) => {
'cmp-switch',
cfg.cls,
{ 'cmp-switch__filled': val in contentHash } ) ) ) } );
let oldValue;
(cfg.store || store).sub( cfg.key, (val)=> {
beforeSwitch && beforeSwitch(val, oldValue);
D.removeChildren(cmp);
if(val in contentHash)
D.appendChild( cmp, contentHash[ val ] );
afterSwitch && (tmpStore.get('loaded') ? afterSwitch(val, oldValue) : tmpStore.once('loaded', ()=> afterSwitch(val, oldValue)));
oldValue = val;
});
return cmp;
......
......@@ -4,13 +4,42 @@ import {AsyncAuthAjax} from "../../../controller/Ajax";
import {API} from "../../../dict/Consts";
import Card from "../../cmp/card/Card";
import CardSlider from "../../cmp/cardSlider/CardSlider";
import AccountNavigation from "../../block/accountNav/AccountNavigation.jsx";
import AccountNavigation from "../../block/accountNav/AccountNavigation";
const Account = D.declare('view.page.Account', () => {
let Slider = new CardSlider( {
name: "newCardsSlider",
itemClick: ( item, action ) => {
action.execute( item );
},
return <div class="account-page">
items: _ => store.sub(
[
'loaded.cards',
'navigation.current',
tmpStore.bind( 'afterNavigation.to' ),
tmpStore.bind( 'newCardsLoaded' ),
],
function( loadedCards, to, newCardsLoaded ){
if( newCardsLoaded !== loadedCards ){
if( loadedCards && to === 'Account' ){
_( cards
.getArray()
.filter( card => card.seen === false )
.sort( ( a, b ) => a.id - b.id )
);
tmpStore.set( 'newCardsLoaded', loadedCards )
}
}
}
)
} );
const dom = <div class="account-page">
<h1 class="readers-only">Страница личного кабинета сотрудника</h1>
<div class="account-page__wrapper">
<div class="account-page__menu">
......@@ -22,24 +51,7 @@ const Account = D.declare('view.page.Account', () => {
<div class="account-page__content-inner">
<div class="account-page__cards">
<h2 class="account-page__title">Новые карточки для вашей должности:</h2>
<CardSlider
items={_=> store.sub(
[
'loaded.cards',
'navigation.current',
tmpStore.bind('loaded')
],
(loadedCards, page, loaded,w)=>{
if(loadedCards && page === 'Account' && loaded)
_(cards
.getArray()
.filter(card=>card.seen === false)
.sort((a,b)=>a.id-b.id),
w+(w<1024?0:320+30*2+30*2)
)
})}
/>
{Slider}
<div className="account-page__no-cards">
<div className="account-page__no-cards-info">
<div className="account-page__no-cards-item">
......@@ -65,100 +77,22 @@ const Account = D.declare('view.page.Account', () => {
<div className="account-page__nav">
<AccountNavigation/>
</div>
{/* {(()=> {
let c = <div/>;
(async () => {
const result = await AsyncAuthAjax.get(API.ENDPOINTS.GET_USER_NEW_CARDS());
D.appendChild(c, result.map((item, n) =>
<div class="cards-list__item">
<Card
type={'product,info,other'.split(',')[n % 3]}
disabled={n % 5 === 0}
seen={n % 4 === 0}
title={item.name}
image={item.image}
/>
</div>
));
})();
return c
})()}*/}
{/*
<div class="cards-list__item">
<div class="card card--info">
<div class="card__image">
<img src="/uploads/images/card_product1.jpg" alt=""/>
</div>
<h3 class="card__title">Название карточки</h3>
<div class="card__footer">
<Button class={"button card__button"}>
<span>Изучить</span>
</Button>
</div>
</div>
</div>
<div class="cards-list__item">
<div class="card card--product">
<div class="card__image">
<img src="/uploads/images/card_product2.jpg" alt=""/>
</div>
<h3 class="card__title">Название карточки</h3>
<div class="card__footer">
<Button class={"button card__button"}>
<span>Изучить</span>
</Button>
</div>
</div>
</div>
<div class="cards-list__item">
<div class="card card--other">
<div class="card__image">
<img src="/uploads/images/card_product3.jpg" alt=""/>
</div>
<h3 class="card__title">Название карточки</h3>
<div class="card__footer">
<Button class={"button card__button"}>
<span>Изучить</span>
</Button>
</div>
</div>
</div>
<div class="cards-list__item">
<div class="card card--seen">
<div class="card__image">
<img src="/uploads/images/card_product4.jpg" alt=""/>
</div>
<h3 class="card__title">Название карточки</h3>
<div class="card__footer">
<div class="card__note">
<span>Просмотрена</span>
<Eye width="20" height="13" />
</div>
</div>
</div>
</div>
<div class="cards-list__item">
<div class="card card--disabled">
<div class="card__image">
<img src="/uploads/images/card-disabled.png" alt=""/>
</div>
<h3 class="card__title">Карточек нет</h3>
<div class="card__footer">
</div>
</div>
</div>*/}
</div>
</div>
</div>
</div>
</div>
</div>;
tmpStore.valEqualOnly('afterNavigation.to', 'Account')(function() {
Slider.restore();
});
tmpStore.valEqualOnly('beforeNavigation.from', 'Account')(function() {
Slider.save();
});
return dom;
});
export default Account;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment