Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

unigrid #16

Open
wants to merge 24 commits into
base: master
Choose a base branch
from
Open
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
app working again
artwol993 committed May 11, 2021
commit ca8760fb15eea770aec0c3a7951c29bf4d7e1eb1
1 change: 0 additions & 1 deletion React-starter
Submodule React-starter deleted from 77e787
10 changes: 4 additions & 6 deletions react-starter/examples/unigrid.html
Original file line number Diff line number Diff line change
@@ -22,7 +22,6 @@
</head>

<body>
<h2>test</h2>
<h1>Unigrid Style Guide</h1>
<p>Unigrid is a React component that implements a configurable table composed of lower-level multipurpose reusable
components.</p>
@@ -48,8 +47,7 @@ <h2 id="unigrid">Unigrid</h2>
components. Those components should then be placed on a page within a new dedicated component built using non-table
tags (i.e. <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/div">&lt;div&gt;</a> or similar that
are semantically correct depending on the context within the page). <a href="#unigrid"><b>Unigrid</b></a> components
<b>can not</b> be nested (can not be contained within other Unigrid components).
</p>
<b>can not</b> be nested (can not be contained within other Unigrid components).</p>

<h2 id="unigrid-header">UnigridHeader</h2>
<p>Uses tag <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/thead">&lt;thead&gt;</a>. Contains zero
@@ -81,9 +79,9 @@ <h2 id="unigrid-cell">UnigridCell</h2>

<h1>Unigrid Examples</h1>
<div id="container"></div>
<script src="/jspm_packages/system.js"></script>
<script src="/jspm.config.js"></script>
<!-- <script src="/jspm_packages/system.js"></script>
<script src="/jspm.config.js"></script> -->
<script>SystemJS.import('examples/app');</script>
</body>

</html>
</html>
5,694 changes: 1,156 additions & 4,538 deletions react-starter/package-lock.json

Large diffs are not rendered by default.

