Add OC.Util to the server bundle

Signed-off-by: Christoph Wurst <christoph@winzerhof-wurst.at>
This commit is contained in:
Christoph Wurst 2019-01-31 18:50:59 +01:00
parent 9de02d3267
commit 0d43ef06f5
No known key found for this signature in database
GPG Key ID: CC42AC2A7F0E56D8
8 changed files with 529 additions and 427 deletions

57
core/js/dist/main.js vendored

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -1311,39 +1311,6 @@ function initCore() {
$(document).ready(initCore);
/**
* Returns a human readable file size
* @param {number} size Size in bytes
* @param {boolean} skipSmallSizes return '< 1 kB' for small files
* @return {string}
*/
function humanFileSize(size, skipSmallSizes) {
var humanList = ['B', 'KB', 'MB', 'GB', 'TB'];
// Calculate Log with base 1024: size = 1024 ** order
var order = size > 0 ? Math.floor(Math.log(size) / Math.log(1024)) : 0;
// Stay in range of the byte sizes that are defined
order = Math.min(humanList.length - 1, order);
var readableFormat = humanList[order];
var relativeSize = (size / Math.pow(1024, order)).toFixed(1);
if(skipSmallSizes === true && order === 0) {
if(relativeSize !== "0.0"){
return '< 1 KB';
} else {
return '0 KB';
}
}
if(order < 2){
relativeSize = parseFloat(relativeSize).toFixed(0);
}
else if(relativeSize.substr(relativeSize.length-2,2)==='.0'){
relativeSize=relativeSize.substr(0,relativeSize.length-2);
}
else{
relativeSize = parseFloat(relativeSize).toLocaleString(OC.getCanonicalLocale());
}
return relativeSize + ' ' + readableFormat;
}
/**
* Format an UNIX timestamp to a human understandable format
* @param {number} timestamp UNIX timestamp
@ -1379,381 +1346,6 @@ function relative_modified_date(timestamp) {
return OC.Util.relativeModifiedDate(timestamp * 1000);
}
/**
* Utility functions
* @namespace
*/
OC.Util = {
// TODO: remove original functions from global namespace
humanFileSize: humanFileSize,
/**
* Returns a file size in bytes from a humanly readable string
* Makes 2kB to 2048.
* Inspired by computerFileSize in helper.php
* @param {string} string file size in human readable format
* @return {number} or null if string could not be parsed
*
*
*/
computerFileSize: function (string) {
if (typeof string !== 'string') {
return null;
}
var s = string.toLowerCase().trim();
var bytes = null;
var bytesArray = {
'b' : 1,
'k' : 1024,
'kb': 1024,
'mb': 1024 * 1024,
'm' : 1024 * 1024,
'gb': 1024 * 1024 * 1024,
'g' : 1024 * 1024 * 1024,
'tb': 1024 * 1024 * 1024 * 1024,
't' : 1024 * 1024 * 1024 * 1024,
'pb': 1024 * 1024 * 1024 * 1024 * 1024,
'p' : 1024 * 1024 * 1024 * 1024 * 1024
};
var matches = s.match(/^[\s+]?([0-9]*)(\.([0-9]+))?( +)?([kmgtp]?b?)$/i);
if (matches !== null) {
bytes = parseFloat(s);
if (!isFinite(bytes)) {
return null;
}
} else {
return null;
}
if (matches[5]) {
bytes = bytes * bytesArray[matches[5]];
}
bytes = Math.round(bytes);
return bytes;
},
/**
* @param timestamp
* @param format
* @returns {string} timestamp formatted as requested
*/
formatDate: function (timestamp, format) {
format = format || "LLL";
return moment(timestamp).format(format);
},
/**
* @param timestamp
* @returns {string} human readable difference from now
*/
relativeModifiedDate: function (timestamp) {
var diff = moment().diff(moment(timestamp));
if (diff >= 0 && diff < 45000 ) {
return t('core', 'seconds ago');
}
return moment(timestamp).fromNow();
},
/**
* Returns whether this is IE
*
* @return {bool} true if this is IE, false otherwise
*/
isIE: function() {
return $('html').hasClass('ie');
},
/**
* Returns the width of a generic browser scrollbar
*
* @return {int} width of scrollbar
*/
getScrollBarWidth: function() {
if (this._scrollBarWidth) {
return this._scrollBarWidth;
}
var inner = document.createElement('p');
inner.style.width = "100%";
inner.style.height = "200px";
var outer = document.createElement('div');
outer.style.position = "absolute";
outer.style.top = "0px";
outer.style.left = "0px";
outer.style.visibility = "hidden";
outer.style.width = "200px";
outer.style.height = "150px";
outer.style.overflow = "hidden";
outer.appendChild (inner);
document.body.appendChild (outer);
var w1 = inner.offsetWidth;
outer.style.overflow = 'scroll';
var w2 = inner.offsetWidth;
if(w1 === w2) {
w2 = outer.clientWidth;
}
document.body.removeChild (outer);
this._scrollBarWidth = (w1 - w2);
return this._scrollBarWidth;
},
/**
* Remove the time component from a given date
*
* @param {Date} date date
* @return {Date} date with stripped time
*/
stripTime: function(date) {
// FIXME: likely to break when crossing DST
// would be better to use a library like momentJS
return new Date(date.getFullYear(), date.getMonth(), date.getDate());
},
_chunkify: function(t) {
// Adapted from http://my.opera.com/GreyWyvern/blog/show.dml/1671288
var tz = [], x = 0, y = -1, n = 0, code, c;
while (x < t.length) {
c = t.charAt(x);
// only include the dot in strings
var m = ((!n && c === '.') || (c >= '0' && c <= '9'));
if (m !== n) {
// next chunk
y++;
tz[y] = '';
n = m;
}
tz[y] += c;
x++;
}
return tz;
},
/**
* Compare two strings to provide a natural sort
* @param a first string to compare
* @param b second string to compare
* @return -1 if b comes before a, 1 if a comes before b
* or 0 if the strings are identical
*/
naturalSortCompare: function(a, b) {
var x;
var aa = OC.Util._chunkify(a);
var bb = OC.Util._chunkify(b);
for (x = 0; aa[x] && bb[x]; x++) {
if (aa[x] !== bb[x]) {
var aNum = Number(aa[x]), bNum = Number(bb[x]);
// note: == is correct here
if (aNum == aa[x] && bNum == bb[x]) {
return aNum - bNum;
} else {
// Note: This locale setting isn't supported by all browsers but for the ones
// that do there will be more consistency between client-server sorting
return aa[x].localeCompare(bb[x], OC.getLanguage());
}
}
}
return aa.length - bb.length;
},
/**
* Calls the callback in a given interval until it returns true
* @param {function} callback
* @param {integer} interval in milliseconds
*/
waitFor: function(callback, interval) {
var internalCallback = function() {
if(callback() !== true) {
setTimeout(internalCallback, interval);
}
};
internalCallback();
},
/**
* Checks if a cookie with the given name is present and is set to the provided value.
* @param {string} name name of the cookie
* @param {string} value value of the cookie
* @return {boolean} true if the cookie with the given name has the given value
*/
isCookieSetToValue: function(name, value) {
var cookies = document.cookie.split(';');
for (var i=0; i < cookies.length; i++) {
var cookie = cookies[i].split('=');
if (cookie[0].trim() === name && cookie[1].trim() === value) {
return true;
}
}
return false;
}
};
/**
* Utility class for the history API,
* includes fallback to using the URL hash when
* the browser doesn't support the history API.
*
* @namespace
*/
OC.Util.History = {
_handlers: [],
/**
* Push the current URL parameters to the history stack
* and change the visible URL.
* Note: this includes a workaround for IE8/IE9 that uses
* the hash part instead of the search part.
*
* @param {Object|string} params to append to the URL, can be either a string
* or a map
* @param {string} [url] URL to be used, otherwise the current URL will be used,
* using the params as query string
* @param {boolean} [replace=false] whether to replace instead of pushing
*/
_pushState: function(params, url, replace) {
var strParams;
if (typeof(params) === 'string') {
strParams = params;
}
else {
strParams = OC.buildQueryString(params);
}
if (window.history.pushState) {
url = url || location.pathname + '?' + strParams;
// Workaround for bug with SVG and window.history.pushState on Firefox < 51
// https://bugzilla.mozilla.org/show_bug.cgi?id=652991
var isFirefox = navigator.userAgent.toLowerCase().indexOf('firefox') > -1;
if (isFirefox && parseInt(navigator.userAgent.split('/').pop()) < 51) {
var patterns = document.querySelectorAll('[fill^="url(#"], [stroke^="url(#"], [filter^="url(#invert"]');
for (var i = 0, ii = patterns.length, pattern; i < ii; i++) {
pattern = patterns[i];
pattern.style.fill = pattern.style.fill;
pattern.style.stroke = pattern.style.stroke;
pattern.removeAttribute("filter");
pattern.setAttribute("filter", "url(#invert)");
}
}
if (replace) {
window.history.replaceState(params, '', url);
} else {
window.history.pushState(params, '', url);
}
}
// use URL hash for IE8
else {
window.location.hash = '?' + strParams;
// inhibit next onhashchange that just added itself
// to the event queue
this._cancelPop = true;
}
},
/**
* Push the current URL parameters to the history stack
* and change the visible URL.
* Note: this includes a workaround for IE8/IE9 that uses
* the hash part instead of the search part.
*
* @param {Object|string} params to append to the URL, can be either a string
* or a map
* @param {string} [url] URL to be used, otherwise the current URL will be used,
* using the params as query string
*/
pushState: function(params, url) {
return this._pushState(params, url, false);
},
/**
* Push the current URL parameters to the history stack
* and change the visible URL.
* Note: this includes a workaround for IE8/IE9 that uses
* the hash part instead of the search part.
*
* @param {Object|string} params to append to the URL, can be either a string
* or a map
* @param {string} [url] URL to be used, otherwise the current URL will be used,
* using the params as query string
*/
replaceState: function(params, url) {
return this._pushState(params, url, true);
},
/**
* Add a popstate handler
*
* @param handler function
*/
addOnPopStateHandler: function(handler) {
this._handlers.push(handler);
},
/**
* Parse a query string from the hash part of the URL.
* (workaround for IE8 / IE9)
*/
_parseHashQuery: function() {
var hash = window.location.hash,
pos = hash.indexOf('?');
if (pos >= 0) {
return hash.substr(pos + 1);
}
if (hash.length) {
// remove hash sign
return hash.substr(1);
}
return '';
},
_decodeQuery: function(query) {
return query.replace(/\+/g, ' ');
},
/**
* Parse the query/search part of the URL.
* Also try and parse it from the URL hash (for IE8)
*
* @return map of parameters
*/
parseUrlQuery: function() {
var query = this._parseHashQuery(),
params;
// try and parse from URL hash first
if (query) {
params = OC.parseQueryString(this._decodeQuery(query));
}
// else read from query attributes
params = _.extend(params || {}, OC.parseQueryString(this._decodeQuery(location.search)));
return params || {};
},
_onPopState: function(e) {
if (this._cancelPop) {
this._cancelPop = false;
return;
}
var params;
if (!this._handlers.length) {
return;
}
params = (e && e.state);
if (_.isString(params)) {
params = OC.parseQueryString(params);
} else if (!params) {
params = this.parseUrlQuery() || {};
}
for (var i = 0; i < this._handlers.length; i++) {
this._handlers[i](params);
}
}
};
// fallback to hashchange when no history support
if (window.history.pushState) {
window.onpopstate = _.bind(OC.Util.History._onPopState, OC.Util.History);

View File

@ -30,6 +30,7 @@ import Notification from './notification'
import PasswordConfirmation from './password-confirmation'
import Plugins from './plugins'
import search from './search'
import Util from './util'
/** @namespace OC */
export default {
@ -44,4 +45,5 @@ export default {
PasswordConfirmation,
Plugins,
search,
Util,
}

183
core/src/OC/util-history.js Normal file
View File

@ -0,0 +1,183 @@
/*
* @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
*
* @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
*
* @license GNU AGPL version 3 or any later version
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation, either version 3 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
import _ from 'underscore'
import OC from './index'
/**
* Utility class for the history API,
* includes fallback to using the URL hash when
* the browser doesn't support the history API.
*
* @namespace OC.Util.History
*/
export default {
_handlers: [],
/**
* Push the current URL parameters to the history stack
* and change the visible URL.
* Note: this includes a workaround for IE8/IE9 that uses
* the hash part instead of the search part.
*
* @param {Object|string} params to append to the URL, can be either a string
* or a map
* @param {string} [url] URL to be used, otherwise the current URL will be used,
* using the params as query string
* @param {boolean} [replace=false] whether to replace instead of pushing
*/
_pushState: function (params, url, replace) {
var strParams;
if (typeof (params) === 'string') {
strParams = params;
} else {
strParams = OC.buildQueryString(params);
}
if (window.history.pushState) {
url = url || location.pathname + '?' + strParams;
// Workaround for bug with SVG and window.history.pushState on Firefox < 51
// https://bugzilla.mozilla.org/show_bug.cgi?id=652991
var isFirefox = navigator.userAgent.toLowerCase().indexOf('firefox') > -1;
if (isFirefox && parseInt(navigator.userAgent.split('/').pop()) < 51) {
var patterns = document.querySelectorAll('[fill^="url(#"], [stroke^="url(#"], [filter^="url(#invert"]');
for (var i = 0, ii = patterns.length, pattern; i < ii; i++) {
pattern = patterns[i];
pattern.style.fill = pattern.style.fill;
pattern.style.stroke = pattern.style.stroke;
pattern.removeAttribute("filter");
pattern.setAttribute("filter", "url(#invert)");
}
}
if (replace) {
window.history.replaceState(params, '', url);
} else {
window.history.pushState(params, '', url);
}
}
// use URL hash for IE8
else {
window.location.hash = '?' + strParams;
// inhibit next onhashchange that just added itself
// to the event queue
this._cancelPop = true;
}
},
/**
* Push the current URL parameters to the history stack
* and change the visible URL.
* Note: this includes a workaround for IE8/IE9 that uses
* the hash part instead of the search part.
*
* @param {Object|string} params to append to the URL, can be either a string
* or a map
* @param {string} [url] URL to be used, otherwise the current URL will be used,
* using the params as query string
*/
pushState: function (params, url) {
return this._pushState(params, url, false);
},
/**
* Push the current URL parameters to the history stack
* and change the visible URL.
* Note: this includes a workaround for IE8/IE9 that uses
* the hash part instead of the search part.
*
* @param {Object|string} params to append to the URL, can be either a string
* or a map
* @param {string} [url] URL to be used, otherwise the current URL will be used,
* using the params as query string
*/
replaceState: function (params, url) {
return this._pushState(params, url, true);
},
/**
* Add a popstate handler
*
* @param handler function
*/
addOnPopStateHandler: function (handler) {
this._handlers.push(handler);
},
/**
* Parse a query string from the hash part of the URL.
* (workaround for IE8 / IE9)
*/
_parseHashQuery: function () {
var hash = window.location.hash,
pos = hash.indexOf('?');
if (pos >= 0) {
return hash.substr(pos + 1);
}
if (hash.length) {
// remove hash sign
return hash.substr(1);
}
return '';
},
_decodeQuery: function (query) {
return query.replace(/\+/g, ' ');
},
/**
* Parse the query/search part of the URL.
* Also try and parse it from the URL hash (for IE8)
*
* @return map of parameters
*/
parseUrlQuery: function () {
var query = this._parseHashQuery(),
params;
// try and parse from URL hash first
if (query) {
params = OC.parseQueryString(this._decodeQuery(query));
}
// else read from query attributes
params = _.extend(params || {}, OC.parseQueryString(this._decodeQuery(location.search)));
return params || {};
},
_onPopState: function (e) {
if (this._cancelPop) {
this._cancelPop = false;
return;
}
var params;
if (!this._handlers.length) {
return;
}
params = (e && e.state);
if (_.isString(params)) {
params = OC.parseQueryString(params);
} else if (!params) {
params = this.parseUrlQuery() || {};
}
for (var i = 0; i < this._handlers.length; i++) {
this._handlers[i](params);
}
}
}

251
core/src/OC/util.js Normal file
View File

@ -0,0 +1,251 @@
/* global t */
/*
* @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
*
* @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
*
* @license GNU AGPL version 3 or any later version
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation, either version 3 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
import $ from 'jquery'
import moment from 'moment'
import History from './util-history'
import OC from './index'
import humanFileSize from '../Util/human-file-size'
/**
* Utility functions
* @namespace OC.Util
*/
export default {
History,
// TODO: remove original functions from global namespace
humanFileSize,
/**
* Returns a file size in bytes from a humanly readable string
* Makes 2kB to 2048.
* Inspired by computerFileSize in helper.php
* @param {string} string file size in human readable format
* @return {number} or null if string could not be parsed
*
*
*/
computerFileSize: function (string) {
if (typeof string !== 'string') {
return null;
}
var s = string.toLowerCase().trim();
var bytes = null;
var bytesArray = {
'b': 1,
'k': 1024,
'kb': 1024,
'mb': 1024 * 1024,
'm': 1024 * 1024,
'gb': 1024 * 1024 * 1024,
'g': 1024 * 1024 * 1024,
'tb': 1024 * 1024 * 1024 * 1024,
't': 1024 * 1024 * 1024 * 1024,
'pb': 1024 * 1024 * 1024 * 1024 * 1024,
'p': 1024 * 1024 * 1024 * 1024 * 1024
};
var matches = s.match(/^[\s+]?([0-9]*)(\.([0-9]+))?( +)?([kmgtp]?b?)$/i);
if (matches !== null) {
bytes = parseFloat(s);
if (!isFinite(bytes)) {
return null;
}
} else {
return null;
}
if (matches[5]) {
bytes = bytes * bytesArray[matches[5]];
}
bytes = Math.round(bytes);
return bytes;
},
/**
* @param timestamp
* @param format
* @returns {string} timestamp formatted as requested
*/
formatDate: function (timestamp, format) {
format = format || "LLL";
return moment(timestamp).format(format);
},
/**
* @param timestamp
* @returns {string} human readable difference from now
*/
relativeModifiedDate: function (timestamp) {
var diff = moment().diff(moment(timestamp));
if (diff >= 0 && diff < 45000) {
return t('core', 'seconds ago');
}
return moment(timestamp).fromNow();
},
/**
* Returns whether this is IE
*
* @return {bool} true if this is IE, false otherwise
*/
isIE: function () {
return $('html').hasClass('ie');
},
/**
* Returns the width of a generic browser scrollbar
*
* @return {int} width of scrollbar
*/
getScrollBarWidth: function () {
if (this._scrollBarWidth) {
return this._scrollBarWidth;
}
var inner = document.createElement('p');
inner.style.width = "100%";
inner.style.height = "200px";
var outer = document.createElement('div');
outer.style.position = "absolute";
outer.style.top = "0px";
outer.style.left = "0px";
outer.style.visibility = "hidden";
outer.style.width = "200px";
outer.style.height = "150px";
outer.style.overflow = "hidden";
outer.appendChild(inner);
document.body.appendChild(outer);
var w1 = inner.offsetWidth;
outer.style.overflow = 'scroll';
var w2 = inner.offsetWidth;
if (w1 === w2) {
w2 = outer.clientWidth;
}
document.body.removeChild(outer);
this._scrollBarWidth = (w1 - w2);
return this._scrollBarWidth;
},
/**
* Remove the time component from a given date
*
* @param {Date} date date
* @return {Date} date with stripped time
*/
stripTime: function (date) {
// FIXME: likely to break when crossing DST
// would be better to use a library like momentJS
return new Date(date.getFullYear(), date.getMonth(), date.getDate());
},
_chunkify: function (t) {
// Adapted from http://my.opera.com/GreyWyvern/blog/show.dml/1671288
var tz = [], x = 0, y = -1, n = 0, code, c;
while (x < t.length) {
c = t.charAt(x);
// only include the dot in strings
var m = ((!n && c === '.') || (c >= '0' && c <= '9'));
if (m !== n) {
// next chunk
y++;
tz[y] = '';
n = m;
}
tz[y] += c;
x++;
}
return tz;
},
/**
* Compare two strings to provide a natural sort
* @param a first string to compare
* @param b second string to compare
* @return -1 if b comes before a, 1 if a comes before b
* or 0 if the strings are identical
*/
naturalSortCompare: function (a, b) {
var x;
var aa = this._chunkify(a);
var bb = this._chunkify(b);
for (x = 0; aa[x] && bb[x]; x++) {
if (aa[x] !== bb[x]) {
var aNum = Number(aa[x]), bNum = Number(bb[x]);
// note: == is correct here
if (aNum == aa[x] && bNum == bb[x]) {
return aNum - bNum;
} else {
// Note: This locale setting isn't supported by all browsers but for the ones
// that do there will be more consistency between client-server sorting
return aa[x].localeCompare(bb[x], OC.getLanguage());
}
}
}
return aa.length - bb.length;
},
/**
* Calls the callback in a given interval until it returns true
* @param {function} callback
* @param {integer} interval in milliseconds
*/
waitFor: function (callback, interval) {
var internalCallback = function () {
if (callback() !== true) {
setTimeout(internalCallback, interval);
}
};
internalCallback();
},
/**
* Checks if a cookie with the given name is present and is set to the provided value.
* @param {string} name name of the cookie
* @param {string} value value of the cookie
* @return {boolean} true if the cookie with the given name has the given value
*/
isCookieSetToValue: function (name, value) {
var cookies = document.cookie.split(';');
for (var i = 0; i < cookies.length; i++) {
var cookie = cookies[i].split('=');
if (cookie[0].trim() === name && cookie[1].trim() === value) {
return true;
}
}
return false;
}
}

View File

@ -0,0 +1,51 @@
/*
* @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
*
* @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
*
* @license GNU AGPL version 3 or any later version
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation, either version 3 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/**
* Returns a human readable file size
* @param {number} size Size in bytes
* @param {boolean} skipSmallSizes return '< 1 kB' for small files
* @return {string}
*/
export default function humanFileSize (size, skipSmallSizes) {
var humanList = ['B', 'KB', 'MB', 'GB', 'TB'];
// Calculate Log with base 1024: size = 1024 ** order
var order = size > 0 ? Math.floor(Math.log(size) / Math.log(1024)) : 0;
// Stay in range of the byte sizes that are defined
order = Math.min(humanList.length - 1, order);
var readableFormat = humanList[order];
var relativeSize = (size / Math.pow(1024, order)).toFixed(1);
if (skipSmallSizes === true && order === 0) {
if (relativeSize !== "0.0") {
return '< 1 KB';
} else {
return '0 KB';
}
}
if (order < 2) {
relativeSize = parseFloat(relativeSize).toFixed(0);
} else if (relativeSize.substr(relativeSize.length - 2, 2) === '.0') {
relativeSize = relativeSize.substr(0, relativeSize.length - 2);
} else {
relativeSize = parseFloat(relativeSize).toLocaleString(OC.getCanonicalLocale());
}
return relativeSize + ' ' + readableFormat;
}

View File

@ -52,6 +52,7 @@ import OC from './OC/index'
import OCP from './OCP/index'
import OCA from './OCA/index'
import escapeHTML from './Util/escapeHTML'
import humanFileSize from './Util/human-file-size'
window['_'] = _
window['$'] = $
@ -74,6 +75,7 @@ window['OC'] = OC
window['OCP'] = OCP
window['OCA'] = OCA
window['escapeHTML'] = escapeHTML
window['humanFileSize'] = humanFileSize
/**
* translate a string