+ upload demo ```typescript import React, { useEffect, useRef, useState } from "react"; import { Progress, Row, Col, } from "antd"; import { ProgressProps } from "antd/lib/progress"; import { UploaderCore } from "lmtools";
npm install lmtools
+ upload demo
``typescript
下载: ${ok_file.current.name}
import React, { useEffect, useRef, useState } from "react";
import { Progress, Row, Col, } from "antd";
import { ProgressProps } from "antd/lib/progress";
import { UploaderCore } from "lmtools";
export function MyUpload() {
const [precent, setPrecent] = useState(0);
const [status, setStatus] = useState
const [file, setFile] = useState
const [downloadurl, setDownloadurl] = useState
const uploader = useRef
const ok_file = useRef
useEffect(() => {
if (!file) {
return;
}
new UploaderCore({
"downloadUrl": "http://xxx/fastdfs/",
"endpoint": "http://xxx/upload/part/file",
"onError": (error) => {
setStatus("exception");
console.error("Failed because: " + error);
},
"onProgress": (bytesSent, bytesTotal) => {
const percentage = (bytesSent / bytesTotal * 100).toFixed(2);
setPrecent(+percentage);
console.log(bytesSent, bytesTotal, percentage + "%")
},
"onSuccess": (url, id, upload) => {
ok_file.current = upload.file as File;
setDownloadurl(url);
setPrecent(100);
setStatus("success");
console.log("下载地址 %s, 文件id %s", url, id);
}
}).read(file, _uploader => {
uploader.current = _uploader;
});
return () => uploader.current = null;
}, [file]);
// new Blob([{}], {"t"})
useEffect(() => {
if (!uploader.current) return;
if (status === "active") {
uploader.current.start();
} else if (status === "normal") {
uploader.current.abort();
}
}, [status]);
return (
<>
{
if (file !== ev.target.files[0]) {
setPrecent(0);
setStatus("normal");
}
setFile(ev.target.files[0]);
}} />
{ status === "success" ? {} : null }
`
>
);
}
`
+ 菜单绑定渲染懒加载路由(不再维护dynamic_renders_routers)
typescript
`
/**
* @interface 权限菜单定义
* @description page 表示唯一路由,label 表示菜单中文名
*/
export
interface subMenus_t {
label: string;
page: string;
icon?: string;
subMenus?: subMenus_t[];
menuApi?: any;
}
const menus: subMenus_t[];
// 之后赋值到menus
// 一个渲染懒路由的示例
class A extends React.Component {
render() {
return (
<>
{
dynamic_renders_routers(menus, {
"page1": { //
"path": "page1", // 相对路由,跟随之前的路由
"toload": [() => import("../page1.jsx"), { other: "附加属性" }]
},
"page2": {
"path": "/page2", // 绝对路由
"toload": () => import("../page2.jsx")
},
"*": {
"path": "/404",
"toload": () => import("../404.jsx")
}
}, {
with_switch: {
//
},
with_Redirect: {
//
}
})
}
>
)
}
}
`
+ 懒加载路由,单组件
typescript
`
import { LazyRoute } from "lmtools";
const Detail = () => import("../../common/work_order_detail/index.jsx");
function() {
return (
)
}
`
+ 错误捕捉
typescript
`
import { ErrorCatch } from 'lmtools';
import { notification } from 'antd';
function err_handler(error: Error) {
notification.error({
message: error.name,
description: (
<>
${error.message}{}
>
),
duration: null,
});
}
// 渲染异常
function App() {
let a = 10;
return {a.b};
}
export default ErrorCatch(err_handler)(App);
BlobToDataURL
+ 工具类函数
- blob转url:
DataUrlToImage
- url转img:
ImageToDataURL
- img转url:
Base64ToBlob
- base64转blob:
ImageToBlob`
- img转blob: