mirror of
https://github.com/ascribe/onion.git
synced 2024-12-22 17:33:14 +01:00
merge table branch
This commit is contained in:
commit
b8ffac4275
2
.gitignore
vendored
2
.gitignore
vendored
@ -15,3 +15,5 @@ node_modules
|
||||
npm-debug.log
|
||||
|
||||
build/app.js
|
||||
|
||||
.DS_Store
|
@ -18,9 +18,7 @@ Install some nice extensions for Chrom(e|ium):
|
||||
git clone git@bitbucket.org:ascribe/onion.git
|
||||
cd onion
|
||||
npm install
|
||||
npm run watch
|
||||
|
||||
python -mSimpleHTTPServer
|
||||
gulp serve
|
||||
```
|
||||
|
||||
|
||||
|
24
css/main.css
24
css/main.css
@ -12,11 +12,13 @@
|
||||
.ascribe-table-header-row {
|
||||
border-bottom: 2px solid rgba(2, 182, 163, 0.5);
|
||||
border-top: 2px solid rgba(2, 182, 163, 0.5);
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.ascribe-table-header-column {
|
||||
display: table;
|
||||
height: 4em;
|
||||
height:3em;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.ascribe-table-header-column > span {
|
||||
@ -31,10 +33,10 @@
|
||||
.ascribe-table-header-column > span > .glyphicon {
|
||||
font-size: .5em;
|
||||
}
|
||||
|
||||
/*
|
||||
.ascribe-table-item:nth-child(even) {
|
||||
background-color: #F5F5F5;
|
||||
}
|
||||
}*/
|
||||
|
||||
/*.ascribe-table-item:hover {
|
||||
background-color: #EEEEEE;
|
||||
@ -44,7 +46,7 @@
|
||||
display: table;
|
||||
font-family: 'Source Sans Pro';
|
||||
font-size: 1.2em;
|
||||
height: 4em;
|
||||
height:3em;
|
||||
}
|
||||
|
||||
.ascribe-table-item-column > * {
|
||||
@ -52,6 +54,7 @@
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
.ascribe-table-item-selected {
|
||||
/*.btn-ascribe, .btn-ascribe:hover, .btn-ascribe:active, .btn-ascribe:focus {*/
|
||||
/*background-color: rgba(2, 182, 163, 0.5);*/
|
||||
/*border-color: rgba(2, 182, 163, 0.5);*/
|
||||
@ -109,6 +112,19 @@
|
||||
background-color: rgba(2, 182, 163, 0.5);
|
||||
}
|
||||
|
||||
.ascribe-table-item-selectable {
|
||||
cursor: default;
|
||||
}
|
||||
|
||||
.piece-list-toolbar {
|
||||
height:3em;
|
||||
}
|
||||
|
||||
.no-margin {
|
||||
margin-right: 0;
|
||||
margin-left: 0;
|
||||
}
|
||||
|
||||
.ascribe-detail-header {
|
||||
margin-top: 2em;
|
||||
}
|
||||
|
67
gulpfile.js
Normal file
67
gulpfile.js
Normal file
@ -0,0 +1,67 @@
|
||||
var gulp = require('gulp');
|
||||
var gulpif = require('gulp-if');
|
||||
var sourcemaps = require('gulp-sourcemaps');
|
||||
var util = require('gulp-util');
|
||||
var source = require('vinyl-source-stream');
|
||||
var buffer = require('vinyl-buffer');
|
||||
var watchify = require('watchify');
|
||||
var browserify = require('browserify');
|
||||
var browserSync = require('browser-sync');
|
||||
var babelify = require('babelify');
|
||||
var notify = require('gulp-notify');
|
||||
var _ = require('lodash');
|
||||
|
||||
gulp.task('build', function() {
|
||||
bundle(false);
|
||||
});
|
||||
|
||||
gulp.task('serve', ['browser-sync'], function() {
|
||||
bundle(true);
|
||||
});
|
||||
|
||||
gulp.task('browser-sync', function() {
|
||||
browserSync({
|
||||
server: {
|
||||
baseDir: "."
|
||||
},
|
||||
port: process.env.PORT || 3000
|
||||
});
|
||||
});
|
||||
|
||||
function bundle(watch) {
|
||||
var bro;
|
||||
|
||||
if (watch) {
|
||||
bro = watchify(browserify('./js/app.js',
|
||||
// Assigning debug to have sourcemaps
|
||||
_.assign(watchify.args, {
|
||||
debug: true
|
||||
})));
|
||||
bro.on('update', function() {
|
||||
rebundle(bro, true);
|
||||
});
|
||||
} else {
|
||||
bro = browserify('./js/app.js', {
|
||||
debug: true
|
||||
});
|
||||
}
|
||||
|
||||
bro.transform(babelify.configure({
|
||||
compact: false
|
||||
}));
|
||||
|
||||
function rebundle(bundler, watch) {
|
||||
return bundler.bundle()
|
||||
.on('error', notify.onError('Error: <%= error.message %>'))
|
||||
.pipe(source('app.js'))
|
||||
.pipe(buffer())
|
||||
.pipe(sourcemaps.init({
|
||||
loadMaps: true
|
||||
})) // loads map from browserify file
|
||||
.pipe(sourcemaps.write()) // writes .map file
|
||||
.pipe(gulp.dest('./build'))
|
||||
.pipe(browserSync.stream());
|
||||
}
|
||||
|
||||
return rebundle(bro);
|
||||
}
|
@ -5,7 +5,8 @@ import EditionListFetcher from '../fetchers/edition_list_fetcher.js';
|
||||
class EditionListActions {
|
||||
constructor() {
|
||||
this.generateActions(
|
||||
'updateEditionList'
|
||||
'updateEditionList',
|
||||
'selectEdition'
|
||||
);
|
||||
}
|
||||
|
||||
@ -14,7 +15,7 @@ class EditionListActions {
|
||||
.fetch(pieceId)
|
||||
.then((res) => {
|
||||
this.actions.updateEditionList({
|
||||
'editionList': res.editions,
|
||||
'editionListOfPiece': res.editions,
|
||||
pieceId
|
||||
});
|
||||
})
|
||||
|
32
js/components/acl_button.js
Normal file
32
js/components/acl_button.js
Normal file
@ -0,0 +1,32 @@
|
||||
import React from 'react';
|
||||
|
||||
import AppConstants from '../constants/application_constants';
|
||||
|
||||
let AclButton = React.createClass({
|
||||
propTypes: {
|
||||
action: React.PropTypes.oneOf(AppConstants.aclList).isRequired,
|
||||
availableAcls: React.PropTypes.array.isRequired
|
||||
},
|
||||
|
||||
render() {
|
||||
let shouldDisplay = this.props.availableAcls.indexOf(this.props.action) > -1;
|
||||
let styles = {};
|
||||
|
||||
if(shouldDisplay) {
|
||||
styles.display = 'inline-block';
|
||||
} else {
|
||||
styles.display = 'none';
|
||||
}
|
||||
|
||||
return (
|
||||
<button
|
||||
style={styles}
|
||||
type="button"
|
||||
className="btn btn-default btn-sm">
|
||||
{this.props.action.toUpperCase()}
|
||||
</button>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
export default AclButton;
|
@ -0,0 +1,82 @@
|
||||
import React from 'react';
|
||||
|
||||
import EditionListStore from '../../stores/edition_list_store';
|
||||
|
||||
import AclButton from '../acl_button';
|
||||
|
||||
let PieceListToolbar = React.createClass({
|
||||
getInitialState() {
|
||||
return EditionListStore.getState();
|
||||
},
|
||||
|
||||
onChange(state) {
|
||||
this.setState(state);
|
||||
},
|
||||
|
||||
componentDidMount() {
|
||||
EditionListStore.listen(this.onChange)
|
||||
},
|
||||
|
||||
componentDidUnmount() {
|
||||
EditionListStore.unlisten(this.onChange)
|
||||
},
|
||||
|
||||
filterForSelected(edition) {
|
||||
return edition.selected;
|
||||
},
|
||||
|
||||
fetchSelectedEditionList() {
|
||||
let selectedEditionList = [];
|
||||
|
||||
Object
|
||||
.keys(this.state.editionList)
|
||||
.forEach((key) => {
|
||||
let filteredEditionsForPiece = this.state.editionList[key].filter(this.filterForSelected);
|
||||
selectedEditionList = selectedEditionList.concat(filteredEditionsForPiece);
|
||||
});
|
||||
|
||||
return selectedEditionList;
|
||||
},
|
||||
|
||||
intersectAcls(a, b) {
|
||||
return a.filter((val) => b.indexOf(val) > -1);
|
||||
},
|
||||
|
||||
getAvailableAcls() {
|
||||
let availableAcls = [];
|
||||
let selectedEditionList = this.fetchSelectedEditionList();
|
||||
|
||||
// If no edition has been selected, availableActions is empty
|
||||
// If only one edition has been selected, their actions are available
|
||||
// If more than one editions have been selected, their acl properties are intersected
|
||||
if(selectedEditionList.length >= 1) {
|
||||
availableAcls = selectedEditionList[0].acl;
|
||||
}
|
||||
if(selectedEditionList.length >= 2) {
|
||||
for(let i = 1; i < selectedEditionList.length; i++) {
|
||||
availableAcls = this.intersectAcls(availableAcls, selectedEditionList[i].acl);
|
||||
}
|
||||
}
|
||||
|
||||
return availableAcls;
|
||||
},
|
||||
|
||||
render() {
|
||||
let availableAcls = this.getAvailableAcls();
|
||||
|
||||
return (
|
||||
<div className="row no-margin">
|
||||
<div className="col-xs-12 col-sm-12 col-md-12 col-lg-12 piece-list-toolbar">
|
||||
<div className="pull-right">
|
||||
<AclButton availableAcls={availableAcls} action="transfer" />
|
||||
<AclButton availableAcls={availableAcls} action="consign" />
|
||||
<AclButton availableAcls={availableAcls} action="share" />
|
||||
<AclButton availableAcls={availableAcls} action="loan" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
export default PieceListToolbar;
|
@ -27,7 +27,13 @@ let Table = React.createClass({
|
||||
if(this.props.itemList && this.props.itemList.length > 0) {
|
||||
return (
|
||||
<div className="ascribe-table">
|
||||
<TableHeader columnList={this.props.columnList} itemList={this.props.itemList} fetchList={this.props.fetchList} changeOrder={this.props.changeOrder} orderAsc={this.props.orderAsc} orderBy={this.props.orderBy} />
|
||||
<TableHeader
|
||||
columnList={this.props.columnList}
|
||||
itemList={this.props.itemList}
|
||||
fetchList={this.props.fetchList}
|
||||
changeOrder={this.props.changeOrder}
|
||||
orderAsc={this.props.orderAsc}
|
||||
orderBy={this.props.orderBy} />
|
||||
{this.renderChildren()}
|
||||
</div>
|
||||
);
|
||||
|
@ -12,9 +12,9 @@ let TableHeader = React.createClass({
|
||||
propTypes: {
|
||||
columnList: React.PropTypes.arrayOf(React.PropTypes.instanceOf(TableColumnContentModel)),
|
||||
itemList: React.PropTypes.array.isRequired,
|
||||
changeOrder: React.PropTypes.func.isRequired,
|
||||
orderAsc: React.PropTypes.bool.isRequired,
|
||||
orderBy: React.PropTypes.string.isRequired
|
||||
changeOrder: React.PropTypes.func,
|
||||
orderAsc: React.PropTypes.bool,
|
||||
orderBy: React.PropTypes.string
|
||||
},
|
||||
|
||||
render() {
|
||||
@ -23,7 +23,7 @@ let TableHeader = React.createClass({
|
||||
<div className="row">
|
||||
{this.props.columnList.map((val, i) => {
|
||||
|
||||
let columnClasses = this.calcColumnClasses(this.props.columnList, i);
|
||||
let columnClasses = this.calcColumnClasses(this.props.columnList, i, 12);
|
||||
let columnName = this.props.columnList[i].columnName;
|
||||
let canBeOrdered = this.props.columnList[i].canBeOrdered;
|
||||
|
||||
|
@ -8,10 +8,10 @@ let TableHeaderItem = React.createClass({
|
||||
columnClasses: React.PropTypes.string.isRequired,
|
||||
displayName: React.PropTypes.string.isRequired,
|
||||
columnName: React.PropTypes.string.isRequired,
|
||||
canBeOrdered: React.PropTypes.bool.isRequired,
|
||||
changeOrder: React.PropTypes.func.isRequired,
|
||||
orderAsc: React.PropTypes.bool.isRequired,
|
||||
orderBy: React.PropTypes.string.isRequired
|
||||
canBeOrdered: React.PropTypes.bool,
|
||||
changeOrder: React.PropTypes.func,
|
||||
orderAsc: React.PropTypes.bool,
|
||||
orderBy: React.PropTypes.string
|
||||
},
|
||||
|
||||
changeOrder() {
|
||||
@ -19,7 +19,7 @@ let TableHeaderItem = React.createClass({
|
||||
},
|
||||
|
||||
render() {
|
||||
if(this.props.canBeOrdered) {
|
||||
if(this.props.canBeOrdered && this.props.changeOrder && this.props.orderAsc != null && this.props.orderBy) {
|
||||
if(this.props.columnName === this.props.orderBy) {
|
||||
return (
|
||||
<div
|
||||
|
@ -1,38 +1,30 @@
|
||||
import React from 'react';
|
||||
|
||||
import TableColumnMixin from '../../mixins/table_column_mixin';
|
||||
|
||||
import TableColumnContentModel from '../../models/table_column_content_model';
|
||||
|
||||
import TableItemWrapper from './table_item_wrapper';
|
||||
|
||||
|
||||
let TableItem = React.createClass({
|
||||
mixins: [TableColumnMixin],
|
||||
|
||||
propTypes: {
|
||||
columnList: React.PropTypes.arrayOf(React.PropTypes.instanceOf(TableColumnContentModel)),
|
||||
columnContent: React.PropTypes.object
|
||||
columnContent: React.PropTypes.object,
|
||||
onClick: React.PropTypes.func, // See: https://facebook.github.io/react/tips/expose-component-functions.html
|
||||
classNames: React.PropTypes.string
|
||||
},
|
||||
|
||||
render() {
|
||||
let calcColumnElementContent = () => {
|
||||
return this.props.columnList.map((column, i) => {
|
||||
|
||||
let TypeElement = column.displayType;
|
||||
let columnClass = this.calcColumnClasses(this.props.columnList, i);
|
||||
|
||||
return (
|
||||
<div className={columnClass + ' ascribe-table-item-column'} key={i}>
|
||||
<TypeElement content={this.props.columnContent[column.columnName]} width="50" />
|
||||
</div>
|
||||
);
|
||||
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="col-xs-12 col-sm-12 col-md-12 col-lg-12 ascribe-table-item">
|
||||
<div
|
||||
className={this.props.classNames + ' col-xs-12 col-sm-12 col-md-12 col-lg-12 ascribe-table-item'}
|
||||
onClick={this.props.onClick}>
|
||||
<div className="row">
|
||||
{calcColumnElementContent()}
|
||||
<TableItemWrapper
|
||||
columnList={this.props.columnList}
|
||||
columnContent={this.props.columnContent}
|
||||
columnWidth={12}>
|
||||
</TableItemWrapper>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
18
js/components/ascribe_table/table_item_acl.js
Normal file
18
js/components/ascribe_table/table_item_acl.js
Normal file
@ -0,0 +1,18 @@
|
||||
import React from 'react';
|
||||
|
||||
|
||||
let TableItemAcl = React.createClass({
|
||||
propTypes: {
|
||||
content: React.PropTypes.array.isRequired
|
||||
},
|
||||
|
||||
render() {
|
||||
return (
|
||||
<span>
|
||||
{this.props.content.join('/')}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
export default TableItemAcl;
|
38
js/components/ascribe_table/table_item_selectable.js
Normal file
38
js/components/ascribe_table/table_item_selectable.js
Normal file
@ -0,0 +1,38 @@
|
||||
import React from 'react';
|
||||
import classNames from 'classnames';
|
||||
|
||||
import TableColumnContentModel from '../../models/table_column_content_model';
|
||||
|
||||
import TableItem from './table_item';
|
||||
|
||||
// This component is implemented as recommended here: http://stackoverflow.com/a/25723635/1263876
|
||||
let TableItemSelectable = React.createClass({
|
||||
|
||||
propTypes: {
|
||||
columnList: React.PropTypes.arrayOf(React.PropTypes.instanceOf(TableColumnContentModel)),
|
||||
columnContent: React.PropTypes.object,
|
||||
parentId: React.PropTypes.number,
|
||||
className: React.PropTypes.string
|
||||
},
|
||||
|
||||
selectItem() {
|
||||
this.props.selectItem(this.props.parentId, this.props.columnContent.edition_number);
|
||||
},
|
||||
|
||||
render() {
|
||||
let tableItemClasses = classNames({
|
||||
'ascribe-table-item-selected': this.props.columnContent.selected
|
||||
});
|
||||
|
||||
return (
|
||||
<TableItem
|
||||
classNames={tableItemClasses + ' ' + this.props.className}
|
||||
columnList={this.props.columnList}
|
||||
columnContent={this.props.columnContent}
|
||||
onClick={this.selectItem}>
|
||||
</TableItem>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
export default TableItemSelectable;
|
@ -5,12 +5,12 @@ import TableColumnContentModel from '../../models/table_column_content_model';
|
||||
import EditionListStore from '../../stores/edition_list_store';
|
||||
import EditionListActions from '../../actions/edition_list_actions';
|
||||
|
||||
// ToDo: Create Table-specific Utils to not lock it to projects utilities
|
||||
import GeneralUtils from '../../utils/general_utils';
|
||||
|
||||
import Table from './table';
|
||||
import TableItem from './table_item';
|
||||
import TableItemWrapper from './table_item_wrapper';
|
||||
import TableItemText from './table_item_text';
|
||||
import TableItemAcl from './table_item_acl';
|
||||
import TableItemSelectable from './table_item_selectable';
|
||||
import TableItemSubtableButton from './table_item_subtable_button';
|
||||
|
||||
|
||||
@ -40,6 +40,7 @@ let TableItemSubtable = React.createClass({
|
||||
'open': false
|
||||
});
|
||||
} else {
|
||||
|
||||
EditionListActions.fetchEditionList(this.props.columnContent.id);
|
||||
this.setState({
|
||||
'open': true,
|
||||
@ -48,43 +49,21 @@ let TableItemSubtable = React.createClass({
|
||||
}
|
||||
},
|
||||
|
||||
calcColumnClasses(list, i) {
|
||||
let bootstrapClasses = ['col-xs-', 'col-sm-', 'col-md-', 'col-lg-'];
|
||||
|
||||
let listOfRowValues = list.map((column) => column.rowWidth );
|
||||
let numOfColumns = GeneralUtils.sumNumList(listOfRowValues);
|
||||
|
||||
if(numOfColumns > 10) {
|
||||
throw new Error('Bootstrap has only 12 columns to assign. You defined ' + numOfColumns + '. Change this in the columnMap you\'re passing to the table.')
|
||||
} else {
|
||||
return bootstrapClasses.join( listOfRowValues[i] + ' ') + listOfRowValues[i];
|
||||
}
|
||||
selectItem(parentId, itemId) {
|
||||
EditionListActions.selectEdition({
|
||||
'pieceId': parentId,
|
||||
'editionId': itemId
|
||||
});
|
||||
},
|
||||
|
||||
render() {
|
||||
|
||||
let calcColumnElementContent = () => {
|
||||
return this.props.columnList.map((column, i) => {
|
||||
|
||||
let TypeElement = column.displayType;
|
||||
let columnClass = this.calcColumnClasses(this.props.columnList, i);
|
||||
|
||||
return (
|
||||
<div className={columnClass + ' ascribe-table-item-column'} key={i}>
|
||||
<TypeElement content={this.props.columnContent[column.columnName]} width="50" />
|
||||
</div>
|
||||
);
|
||||
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
let renderEditionListTable = () => {
|
||||
|
||||
let columnList = [
|
||||
new TableColumnContentModel('edition_number', 'Edition Number', TableItemText, 2, false),
|
||||
new TableColumnContentModel('user_registered', 'User', TableItemText, 4, true),
|
||||
new TableColumnContentModel('bitcoin_id', 'Bitcoin Address', TableItemText, 4, true)
|
||||
new TableColumnContentModel('acl', 'Actions', TableItemAcl, 4, true)
|
||||
];
|
||||
|
||||
if(this.state.open && this.state.editionList[this.props.columnContent.id] && this.state.editionList[this.props.columnContent.id].length) {
|
||||
@ -94,9 +73,12 @@ let TableItemSubtable = React.createClass({
|
||||
<Table itemList={this.state.editionList[this.props.columnContent.id]} columnList={columnList}>
|
||||
{this.state.editionList[this.props.columnContent.id].map((edition, i) => {
|
||||
return (
|
||||
<TableItem
|
||||
<TableItemSelectable
|
||||
className="ascribe-table-item-selectable"
|
||||
selectItem={this.selectItem}
|
||||
parentId={this.props.columnContent.id}
|
||||
key={i}>
|
||||
</TableItem>
|
||||
</TableItemSelectable>
|
||||
);
|
||||
})}
|
||||
</Table>
|
||||
@ -109,9 +91,13 @@ let TableItemSubtable = React.createClass({
|
||||
return (
|
||||
<div className="col-xs-12 col-sm-12 col-md-12 col-lg-12 ascribe-table-item">
|
||||
<div className="row">
|
||||
{calcColumnElementContent()}
|
||||
<div className="col-xs-2 col-sm-2 col-md-2 col-lg-2 ascribe-table-item-column">
|
||||
<TableItemSubtableButton content="Editions" onClick={this.loadEditionList}>
|
||||
<TableItemWrapper
|
||||
columnList={this.props.columnList}
|
||||
columnContent={this.props.columnContent}
|
||||
columnWidth={12}>
|
||||
</TableItemWrapper>
|
||||
<div className="col-xs-1 col-sm-1 col-md-1 col-lg-1 ascribe-table-item-column">
|
||||
<TableItemSubtableButton content="+" onClick={this.loadEditionList}>
|
||||
</TableItemSubtableButton>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -10,7 +10,7 @@ let TableItemSubtableButton = React.createClass({
|
||||
render() {
|
||||
return (
|
||||
<span>
|
||||
<button type="button" className="btn btn-ascribe btn-primary btn-sm" onClick={this.props.onClick}>
|
||||
<button type="button" className="btn btn-default btn-sm ascribe-table-expand-button" onClick={this.props.onClick}>
|
||||
{this.props.content}
|
||||
</button>
|
||||
</span>
|
||||
|
34
js/components/ascribe_table/table_item_wrapper.js
Normal file
34
js/components/ascribe_table/table_item_wrapper.js
Normal file
@ -0,0 +1,34 @@
|
||||
import React from 'react';
|
||||
|
||||
import TableColumnContentModel from '../../models/table_column_content_model';
|
||||
import TableColumnMixin from '../../mixins/table_column_mixin';
|
||||
|
||||
let TableItemWrapper = React.createClass({
|
||||
mixins: [TableColumnMixin],
|
||||
propTypes: {
|
||||
columnList: React.PropTypes.arrayOf(React.PropTypes.instanceOf(TableColumnContentModel)),
|
||||
columnContent: React.PropTypes.object,
|
||||
columnWidth: React.PropTypes.number.isRequired
|
||||
},
|
||||
|
||||
render() {
|
||||
return (
|
||||
<div>
|
||||
{this.props.columnList.map((column, i) => {
|
||||
|
||||
let TypeElement = column.displayType;
|
||||
let columnClass = this.calcColumnClasses(this.props.columnList, i, this.props.columnWidth);
|
||||
|
||||
return (
|
||||
<div className={columnClass + ' ascribe-table-item-column'} key={i}>
|
||||
<TypeElement content={this.props.columnContent[column.columnName]} width="50" />
|
||||
</div>
|
||||
);
|
||||
|
||||
})}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
export default TableItemWrapper;
|
@ -15,6 +15,8 @@ import TableColumnContentModel from '../models/table_column_content_model';
|
||||
|
||||
import Pagination from './ascribe_pagination/pagination';
|
||||
|
||||
import PieceListToolbar from './ascribe_piece_list_toolbar/piece_list_toolbar';
|
||||
|
||||
|
||||
let PieceList = React.createClass({
|
||||
|
||||
@ -62,6 +64,7 @@ let PieceList = React.createClass({
|
||||
if(this.state.pieceList && this.state.pieceList.length > 0) {
|
||||
return (
|
||||
<div>
|
||||
<PieceListToolbar />
|
||||
<Table
|
||||
columnList={columnList}
|
||||
changeOrder={this.tableChangeOrder}
|
||||
|
@ -1,8 +1,7 @@
|
||||
let constants = {
|
||||
'baseUrl': 'http://localhost:8000/api/',
|
||||
//'baseUrl': 'http://staging.ascribe.io/api/',
|
||||
'debugCredentialBase64': 'ZGltaUBtYWlsaW5hdG9yLmNvbTowMDAwMDAwMDAw' // dimi@mailinator:0000000000
|
||||
|
||||
'debugCredentialBase64': 'ZGltaUBtYWlsaW5hdG9yLmNvbTowMDAwMDAwMDAw', // dimi@mailinator:0000000000
|
||||
'aclList': ['edit', 'consign', 'transfer', 'loan', 'share', 'download', 'view', 'delete', 'del_from_collection', 'add_to_collection']
|
||||
};
|
||||
export default constants;
|
||||
|
||||
export default constants;
|
@ -7,14 +7,14 @@ let TableColumnMixin = {
|
||||
* Generates the bootstrap grid column declarations automatically using
|
||||
* the columnMap.
|
||||
*/
|
||||
calcColumnClasses(list, i) {
|
||||
calcColumnClasses(list, i, numOfColumns) {
|
||||
let bootstrapClasses = ['col-xs-', 'col-sm-', 'col-md-', 'col-lg-'];
|
||||
|
||||
let listOfRowValues = list.map((column) => column.rowWidth );
|
||||
let numOfColumns = GeneralUtils.sumNumList(listOfRowValues);
|
||||
let numOfUsedColumns = GeneralUtils.sumNumList(listOfRowValues);
|
||||
|
||||
if(numOfColumns > 12) {
|
||||
throw new Error('Bootstrap has only 12 columns to assign. You defined ' + numOfColumns + '. Change this in the columnMap you\'re passing to the table.')
|
||||
if(numOfUsedColumns > numOfColumns) {
|
||||
throw new Error('This table has only ' + numOfColumns + ' columns to assign. You defined ' + numOfUsedColumns + '. Change this in the columnMap you\'re passing to the table.')
|
||||
} else {
|
||||
return bootstrapClasses.join( listOfRowValues[i] + ' ') + listOfRowValues[i];
|
||||
}
|
||||
|
@ -1,3 +1,5 @@
|
||||
import React from 'react';
|
||||
|
||||
import alt from '../alt';
|
||||
import EditionsListActions from '../actions/edition_list_actions';
|
||||
|
||||
@ -7,8 +9,29 @@ class EditionListStore {
|
||||
this.bindActions(EditionsListActions);
|
||||
}
|
||||
|
||||
onUpdateEditionList({pieceId, editionList}) {
|
||||
this.editionList[pieceId] = editionList;
|
||||
onUpdateEditionList({pieceId, editionListOfPiece}) {
|
||||
if(this.editionList[pieceId]) {
|
||||
this.editionList[pieceId].forEach((edition, i) => {
|
||||
// This uses the index of the new editionList for determining the edition.
|
||||
// If the list of editions can be sorted in the future, this needs to be changed!
|
||||
editionListOfPiece[i] = React.addons.update(edition, {$merge: editionListOfPiece[i]});
|
||||
})
|
||||
}
|
||||
this.editionList[pieceId] = editionListOfPiece;
|
||||
}
|
||||
|
||||
onSelectEdition({pieceId, editionId}) {
|
||||
|
||||
this.editionList[pieceId].forEach((edition) => {
|
||||
if(edition.edition_number === editionId) {
|
||||
if(edition.selected) {
|
||||
edition.selected = false;
|
||||
} else {
|
||||
edition.selected = true;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
|
22
package.json
22
package.json
@ -3,26 +3,24 @@
|
||||
"version": "0.0.1",
|
||||
"description": "Das neue web client for Ascribe",
|
||||
"main": "js/app.js",
|
||||
"scripts": {
|
||||
"watch": "watchify -o build/app.js -v -d js/app.js",
|
||||
"build": "browserify . -t [envify --NODE_ENV production] | uglifyjs -cm > build/app.js",
|
||||
"test": "jest"
|
||||
},
|
||||
"author": "Ascribe",
|
||||
"license": "Copyright",
|
||||
"browserify": {
|
||||
"transform": [
|
||||
"babelify",
|
||||
"envify"
|
||||
]
|
||||
},
|
||||
"devDependencies": {
|
||||
"babel-jest": "^4.0.0",
|
||||
"babelify": "^6.0.2",
|
||||
"babelify": "^6.1.2",
|
||||
"browser-sync": "^2.7.5",
|
||||
"browserify": "^9.0.8",
|
||||
"envify": "^3.4.0",
|
||||
"gulp": "^3.8.11",
|
||||
"gulp-if": "^1.2.5",
|
||||
"gulp-notify": "^2.2.0",
|
||||
"gulp-sourcemaps": "^1.5.2",
|
||||
"gulp-util": "^3.0.4",
|
||||
"jest-cli": "^0.4.0",
|
||||
"lodash": "^3.9.3",
|
||||
"reactify": "^1.1.0",
|
||||
"vinyl-buffer": "^1.0.0",
|
||||
"vinyl-source-stream": "^1.1.0",
|
||||
"watchify": "^3.1.2"
|
||||
},
|
||||
"dependencies": {
|
||||
|
Loading…
Reference in New Issue
Block a user