6 changes: 1 addition & 5 deletions react-starter/package.json
Original file line number Diff line number Diff line change
@@ -20,7 +20,6 @@
"babel-loader": "^8.2.2",
"css-loader": "^5.2.4",
"express": "^4.17.1",
"json-loader": "^0.5.7",
"sass": "^1.32.11",
"sass-loader": "^11.0.1",
"style-loader": "^2.0.0",
@@ -30,11 +29,8 @@
"webpack-dev-server": "^3.11.2"
},
"dependencies": {
"eslint": "^7.25.0",
"image-webpack-loader": "^7.0.1",
"lodash": "^4.17.21",
"react": "^17.0.2",
"react-dom": "^17.0.2",
"unigrid": "0.0.45"
"react-dom": "^17.0.2"
}
}
5 changes: 0 additions & 5 deletions react-starter/sass/App.scss
Original file line number Diff line number Diff line change
@@ -139,26 +139,21 @@ hr {

.unigrid-header {
grid-column: 1 / 6;
background-color: red;
}

.unigrid-header-container {
display: grid;
grid-template-columns: repeat(5, 1fr);


}

.unigrid-header-container-box {
grid-column: 1/6;
}
.unigrid-segment {
grid-row: 2 / 5;
background-color: blue;
}

.unigrid-footer {
grid-row: 5;
background-color: yellow;
}

5 changes: 3 additions & 2 deletions react-starter/src/App.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import React from "react";
import "../sass/App.scss"
import { Unigrid } from "../unigrid"
import "../sass/App.scss";
// import { Unigrid } from "../unigrid"
import { UnigridExamples } from '../examples/UnigridExamples';

function App() {
@@ -15,4 +15,5 @@ function App() {
)
}


export default App
64 changes: 31 additions & 33 deletions react-starter/src/Unigrid.js
Original file line number Diff line number Diff line change
@@ -25,39 +25,37 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

import React from 'react';
import { isDefined, cleanProps, newChildren } from './helpers';
import { getIterator } from './iterators';

const json = require('./json/tableResp1.json')
import { isDefined, cleanProps, newChildren } from 'src/helpers';
import { getIterator } from 'src/iterators';

export default class Unigrid extends React.Component {
constructor(props) {
super(props);
this.state = isDefined(this.props, 'box') ? this.props.box : undefined;
}

static isUnigrid() {
return true;
}

static create(oProps, oBox) {
const nProps = Object.assign({}, oProps.table || {}, oProps);
const { table, data, item, box, cellTypes, ...cfg } = nProps;
const children = newChildren(cfg, oBox, oProps, data, item);
const cleaned = cleanProps(nProps);
return React.createElement(cfg.renderAs || 'table', cleaned, children);
}

getBox() {
return this.box || this.props.box || {};
}

setBox(box) {
this.box = box;
this.setState(box);
}

render() {
return Unigrid.create(this.props, this.getBox());
}
constructor(props) {
super(props);
this.state = isDefined(this.props, 'box') ? this.props.box : undefined;
}

static isUnigrid() {
return true;
}

static create(oProps, oBox) {
const nProps = Object.assign({}, oProps.table || {}, oProps);
const { table, data, item, box, cellTypes, ...cfg } = nProps;
const children = newChildren(cfg, oBox, oProps, data, item);
const cleaned = cleanProps(nProps);
return React.createElement(cfg.renderAs || 'table', cleaned, children);
}

getBox() {
return this.box || this.props.box || {};
}

setBox(box) {
this.box = box;
this.setState(box);
}

render() {
return Unigrid.create(this.props, this.getBox());
}
}
20 changes: 10 additions & 10 deletions react-starter/src/UnigridCells.js
Original file line number Diff line number Diff line change
@@ -25,22 +25,22 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

import React from 'react';
import { cleanCellProps } from './helpers';
import { cleanCellProps } from 'src/helpers';

export const UnigridEmptyCell = (p) => {
const cleaned = cleanCellProps(p);
const Tx = p.Tx;
return (<Tx {...cleaned} />);
const cleaned = cleanCellProps(p);
const Tx = p.Tx;
return (<Tx {...cleaned} />);
}

export const UnigridTextCell = (p) => {
const cleaned = cleanCellProps(p);
const Tx = p.Tx;
return (<Tx {...cleaned} >{p.cell}</Tx>);
const cleaned = cleanCellProps(p);
const Tx = p.Tx;
return (<Tx {...cleaned} >{p.cell}</Tx>);
}

export const UnigridNumberCell = (p) => {
const cleaned = cleanCellProps(p);
const Tx = p.Tx;
return (<Tx {...cleaned} >{p.cell.toString()}</Tx>);
const cleaned = cleanCellProps(p);
const Tx = p.Tx;
return (<Tx {...cleaned} >{p.cell.toString()}</Tx>);
}
252 changes: 126 additions & 126 deletions react-starter/src/UnigridRow.js
Original file line number Diff line number Diff line change
@@ -26,156 +26,156 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

import React from 'react';
import {
UnigridEmptyCell,
UnigridTextCell,
UnigridNumberCell
} from './UnigridCells';
import { isDefined, tryAmend, idMaker, cleanProps } from './helpers';
import { applyFormatter } from './sorting';
UnigridEmptyCell,
UnigridTextCell,
UnigridNumberCell
} from 'src/UnigridCells';
import { isDefined, tryAmend, idMaker, cleanProps } from 'src/helpers';
import { applyFormatter } from 'src/sorting';

