mirror of
https://gitcode.com/gh_mirrors/hy/Hydro.git
synced 2026-10-20 17:46:28 +08:00
add ui
This commit is contained in:
1 parent
777a4bc927
commit
9c45527522
396 files changed
+13772
No files matched your search
@@ -0,0 +1,3 @@
|
||||
export default function (ms) {
|
||||
return new Promise(resolve => setTimeout(resolve, ms));
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
/**
|
||||
*
|
||||
* @param {Event} ev
|
||||
* @param {String} targetUrl
|
||||
* @param {Boolean} alwaysOpenInNewWindow
|
||||
*/
|
||||
export default function emulateAnchorClick(ev, targetUrl, alwaysOpenInNewWindow = false) {
|
||||
let openInNewWindow;
|
||||
if (alwaysOpenInNewWindow) {
|
||||
openInNewWindow = true;
|
||||
} else {
|
||||
openInNewWindow = (ev.ctrlKey || ev.shiftKey || ev.metaKey);
|
||||
}
|
||||
if (openInNewWindow) {
|
||||
window.open(targetUrl);
|
||||
} else {
|
||||
window.location.href = targetUrl;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
import substitute from './substitute';
|
||||
|
||||
export default function i18n(str, ...params) {
|
||||
if (window.LOCALES && window.LOCALES[str]) {
|
||||
return substitute(window.LOCALES[str], params);
|
||||
}
|
||||
return substitute(str, params);
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
export default async function loadReactRedux(storeReducer) {
|
||||
const React = await import('react');
|
||||
const { render, unmountComponentAtNode } = await import('react-dom');
|
||||
const { Provider } = await import('react-redux');
|
||||
const { createStore, applyMiddleware } = await import('redux');
|
||||
const { default: reduxThunk } = await import('redux-thunk');
|
||||
const { default: reduxPromise } = await import('redux-promise-middleware');
|
||||
|
||||
const reduxMiddlewares = [];
|
||||
reduxMiddlewares.push(reduxThunk);
|
||||
reduxMiddlewares.push(reduxPromise());
|
||||
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
const { createLogger } = await import('redux-logger');
|
||||
reduxMiddlewares.push(createLogger({
|
||||
collapsed: true,
|
||||
duration: true,
|
||||
}));
|
||||
}
|
||||
|
||||
const store = createStore(storeReducer, applyMiddleware(...reduxMiddlewares));
|
||||
|
||||
return {
|
||||
React,
|
||||
render,
|
||||
unmountComponentAtNode,
|
||||
Provider,
|
||||
store,
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
export function isAbove(width) {
|
||||
if (window.matchMedia) {
|
||||
return window.matchMedia(`(min-width: ${width}px)`).matches;
|
||||
}
|
||||
return window.innerWidth >= width;
|
||||
}
|
||||
|
||||
export function isBelow(width) {
|
||||
if (window.matchMedia) {
|
||||
return window.matchMedia(`(max-width: ${width}px)`).matches;
|
||||
}
|
||||
return window.innerWidth <= width;
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
/* eslint-disable */
|
||||
|
||||
// https://github.com/andrasq/node-mongoid-js/blob/master/mongoid.js
|
||||
|
||||
export function parse(idstring) {
|
||||
if (typeof idstring !== 'string') {
|
||||
idstring = String(idstring);
|
||||
}
|
||||
return {
|
||||
timestamp: parseInt(idstring.slice( 0, 0+8), 16),
|
||||
machineid: parseInt(idstring.slice( 8, 8+6), 16),
|
||||
pid: parseInt(idstring.slice(14, 14+4), 16),
|
||||
sequence: parseInt(idstring.slice(18, 18+6), 16),
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
export default function parseQueryString(str) {
|
||||
const obj = {};
|
||||
(str || document.location.search)
|
||||
.replace(/(^\?)/, '')
|
||||
.split('&')
|
||||
.forEach((n) => {
|
||||
const [key, value] = n.split('=').map(v => decodeURIComponent(v));
|
||||
obj[key] = value;
|
||||
});
|
||||
return obj;
|
||||
}
|
||||
@@ -0,0 +1,150 @@
|
||||
// Modified from jquery-pjax to support multiple fragments and jQuery 3.0
|
||||
// https://github.com/defunkt/jquery-pjax/blob/master/jquery.pjax.js
|
||||
|
||||
import uuid from 'uuid/v4';
|
||||
|
||||
import Notification from 'vj/components/notification';
|
||||
import NProgress from 'vj/components/nprogress';
|
||||
import request from './request';
|
||||
|
||||
const pjax = {};
|
||||
|
||||
let currentState = null;
|
||||
let currentXHR = null;
|
||||
let inProgress = 0;
|
||||
|
||||
function cancelLastXHR() {
|
||||
if (currentXHR && currentXHR.readyState < 4) {
|
||||
currentXHR.abort();
|
||||
currentXHR = null;
|
||||
}
|
||||
}
|
||||
|
||||
function canonicalizeUrl(url) {
|
||||
const a = document.createElement('a');
|
||||
a.href = url;
|
||||
return a.href;
|
||||
}
|
||||
|
||||
function extractMetaData(requestOption, response) {
|
||||
const metaData = {
|
||||
title: response.title ? response.title : document.title,
|
||||
url: response.url ? response.url : requestOption.url,
|
||||
};
|
||||
metaData.url = canonicalizeUrl(metaData.url);
|
||||
return metaData;
|
||||
}
|
||||
|
||||
function incProgress() {
|
||||
inProgress++;
|
||||
NProgress.done();
|
||||
NProgress.start();
|
||||
}
|
||||
|
||||
function decProgress() {
|
||||
inProgress--;
|
||||
if (inProgress === 0) {
|
||||
NProgress.done();
|
||||
}
|
||||
}
|
||||
|
||||
pjax.request = async (opt) => {
|
||||
const options = {
|
||||
method: 'get',
|
||||
push: true,
|
||||
...opt,
|
||||
};
|
||||
if (!currentState) {
|
||||
// create initial state
|
||||
currentState = {
|
||||
id: uuid(),
|
||||
options: {
|
||||
url: window.location.href,
|
||||
},
|
||||
};
|
||||
window.history.replaceState(currentState, null);
|
||||
}
|
||||
cancelLastXHR();
|
||||
if (options.push) {
|
||||
// in popstate, options.push === false
|
||||
window.history.pushState(null, null, options.url);
|
||||
}
|
||||
incProgress();
|
||||
try {
|
||||
const data = await request.ajax({
|
||||
beforeSend(xhr) {
|
||||
currentXHR = xhr;
|
||||
},
|
||||
...options,
|
||||
});
|
||||
const meta = extractMetaData(options, data);
|
||||
currentState = {
|
||||
id: uuid(),
|
||||
options: opt,
|
||||
};
|
||||
if (options.push) {
|
||||
window.history.replaceState(currentState, null, meta.url);
|
||||
}
|
||||
document.title = meta.title;
|
||||
data.fragments.forEach((fragment) => {
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
if (fragment.html === undefined) {
|
||||
// eslint-disable-next-line quotes
|
||||
throw new Error(`Fragement should contain 'html'`);
|
||||
}
|
||||
}
|
||||
const $el = $(fragment.html.trim());
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
if ($el.length === 0) {
|
||||
// eslint-disable-next-line quotes
|
||||
throw new Error(`Unable to build elements from fragment 'html'`);
|
||||
}
|
||||
}
|
||||
const fragmentId = $el.attr('data-fragment-id');
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
if (!fragmentId) {
|
||||
// eslint-disable-next-line quotes
|
||||
throw new Error(`Unable to extract fragment id from fragment 'html'`);
|
||||
}
|
||||
}
|
||||
const $target = $(`[data-fragment-id="${fragmentId}"]`);
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
if ($target.length === 0) {
|
||||
// eslint-disable-next-line quotes
|
||||
throw new Error(`Unable to get target fragment from fragment id`);
|
||||
}
|
||||
}
|
||||
$target.trigger('vjContentRemove');
|
||||
$target.replaceWith($el);
|
||||
$el.trigger('vjContentNew');
|
||||
});
|
||||
} catch (err) {
|
||||
if (!err.aborted) {
|
||||
Notification.error(err.message);
|
||||
console.log(err);
|
||||
}
|
||||
} finally {
|
||||
decProgress();
|
||||
}
|
||||
};
|
||||
|
||||
function handlePopState(ev) {
|
||||
if (!ev.originalEvent) {
|
||||
return;
|
||||
}
|
||||
const { state } = ev.originalEvent;
|
||||
if (!state) {
|
||||
return;
|
||||
}
|
||||
if (!state.id || (currentState && state.id === currentState.id)) {
|
||||
return;
|
||||
}
|
||||
pjax.request({
|
||||
...state.options,
|
||||
push: false,
|
||||
});
|
||||
}
|
||||
|
||||
$(window).on('popstate', handlePopState);
|
||||
|
||||
export default pjax;
|
||||
@@ -0,0 +1,79 @@
|
||||
import i18n from './i18n';
|
||||
|
||||
const request = {
|
||||
/**
|
||||
* @param {object} options
|
||||
*/
|
||||
async ajax(options) {
|
||||
return new Promise((resolve, reject) => {
|
||||
$
|
||||
.ajax({
|
||||
dataType: 'json',
|
||||
...options,
|
||||
})
|
||||
.fail((jqXHR, textStatus, errorThrown) => {
|
||||
if (textStatus === 'abort') {
|
||||
const err = new Error(i18n('Aborted'));
|
||||
err.aborted = true;
|
||||
reject(err);
|
||||
} else if (jqXHR.readyState === 0) {
|
||||
reject(new Error(i18n('Network error')));
|
||||
} else if (errorThrown instanceof Error) {
|
||||
reject(errorThrown);
|
||||
} else if (typeof jqXHR.responseJSON === 'object' && jqXHR.responseJSON.error) {
|
||||
reject(new Error(jqXHR.responseJSON.error.message));
|
||||
} else {
|
||||
reject(new Error(textStatus));
|
||||
}
|
||||
})
|
||||
.done(resolve);
|
||||
});
|
||||
},
|
||||
|
||||
/**
|
||||
* @param {string} url
|
||||
* @param {JQueryStatic | Node | string | object} dataOrForm
|
||||
* @param {object} options
|
||||
*/
|
||||
post(url, dataOrForm = {}, options = {}) {
|
||||
let postData;
|
||||
if (dataOrForm instanceof jQuery && dataOrForm.is('form')) {
|
||||
// $form
|
||||
postData = dataOrForm.serialize();
|
||||
} else if (dataOrForm instanceof Node && $(dataOrForm).is('form')) {
|
||||
// form
|
||||
postData = $(dataOrForm).serialize();
|
||||
} else if (typeof dataOrForm === 'string') {
|
||||
// foo=bar&box=boz
|
||||
postData = dataOrForm;
|
||||
} else {
|
||||
// {foo: 'bar'}
|
||||
postData = $.param({
|
||||
csrf_token: UiContext.csrf_token,
|
||||
...dataOrForm,
|
||||
}, true);
|
||||
}
|
||||
return request.ajax({
|
||||
url,
|
||||
method: 'post',
|
||||
data: postData,
|
||||
...options,
|
||||
});
|
||||
},
|
||||
|
||||
/**
|
||||
* @param {string} url
|
||||
* @param {object} qs
|
||||
* @param {object} options
|
||||
*/
|
||||
get(url, qs = {}, options = {}) {
|
||||
return request.ajax({
|
||||
url,
|
||||
data: qs,
|
||||
method: 'get',
|
||||
...options,
|
||||
});
|
||||
},
|
||||
};
|
||||
|
||||
export default request;
|
||||
@@ -0,0 +1,57 @@
|
||||
import 'jquery.easing';
|
||||
|
||||
export async function slideDown($element, duration, fromCss = {}, toCss = {}) {
|
||||
const originalStyl = $element.attr('style') || '';
|
||||
$element.css({
|
||||
position: 'absolute',
|
||||
visibility: 'none',
|
||||
display: 'block',
|
||||
});
|
||||
const height = $element.outerHeight();
|
||||
$element.attr('style', originalStyl);
|
||||
$element.css({
|
||||
height: 0,
|
||||
overflow: 'hidden',
|
||||
display: 'block',
|
||||
...fromCss,
|
||||
});
|
||||
$element.height();
|
||||
await $element
|
||||
.transition({
|
||||
height,
|
||||
...toCss,
|
||||
}, {
|
||||
duration,
|
||||
easing: 'easeOutCubic',
|
||||
})
|
||||
.promise();
|
||||
$element.attr('style', originalStyl);
|
||||
$element.css({
|
||||
display: 'block',
|
||||
});
|
||||
}
|
||||
|
||||
export async function slideUp($element, duration, fromCss = {}, toCss = {}) {
|
||||
const originalStyl = $element.attr('style') || '';
|
||||
const height = $element.outerHeight();
|
||||
$element.css({
|
||||
height,
|
||||
overflow: 'hidden',
|
||||
display: 'block',
|
||||
...fromCss,
|
||||
});
|
||||
$element.height();
|
||||
await $element
|
||||
.transition({
|
||||
height: 0,
|
||||
...toCss,
|
||||
}, {
|
||||
duration,
|
||||
easing: 'easeOutCubic',
|
||||
})
|
||||
.promise();
|
||||
$element.attr('style', originalStyl);
|
||||
$element.css({
|
||||
display: 'none',
|
||||
});
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
export default function substitute(str, obj) {
|
||||
return str.replace(/\{([^{}]+)\}/g, (match, key) => {
|
||||
if (obj[key] !== undefined) {
|
||||
return String(obj[key]);
|
||||
}
|
||||
return `{${key}}`;
|
||||
});
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
import _ from 'lodash';
|
||||
|
||||
export default function tpl(pieces, ...substitutions) {
|
||||
let result = pieces[0];
|
||||
for (let i = 0; i < substitutions.length; ++i) {
|
||||
const subst = substitutions[i];
|
||||
let substHtml;
|
||||
if (typeof subst === 'object' && subst.templateRaw) {
|
||||
substHtml = subst.html;
|
||||
} else {
|
||||
substHtml = _.escape(String(subst));
|
||||
}
|
||||
result += substHtml + pieces[i + 1];
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
export function rawHtml(html) {
|
||||
return {
|
||||
templateRaw: true,
|
||||
html,
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
let zIndexCurrent = 1000;
|
||||
|
||||
const manager = {
|
||||
getCurrent() {
|
||||
return zIndexCurrent;
|
||||
},
|
||||
getNext() {
|
||||
return ++zIndexCurrent;
|
||||
},
|
||||
};
|
||||
|
||||
export default manager;
|
||||
Reference in new issue
Block a user