export class UnigridRow extends React.Component {
static mkProps(oCell, item, box, renderAs, rowAs, mixIn, addProp) {
let cell = undefined;
let props = Object.assign({}, addProp, mixIn);

// Special case for deep merging 'cell'
const cellMixIn = isDefined(props, 'cell') &&
typeof (props.cell === 'object') ? props.cell : false;

// create a shallow copy to avoid mutating props
if (typeof (oCell) === 'object') {
Object.assign(props, oCell);
// Re-merge the 'cell' objects from oCell and mixIn
if (cellMixIn && isDefined(oCell, 'cell')
&& typeof (oCell.cell) === 'object') {
props.cell = Object.assign({}, cellMixIn, oCell.cell);
}
} else {
cell = oCell;
}
static mkProps(oCell, item, box, renderAs, rowAs, mixIn, addProp) {
let cell = undefined;
let props = Object.assign({}, addProp, mixIn);

// Special case for deep merging 'cell'
const cellMixIn = isDefined(props, 'cell') &&
typeof (props.cell === 'object') ? props.cell : false;

// create a shallow copy to avoid mutating props
if (typeof (oCell) === 'object') {
Object.assign(props, oCell);
// Re-merge the 'cell' objects from oCell and mixIn
if (cellMixIn && isDefined(oCell, 'cell')
&& typeof (oCell.cell) === 'object') {
props.cell = Object.assign({}, cellMixIn, oCell.cell);
}
} else {
cell = oCell;
}

if (cell !== undefined) {
Object.assign(props, { show: cell });
}
if (!isDefined(props, 'item') && item !== undefined) {
Object.assign(props, { item: item });
}
if (!isDefined(props, 'box') && box !== undefined) {
Object.assign(props, { box: box });
}
if (!isDefined(props, 'renderAs') && renderAs !== undefined) {
Object.assign(props, { renderAs: renderAs });
}
if (!isDefined(props, 'rowAs') && rowAs !== undefined) {
Object.assign(props, { rowAs: rowAs });
if (cell !== undefined) {
Object.assign(props, { show: cell });
}
if (!isDefined(props, 'item') && item !== undefined) {
Object.assign(props, { item: item });
}
if (!isDefined(props, 'box') && box !== undefined) {
Object.assign(props, { box: box });
}
if (!isDefined(props, 'renderAs') && renderAs !== undefined) {
Object.assign(props, { renderAs: renderAs });
}
if (!isDefined(props, 'rowAs') && rowAs !== undefined) {
Object.assign(props, { rowAs: rowAs });
}

return props;
}

return props;
}
static cellTypeAndProps(cell, item, box, renderAs, rowAs, mixIn, addProp) {
if (cell === null) {
let props = this.mkProps(undefined, item, box, renderAs, rowAs, mixIn, addProp);
return ['empty', tryAmend(props, item, box, 'cell', 'cell')];
}

static cellTypeAndProps(cell, item, box, renderAs, rowAs, mixIn, addProp) {
if (cell === null) {
let props = this.mkProps(undefined, item, box, renderAs, rowAs, mixIn, addProp);
return ['empty', tryAmend(props, item, box, 'cell', 'cell')];
}
let cellProps = this.mkProps(cell, item, box, renderAs, rowAs, mixIn, addProp);

let cellProps = this.mkProps(cell, item, box, renderAs, rowAs, mixIn, addProp);
if (!isDefined(cellProps, 'cell') && isDefined(cellProps, 'show')) {
Object.assign(cellProps, { cell: applyFormatter(cellProps) });
}

if (!isDefined(cellProps, 'cell') && isDefined(cellProps, 'show')) {
Object.assign(cellProps, { cell: applyFormatter(cellProps) });
}
cellProps = tryAmend(cellProps, item, box, 'cell', 'cell');

cellProps = tryAmend(cellProps, item, box, 'cell', 'cell');
if (isDefined(cellProps, 'as')) {
return [cellProps.as, cellProps];
}

if (isDefined(cellProps, 'as')) {
return [cellProps.as, cellProps];
return [typeof (cellProps.cell), cellProps];
}

return [typeof (cellProps.cell), cellProps];
}
static createCellForType(cellTypes, type, oProps) {
let { show, using, as, bindToCell, ...nProps } = oProps;

static createCellForType(cellTypes, type, oProps) {
let { show, using, as, bindToCell, ...nProps } = oProps;
const Tx = nProps.renderAs || (nProps.rowAs === 'header' ? 'th' : 'td');
Object.assign(nProps, { Tx: Tx });

const Tx = nProps.renderAs || (nProps.rowAs === 'header' ? 'th' : 'td');
Object.assign(nProps, { Tx: Tx });
if (typeof (type) !== 'string') {
if (isDefined(type, 'type')) {
return React.cloneElement(type, nProps);
}
return React.createElement(type, nProps);
}

if (typeof (type) !== 'string') {
if (isDefined(type, 'type')) {
return React.cloneElement(type, nProps);
}
return React.createElement(type, nProps);
}
if (cellTypes && isDefined(cellTypes, type)) {
return React.createElement(cellTypes[type], nProps);
}

if (cellTypes && isDefined(cellTypes, type)) {
return React.createElement(cellTypes[type], nProps);
}
switch (type) {
case 'string': return (<UnigridTextCell {...nProps} />);
case 'number': return (<UnigridNumberCell {...nProps} />);
case 'empty': return (<UnigridEmptyCell {...nProps} />);
}

switch (type) {
case 'string': return (<UnigridTextCell {...nProps} />);
case 'number': return (<UnigridNumberCell {...nProps} />);
case 'empty': return (<UnigridEmptyCell {...nProps} />);
// 'undefined' type
return (
<UnigridTextCell {...nProps} cell={"Error: " + JSON.stringify(oProps)} />
);
}

// 'undefined' type
return (
<UnigridTextCell {...nProps} cell={"Error: " + JSON.stringify(oProps)} />
);
}

static createAndProcessCell(cell, item, box, renderAs, rowAs, mixIn, cellTypes, oAddProp, idCounter) {
const addProp = Object.assign({}, oAddProp, { key: idCounter.next().value });
let [type, props] = this.cellTypeAndProps(cell, item, box, renderAs, rowAs, mixIn, addProp);
let binds = props.bindToCell || [];
binds = typeof (binds) === 'string' ? [binds] : binds;
let toAdd = [];
for (let i = 0; i < binds.length; i++) {
let funName = binds[i];
let oldFun = props[funName];
if (oldFun !== undefined) {
let newFun = function () {
return oldFun.apply(this.unigridCell, arguments);
static createAndProcessCell(cell, item, box, renderAs, rowAs, mixIn, cellTypes, oAddProp, idCounter) {
const addProp = Object.assign({}, oAddProp, { key: idCounter.next().value });
let [type, props] = this.cellTypeAndProps(cell, item, box, renderAs, rowAs, mixIn, addProp);
let binds = props.bindToCell || [];
binds = typeof (binds) === 'string' ? [binds] : binds;
let toAdd = [];
for (let i = 0; i < binds.length; i++) {
let funName = binds[i];
let oldFun = props[funName];
if (oldFun !== undefined) {
let newFun = function () {
return oldFun.apply(this.unigridCell, arguments);
}
toAdd.push(newFun);
props[funName] = newFun.bind(newFun);
}
}
toAdd.push(newFun);
props[funName] = newFun.bind(newFun);
}
}
let component = this.createCellForType(cellTypes, type, props);
for (let i = 0; i < toAdd.length; i++) {
toAdd[i].unigridCell = component;
}
return component;
}

static create(oCfg) {
const elems = oCfg.cells || [];
const arr = [];
const idCounter = idMaker();
let addProp = isDefined(oCfg, 'treeAmend') ?
{ treeAmend: oCfg.treeAmend } : undefined;

let cfg = tryAmend(oCfg, oCfg.item, oCfg.box);

for (let i of elems) {
arr.push(UnigridRow.createAndProcessCell(
i, cfg.item, cfg.box, cfg.renderAs, cfg.rowAs, cfg.mixIn, cfg.cellTypes, addProp, idCounter
));
let component = this.createCellForType(cellTypes, type, props);
for (let i = 0; i < toAdd.length; i++) {
toAdd[i].unigridCell = component;
}
return component;
}

const children = React.Children.map(cfg.children, (child) => {
const chCfg = Object.assign({}, child.props, { as: child });
arr.push(UnigridRow.createAndProcessCell(
chCfg, cfg.item, cfg.box, cfg.renderAs, cfg.rowAs, cfg.mixIn, cfg.cellTypes, addProp, idCounter
));
});
static create(oCfg) {
const elems = oCfg.cells || [];
const arr = [];
const idCounter = idMaker();
let addProp = isDefined(oCfg, 'treeAmend') ?
{ treeAmend: oCfg.treeAmend } : undefined;

let cfg = tryAmend(oCfg, oCfg.item, oCfg.box);

for (let i of elems) {
arr.push(UnigridRow.createAndProcessCell(
i, cfg.item, cfg.box, cfg.renderAs, cfg.rowAs, cfg.mixIn, cfg.cellTypes, addProp, idCounter
));
}

const cleaned = cleanProps(cfg);
return React.createElement(cfg.renderAs || 'tr', cleaned, arr);
}
const children = React.Children.map(cfg.children, (child) => {
const chCfg = Object.assign({}, child.props, { as: child });
arr.push(UnigridRow.createAndProcessCell(
chCfg, cfg.item, cfg.box, cfg.renderAs, cfg.rowAs, cfg.mixIn, cfg.cellTypes, addProp, idCounter
));
});

render() {
return UnigridRow.create(this.props);
}
const cleaned = cleanProps(cfg);
return React.createElement(cfg.renderAs || 'tr', cleaned, arr);
}

render() {
return UnigridRow.create(this.props);
}
}

export const UnigridHeaderRow = props => <UnigridRow rowAs='header' {...props} />;
54 changes: 27 additions & 27 deletions react-starter/src/UnigridSection.js
Original file line number Diff line number Diff line change
@@ -25,46 +25,46 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

import React from 'react';
import {cleanProps, createChildren} from './helpers';
import { cleanProps, createChildren } from 'src/helpers';

export class UnigridSection extends React.Component {
static _getSectionComponent(section) {
switch (section) {
case 'header': return UnigridHeader;
case 'body': return UnigridSegment;
case 'footer': return UnigridFooter;
static _getSectionComponent(section) {
switch (section) {
case 'header': return UnigridHeader;
case 'body': return UnigridSegment;
case 'footer': return UnigridFooter;
}
}
}

static create(cfg, box, props, counter, section, data, item) {
let children = createChildren(cfg, box, props, counter, data, item);
const cleaned = cleanProps(cfg);
Object.assign(cleaned, {
children: children, unfolded: true, key: counter.next().value
});
return React.createElement(this._getSectionComponent(section), cleaned);
}
static create(cfg, box, props, counter, section, data, item) {
let children = createChildren(cfg, box, props, counter, data, item);
const cleaned = cleanProps(cfg);
Object.assign(cleaned, {
children: children, unfolded: true, key: counter.next().value
});
return React.createElement(this._getSectionComponent(section), cleaned);
}

makeElement(name) {
const {unfolded, box, sectionCounter, data, item, ...cfg} = this.props;
let children = this.props.children;
if (!unfolded) {
children = createChildren(
cfg, box, cfg, sectionCounter, data, item);
makeElement(name) {
const { unfolded, box, sectionCounter, data, item, ...cfg } = this.props;
let children = this.props.children;
if (!unfolded) {
children = createChildren(
cfg, box, cfg, sectionCounter, data, item);
}
const cleaned = cleanProps(cfg);
return React.createElement(name, cleaned, children);
}
const cleaned = cleanProps(cfg);
return React.createElement(name, cleaned, children);
}
}

export class UnigridHeader extends UnigridSection {
render() {return this.makeElement(this.props.renderAs || 'thead');}
render() { return this.makeElement(this.props.renderAs || 'thead'); }
}

export class UnigridSegment extends UnigridSection {
render() {return this.makeElement(this.props.renderAs || 'tbody');}
render() { return this.makeElement(this.props.renderAs || 'tbody'); }
}

export class UnigridFooter extends UnigridSection {
render() {return this.makeElement(this.props.renderAs || 'tfoot');}
render() { return this.makeElement(this.props.renderAs || 'tfoot'); }
}
348 changes: 174 additions & 174 deletions react-starter/src/helpers.js

Large diffs are not rendered by default.

35 changes: 0 additions & 35 deletions react-starter/src/imports.js

This file was deleted.

1 change: 1 addition & 0 deletions react-starter/src/index.js
Original file line number Diff line number Diff line change
@@ -2,4 +2,5 @@ import React from "react"
import ReactDom from "react-dom"
import App from "./App"


ReactDom.render(<App />, document.getElementById('app'))
116 changes: 58 additions & 58 deletions react-starter/src/iterators.js
Original file line number Diff line number Diff line change
@@ -27,76 +27,76 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// *** Data iterators ***

export const isIterable = (obj) => {
// checks for null and undefined
if (obj == null) {
return false;
}
return typeof obj[Symbol.iterator] === 'function';
// checks for null and undefined
if (obj == null) {
return false;
}
return typeof obj[Symbol.iterator] === 'function';
}

export const getIterator = (pData, pSelect) => {
function addIterable(obj) {
return {[Symbol.iterator]: () => obj};
}
function addIterable(obj) {
return { [Symbol.iterator]: () => obj };
}

function makeAllIterator(data) {
let nextIndex = 0;
const obj = {
next: function() {
return nextIndex < data.length ?
{value: data[nextIndex++], done: false} : {done: true};
}
function makeAllIterator(data) {
let nextIndex = 0;
const obj = {
next: function () {
return nextIndex < data.length ?
{ value: data[nextIndex++], done: false } : { done: true };
}
}
return addIterable(obj);
}
return addIterable(obj);
}

function mkIterator(data, how, test) {
const nTest = test || function() {return true;};
let delivered = false;
const obj = {
next: function() {
if (!delivered && nTest(data)) {
delivered = true;
return {value: how(data), done: false};
function mkIterator(data, how, test) {
const nTest = test || function () { return true; };
let delivered = false;
const obj = {
next: function () {
if (!delivered && nTest(data)) {
delivered = true;
return { value: how(data), done: false };
}
return { done: true };
}
}
return {done: true};
}
return addIterable(obj);
}
return addIterable(obj);
}

function makeFirstIterator(data) {
return mkIterator(data, (d) => d[Symbol.iterator]().next().value);
}
function makeFirstIterator(data) {
return mkIterator(data, (d) => d[Symbol.iterator]().next().value);
}

function makeIteratorForItem(item) {
return mkIterator(item, (i) => i);
}
function makeIteratorForItem(item) {
return mkIterator(item, (i) => i);
}

function makeNumberIterator(data, select) {
const test = (d) => select >=0 && select < d.length;
return mkIterator(data, (d) => d[select], test);
}
function makeNumberIterator(data, select) {
const test = (d) => select >= 0 && select < d.length;
return mkIterator(data, (d) => d[select], test);
}

function makeStringIterator(data, select) {
if (select === 'all') {
if (isIterable(data)) {
return data;
} else {
return makeAllIterator(data);
}
} else if (select === 'first') {
if (isIterable(data)) {
return makeFirstIterator(data);
} else {
return makeIteratorForItem(data);
}
function makeStringIterator(data, select) {
if (select === 'all') {
if (isIterable(data)) {
return data;
} else {
return makeAllIterator(data);
}
} else if (select === 'first') {
if (isIterable(data)) {
return makeFirstIterator(data);
} else {
return makeIteratorForItem(data);
}
}
}
}

switch (typeof(pSelect)) {
case 'number': return makeNumberIterator(pData, pSelect);
case 'string': return makeStringIterator(pData, pSelect);
}
return undefined;
switch (typeof (pSelect)) {
case 'number': return makeNumberIterator(pData, pSelect);
case 'string': return makeStringIterator(pData, pSelect);
}
return undefined;
};
212 changes: 106 additions & 106 deletions react-starter/src/sorting.js
Original file line number Diff line number Diff line change
@@ -24,114 +24,114 @@ OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

import {isDefined, idMaker} from './helpers';
import { isDefined, idMaker } from 'src/helpers';

// *** Sorting functions ***

const _propertyFormatter = (props) => {
const nested = props.show.split('.');

let last = props.item;
for (let i = 0; i < nested.length; i++) {
if (!isDefined(last, nested[i])) {
return undefined;
const nested = props.show.split('.');

let last = props.item;
for (let i = 0; i < nested.length; i++) {
if (!isDefined(last, nested[i])) {
return undefined;
}
last = last[nested[i]];
}
last = last[nested[i]];
}
return last;
return last;
};

const _functionFormatter = (props) => props.show(props);

export const applyFormatter = (pProps) => {
let tShow = typeof(pProps.show);
switch(tShow) {
case 'string': return _propertyFormatter(pProps);
case 'function': return _functionFormatter(pProps);
}
return undefined;
let tShow = typeof (pProps.show);
switch (tShow) {
case 'string': return _propertyFormatter(pProps);
case 'function': return _functionFormatter(pProps);
}
return undefined;
};

const _compareString = (a, b) => {
const la = a.toLowerCase();
const lb = b.toLowerCase();
const la = a.toLowerCase();
const lb = b.toLowerCase();

if (la < lb) return -1;
if (la > lb) return 1;
return 0;
if (la < lb) return -1;
if (la > lb) return 1;
return 0;
}

const _compareAttributes = (oAttrA, oAttrB) => {
const noA = oAttrA === undefined || oAttrA === null;
const noB = oAttrB === undefined || oAttrB === null;
if (noA && noB) return 0;
if (noA) return 1; // put undefined/null last
if (noB) return -1;

const attrA = (typeof oAttrA === 'object') ? oAttrA.valueOf() : oAttrA;
const attrB = (typeof oAttrB === 'object') ? oAttrB.valueOf() : oAttrB;

const aType = typeof attrA;
const bType = typeof attrB;
const noA = oAttrA === undefined || oAttrA === null;
const noB = oAttrB === undefined || oAttrB === null;
if (noA && noB) return 0;
if (noA) return 1; // put undefined/null last
if (noB) return -1;

const attrA = (typeof oAttrA === 'object') ? oAttrA.valueOf() : oAttrA;
const attrB = (typeof oAttrB === 'object') ? oAttrB.valueOf() : oAttrB;

const aType = typeof attrA;
const bType = typeof attrB;

if (aType !== bType) {
if (aType === 'number' && bType === 'string') return -1;
if (aType === 'string' && bType === 'number') return 1;
return 0;
}

if (aType !== bType) {
if (aType === 'number' && bType === 'string') return -1;
if (aType === 'string' && bType === 'number') return 1;
if (aType === 'string') {
const retVal = _compareString(attrA, attrB);
if (retVal !== 0) return retVal;
} else if (aType === 'number') {
const retVal = attrA - attrB;
if (retVal !== 0) return retVal;
}
return 0;
}

if (aType === 'string') {
const retVal = _compareString(attrA, attrB);
if(retVal !== 0) return retVal;
} else if (aType === 'number') {
const retVal = attrA - attrB;
if (retVal !== 0) return retVal;
}
return 0;
}

const _compareObjects = (a, b, attrs, isAsc) => {
for (let i = 0; i < attrs.length; i++) {
const aVal = applyFormatter({show: attrs[i], item: a});
const bVal = applyFormatter({show: attrs[i], item: b});
const retVal = _compareAttributes(aVal, bVal);
if (retVal === 0) {
continue;
} else {
return isAsc ? retVal : -retVal;
for (let i = 0; i < attrs.length; i++) {
const aVal = applyFormatter({ show: attrs[i], item: a });
const bVal = applyFormatter({ show: attrs[i], item: b });
const retVal = _compareAttributes(aVal, bVal);
if (retVal === 0) {
continue;
} else {
return isAsc ? retVal : -retVal;
}
}
}
return 0;
return 0;
}

const getColumns = (box, fields) => {
switch(typeof(fields)) {
case 'undefined': return [box.column];
case 'function': return fields(box.column) || [];
case 'string': return [fields];
default: return fields;
}
switch (typeof (fields)) {
case 'undefined': return [box.column];
case 'function': return fields(box.column) || [];
case 'string': return [fields];
default: return fields;
}
}

// fields - The list of fields in the 'item' by which the input 'data'
// should be sorted. If it's a function then it will be called, with the
// selected column as its argument, to obtain the list of fields.
// defOrder - default order if 'box.order' isn't defined.
const _sorter = (data, box, fields, defOrder = 'asc') => {
const itemCounter = idMaker();
const nColumns = getColumns(box, fields);
const isAsc = (box.order || defOrder) === 'asc';
const comparer = (a, b) => _compareObjects(a, b, nColumns, isAsc);
const arr = [];
for (const i of data) {
arr.push(Object.assign({}, {_unigridId: itemCounter.next().value}, i));
}
return arr.sort(comparer);
const itemCounter = idMaker();
const nColumns = getColumns(box, fields);
const isAsc = (box.order || defOrder) === 'asc';
const comparer = (a, b) => _compareObjects(a, b, nColumns, isAsc);
const arr = [];
for (const i of data) {
arr.push(Object.assign({}, { _unigridId: itemCounter.next().value }, i));
}
return arr.sort(comparer);
}

export const getSorter = (colToFields, defOrder) => {
return (data, box) =>
_sorter(data, box, colToFields, defOrder);
return (data, box) =>
_sorter(data, box, colToFields, defOrder);
};

// 'column' is used to track a change in sorting order. This name is supplied
@@ -154,42 +154,42 @@ export const getSorter = (colToFields, defOrder) => {
// i.e. if 'box.column' != 'column. Otherwise the order will alternate.
// The first argument can be a function to override this with a new behaviour.
export const updateBox = (box, column, order) => {
const alternate = (o) => o === 'asc' ? 'desc' : 'asc';
if (typeof(column) === 'function') {
box = column(box, order);
} else {
const nOrder = order || 'new:asc';
let {column: bColumn, order: bOrder} = box;
const isNew = !bColumn || bColumn !== column;
bColumn = isNew ? column : bColumn;

switch(nOrder) {
case 'alter':
bOrder = alternate(bOrder);
break;
case 'old:alter':
bOrder = isNew ? bOrder : alternate(bOrder);
break;
case 'asc':
bOrder = 'asc';
break;
case 'desc':
bOrder = 'desc';
break;
case 'new:asc':
bOrder = isNew ? 'asc' : alternate(bOrder);
break;
case 'new:desc':
bOrder = isNew ? 'desc' : alternate(bOrder);
break;
const alternate = (o) => o === 'asc' ? 'desc' : 'asc';
if (typeof (column) === 'function') {
box = column(box, order);
} else {
const nOrder = order || 'new:asc';
let { column: bColumn, order: bOrder } = box;
const isNew = !bColumn || bColumn !== column;
bColumn = isNew ? column : bColumn;

switch (nOrder) {
case 'alter':
bOrder = alternate(bOrder);
break;
case 'old:alter':
bOrder = isNew ? bOrder : alternate(bOrder);
break;
case 'asc':
bOrder = 'asc';
break;
case 'desc':
bOrder = 'desc';
break;
case 'new:asc':
bOrder = isNew ? 'asc' : alternate(bOrder);
break;
case 'new:desc':
bOrder = isNew ? 'desc' : alternate(bOrder);
break;
}

box = Object.assign({}, box, { column: bColumn, order: bOrder });
}

box = Object.assign({}, box, {column: bColumn, order: bOrder});
}
return box;
return box;
};

export const sort = (unigrid, column, order) => {
let box = unigrid.getBox();
unigrid.setBox(updateBox(box, column, order));
let box = unigrid.getBox();
unigrid.setBox(updateBox(box, column, order));
};
4 changes: 0 additions & 4 deletions react-starter/webpack.config.js
Original file line number Diff line number Diff line change
@@ -21,10 +21,6 @@ module.exports = {
"sass-loader",
],
},
{
test: /\.json$/,
loader: 'json-loader'
}
],
},