vue3中使用 tui-image-editor进行图片处理,并上传

news2024/10/6 5:43:01

效果图

在这里插入图片描述

下载包

pnpm i tui-image-editor
pnpm i tui-color-picker

调用组件

//html部分
<el-dialog v-model="imgshow" destroy-on-close width="40%" draggable align-center :show-close="true"
				:close-on-click-modal="false">
				<template #header>
					<div style="display: flex; justify-content: space-between">
						<div style="display: flex">
							<h3>图片</h3>
						</div>
					</div>
				</template>
				<div class="newBox">
					<!-- 图片处理框 -->
					<SignImage v-if="cropperObj.cVisible" :dialogVisible="cropperObj.cVisible" :title="cropperObj.ctitle"
						:imgUrl="cropperObj.previewsImgUrl" @getNewImg="cropperObj.getNewImg"
						@closeCropperDialog="cropperObj.closeCropperView"></SignImage>

				</div>
			</el-dialog>

//js部分
import { SignImage } from './index';//调用组件
let imgshow = ref<boolean>(false);
const cropperObj = reactive({
	cVisible: true, // 显示切图弹框
	ctitle: "", // 弹框标题
	previewsImgUrl: "https://img0.baidu.com/it/u=2759734465,3558448225&fm=253&app=138&size=w931&n=0&f=JPEG&fmt=auto?sec=1708621200&t=acc59373dca9b8658e33e14a974f6c47", //图片地址
	// 开启剪切弹框
	openCropperView: () => {
		cropperObj.ctitle = "图片处理"
		cropperObj.cVisible = true
	},
	// 关闭弹框所触发的事件
	closeCropperView: (data) => {
		cropperObj.cVisible = false
	},
	// 获取处理完的图片数据
	getNewImg: (val: any) => {
		console.log("val", val);
		pictureAnnotationFun(val)
	}
})
//图片上传函数,并加其他参数
async function pictureAnnotationFun(file: any) {
	const formData = new FormData()
	formData.append("file", file);
	formData.append('id', xx);
	formData.append('bid', xxx);
	try {
		const { code, msg, data } = await uploadimg(formData);
		if (code > 0) {
			cropperObj.cVisible = false;
			ElMessage({
				showClose: true,
				message: '上传成功',
				type: 'success',
			});
		} else {
			ElMessage({
				showClose: true,
				message: '上传失败' + msg,
				type: 'error',
				duration: 0,
			});
		}
	} catch (e) {

		ElMessage({
			showClose: true,
			message: '错误: ' + e.message,
			type: 'error',
			duration: 0,
		});
	}
}


封装组件代码

<template>
	<div class="drawing-container">
		<!-- 绘图组件容器DOM -->
		<div id="tui-image-editor"></div>
		<el-button class="save" type="primary" @click="save">保存</el-button>
	</div>
</template>
<script setup lang="ts">
import 'tui-image-editor/dist/tui-image-editor.css';
import 'tui-color-picker/dist/tui-color-picker.css';
import ImageEditor from 'tui-image-editor';
import { nextTick, onMounted, ref } from 'vue';

// 中文菜单
const locale_zh = {
	ZoomIn: '放大',
	ZoomOut: '缩小',
	Hand: '手掌',
	History: '历史',
	Resize: '调整宽高',
	Crop: '裁剪',
	DeleteAll: '全部删除',
	Delete: '删除',
	Undo: '撤销',
	Redo: '反撤销',
	Reset: '重置',
	Flip: '镜像',
	Rotate: '旋转',
	Draw: '画',
	Shape: '形状标注',
	Icon: '图标标注',
	Text: '文字标注',
	Mask: '遮罩',
	Filter: '滤镜',
	Bold: '加粗',
	Italic: '斜体',
	Underline: '下划线',
	Left: '左对齐',
	Center: '居中',
	Right: '右对齐',
	Color: '颜色',
	'Text size': '字体大小',
	Custom: '自定义',
	Square: '正方形',
	Apply: '应用',
	Cancel: '取消',
	'Flip X': 'X 轴',
	'Flip Y': 'Y 轴',
	Range: '区间',
	Stroke: '描边',
	Fill: '填充',
	Circle: '圆',
	Triangle: '三角',
	Rectangle: '矩形',
	Free: '曲线',
	Straight: '直线',
	Arrow: '箭头',
	'Arrow-2': '箭头2',
	'Arrow-3': '箭头3',
	'Star-1': '星星1',
	'Star-2': '星星2',
	Polygon: '多边形',
	Location: '定位',
	Heart: '心形',
	Bubble: '气泡',
	'Custom icon': '自定义图标',
	'Load Mask Image': '加载蒙层图片',
	Grayscale: '灰度',
	Blur: '模糊',
	Sharpen: '锐化',
	Emboss: '浮雕',
	'Remove White': '除去白色',
	Distance: '距离',
	Brightness: '亮度',
	Noise: '噪音',
	'Color Filter': '彩色滤镜',
	Sepia: '棕色',
	Sepia2: '棕色2',
	Invert: '负片',
	Pixelate: '像素化',
	Threshold: '阈值',
	Tint: '色调',
	Multiply: '正片叠底',
	Blend: '混合色',
	Width: '宽度',
	Height: '高度',
	'Lock Aspect Ratio': '锁定宽高比例',
};

// 画布组件自定义样式
const customTheme = {
	'common.bi.image': '', // 左上角logo图片
	'common.bisize.width': '0px',
	'common.bisize.height': '0px',
	'common.backgroundImage': 'none',
	'common.backgroundColor': '#f3f4f6',
	'common.border': '1px solid #333',

	// header
	'header.backgroundImage': 'none',
	'header.backgroundColor': '#f3f4f6',
	'header.border': '0px',

	// load button
	'loadButton.backgroundColor': '#fff',
	'loadButton.border': '1px solid #ddd',
	'loadButton.color': '#222',
	'loadButton.fontFamily': 'NotoSans, sans-serif',
	'loadButton.fontSize': '12px',
	'loadButton.display': 'none', // 可以直接隐藏掉

	// download button
	'downloadButton.backgroundColor': '#fdba3b',
	'downloadButton.border': '1px solid #fdba3b',
	'downloadButton.color': '#fff',
	'downloadButton.fontFamily': 'NotoSans, sans-serif',
	'downloadButton.fontSize': '12px',
	'downloadButton.display': 'none', // 可以直接隐藏掉

	// icons default
	'menu.normalIcon.color': '#8a8a8a',
	'menu.activeIcon.color': '#555555',
	'menu.disabledIcon.color': '#ccc',
	'menu.hoverIcon.color': '#e9e9e9',
	'submenu.normalIcon.color': '#8a8a8a',
	'submenu.activeIcon.color': '#e9e9e9',

	'menu.iconSize.width': '24px',
	'menu.iconSize.height': '24px',
	'submenu.iconSize.width': '32px',
	'submenu.iconSize.height': '32px',

	// submenu primary color
	'submenu.backgroundColor': '#1e1e1e',
	'submenu.partition.color': '#858585',

	// submenu labels
	'submenu.normalLabel.color': '#858585',
	'submenu.normalLabel.fontWeight': 'lighter',
	'submenu.activeLabel.color': '#fff',
	'submenu.activeLabel.fontWeight': 'lighter',

	// checkbox style
	'checkbox.border': '1px solid #ccc',
	'checkbox.backgroundColor': '#fff',

	// rango style
	'range.pointer.color': '#fff',
	'range.bar.color': '#666',
	'range.subbar.color': '#d1d1d1',

	'range.disabledPointer.color': '#414141',
	'range.disabledBar.color': '#282828',
	'range.disabledSubbar.color': '#414141',

	'range.value.color': '#fff',
	'range.value.fontWeight': 'lighter',
	'range.value.fontSize': '11px',
	'range.value.border': '1px solid #353535',
	'range.value.backgroundColor': '#151515',
	'range.title.color': '#fff',
	'range.title.fontWeight': 'lighter',

	// colorpicker style
	'colorpicker.button.border': '1px solid #1e1e1e',
	'colorpicker.title.color': '#fff',
};

// props
const props = defineProps({
	dialogVisible: {
		type: Boolean,
		default: () => {
			return false;
		},
	},
	title: {
		type: String,
		default: '',
	},
	imgUrl: {
		type: String,
		default: '',
	},
});
const emit = defineEmits(['closeCropperDialog', 'getNewImg']);
const instance = ref<any>(null);

onMounted(() => {

	nextTick(() => {
		init(); // 页面创建完成后调用
	});
});

// 关闭弹框
const closeDialog = () => {
	emit('closeCropperDialog');
	// options.img = ''
};

const init = () => {
	instance.value = new ImageEditor(document.querySelector('#tui-image-editor'), {
		includeUI: {
			loadImage: {
				path: props.imgUrl,
				name: 'image',
			},
			menu: ['resize', 'crop', 'rotate', 'draw', 'shape', 'icon', 'text', 'filter'], // 底部菜单按钮列表 隐藏镜像flip和遮罩mask
			initMenu: 'draw', // 默认打开的菜单项
			menuBarPosition: 'bottom', // 菜单所在的位置
			locale: locale_zh, // 本地化语言为中文
			theme: customTheme, // 自定义样式
		},
		cssMaxWidth: 400, // canvas 最大宽度
		cssMaxHeight: 500, // canvas 最大高度
	});
	document.getElementsByClassName('tui-image-editor-main')[0].style.top = '45px'; // 调整图片显示位置
	document.getElementsByClassName('tie-btn-reset tui-image-editor-item help')[0].style.display = 'none'; // 隐藏顶部重置按钮
};

// 保存图片,并上传
const save = async () => {
	const base64String = instance.value.toDataURL(); // base64 文件
	const data = window.atob(base64String.split(',')[1]);
	const ia = new Uint8Array(data.length);
	for (let i = 0; i < data.length; i++) {
		ia[i] = data.charCodeAt(i);
	}
	const file = new File([ia], "打标.png", { type: "image/png" });
	emit('getNewImg', file);

};
</script>

<style lang="scss" scoped>
.drawing-container {
	width: 100%;
	height: 80vh;
	position: relative;

	.save {
		position: absolute;
		right: 50px;
		top: 15px;
	}
}
</style>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1463283.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

windows极限摸鱼软件(仅6678kb)

时间过得真快啊&#xff0c;不知不觉春节假期就过完了。你已经开始工作了吗&#xff1f;反正我是一直没闲着。 歇的时间久了&#xff0c;一上班这节奏很难一下子转换过来。也可能刚上班&#xff0c;没什么事情做&#xff0c;有点无聊。 &#xff08;好吧&#xff0c;我承认了…

Java 面向对象进阶 11 多态的优势和弊端(黑马)

优势&#xff1a; 代码&#xff1a; public class test {public static void main(String[] args) {Animal a new Dog();a.eat(); } } class Animal{public void eat(){System.out.println("动物再吃东西");} } class Dog extends Animal{Overridepublic void eat(…

如何修改unity的背景颜色

要在Unity中将背景颜色设为黑色&#xff0c;可以按照以下步骤进行&#xff1a; 1、在Unity编辑器中&#xff0c;选择你想要修改背景颜色的摄像机对象&#xff08;一般是Main Camera&#xff09;。 2、在Inspector面板中&#xff0c;找到"Clear Flags"&#xff08;清…

Leetcode155(设计最小栈)

例题&#xff1a; 分析&#xff1a; 题目要求我们必须在常数时间内检索到最小元素。 我们可以使用两个栈&#xff08;A、B&#xff09;来实现&#xff0c;A栈用来正常存储数据、弹出数据&#xff0c; B栈用于存储A栈中的最小元素&#xff0c;如下图&#xff1a; 刚开始&#…

三十年一个大轮回!日股突破“泡沫时期”历史高点

2月22日周四&#xff0c;英伟达四季报业绩超预期&#xff0c;而且本季度业绩指引非常乐观&#xff0c;提振美股股指期货并成为芯片股和AI概念股情绪的重要催化剂。今日亚洲芯片股和AI股起飞&#xff0c;日本在芯片股的带动下突破1989年泡沫时期以来的历史最高收盘价。 美股方面…

SqlServer2016离线安装--Microsoft R Open 和 Microsoft R Server安装文件位置

问题 SQL SERVE 2016离线安装&#xff0c;会出现“Microsoft R Open 和 Microsoft R Server 脱机安装”的界面&#xff0c; 无法点击下一步的情况&#xff0c;如下图&#xff1a; 原因 离线安装时需要下载两个文件 解决方案 1、访问路径下载文件 https://go.microsoft.c…

MATLAB 导出可编辑的eps格式图像

任务描述&#xff1a;部分期刊要求提交可编辑的eps格式图像&#xff0c;方便美工编辑对图像进行美化 我试了直接print或者在figure窗口导出&#xff0c;发现导出的文件放到Adobe AI中并不能编辑&#xff0c;经Google找到解决办法&#xff1a; %EPS exportgraphics(gcf,myVect…

Nginx基础入门

一、Nginx的优势 nginx是一个高性能的HTTP和反向代理服务器&#xff0c;也是一个SMTP&#xff08;邮局&#xff09;服务器。 Nginx的web优势&#xff1a;IO多路复用&#xff0c;时分多路复用&#xff0c;频分多路复用 高并发&#xff0c;IO多路复用&#xff0c;epoll&#xf…

2024年1月手机市场行业分析:苹果手机份额骤降,国产高端手机成功逆袭!

小米Ultra发布。 一方面&#xff0c;我们有望看到国产手机再一次超越自己的决心&#xff0c;继续创新追逐高端&#xff1b;另一方面&#xff0c;我们也不得不正视目前手机市场所面临的危机状态。 2024年1月的线上手机市场远不如去年。根据鲸参谋数据显示&#xff0c;今年1月京…

linux系统内核升级

1.查看旧版本内核 2.导入密钥 rpm --import https://www.elrepo.org/RPM-GPG-KEY-elrepo.org 3.安装yum源 rpm -Uvh http://www.elrepo.org/elrepo-release-7.0-2.el7.elrepo.noarch.rpm4.启用elrepo-kernel仓库并安装最新内核版本 yum --enablerepoelrepo-kernel install …

【AIGC】开源音频工具AudioCraft

AudioCraft是一个开源框架&#xff0c;旨在生成高质量的音频&#xff0c;适用于音乐、声音生成和压缩等多种应用。 先听效果&#xff1a; aimusic 它由三个模型组成&#xff1a;MusicGen、AudioGen和EnCodec。 *MusicGen&#xff1a;*这个模型使用了Meta拥有和特别许可的音乐进…

WP----Look 我看的见你,你却看不见我 tips:sql injection tips2: mysql 字符集

0x00 题目连接打开后&#xff0c;是空白的&#xff0c;源代码也是空白的 这种情况就抓包&#xff0c;看请求包和相应包里面是否有提示 相应包中存在很特别的响应头X-HT: verify 可能是参数&#xff0c;传递任意参数过去 0x01 传递5个长度的参数时&#xff0c;返回 说明参数的…

相机图像质量研究(35)常见问题总结:图像处理对成像的影响--运动噪声

系列文章目录 相机图像质量研究(1)Camera成像流程介绍 相机图像质量研究(2)ISP专用平台调优介绍 相机图像质量研究(3)图像质量测试介绍 相机图像质量研究(4)常见问题总结&#xff1a;光学结构对成像的影响--焦距 相机图像质量研究(5)常见问题总结&#xff1a;光学结构对成…

使用 C++23 协程实现第一个 co_await 同步风格调用接口--Qt计算文件哈希值

C加入了协程 coroutine的特性&#xff0c;一直没有动手实现过。看了网上很多文章&#xff0c;已经了解了协程作为“可被中断和恢复的函数”的一系列特点。在学习过程中&#xff0c;我发现大多数网上的例子&#xff0c;要不就是在main()函数的控制台程序里演示yeild,await, resu…

命令执行 [WUSTCTF2020]朴实无华1

做题&#xff1a; 打开题目 我们用dirsearch扫描一下看看 扫描到有robots.txt&#xff0c;访问一下看看 提示我们 /fAke_f1agggg.php 那就访问一下&#xff0c;不是真的flag bp抓包一下 得到提示&#xff0c; /fl4g.php&#xff0c;访问一下看看 按alt&#xff0c;点击修复文…

IP地理位置查询定位:技术原理与实际应用

在互联网时代&#xff0c;IP地址是连接世界的桥梁&#xff0c;而了解IP地址的地理位置对于网络管理、个性化服务以及安全监控都至关重要。IP数据云将深入探讨IP地理位置查询定位的技术原理、实际应用场景以及相关的隐私保护问题&#xff0c;旨在为读者提供全面了解和应用该技术…

Shopee平台选品原则指南:如何科学有效地进行产品选品

在当今激烈竞争的电商市场中&#xff0c;如何在Shopee平台上选择适合的产品进行销售&#xff0c;是每位卖家都要面对的重要问题。针对这一挑战&#xff0c;我们整理了一些关键原则&#xff0c;帮助卖家们在选品过程中更加科学和有效地进行决策。 先给大家推荐一款shopee知虾数…

一文弄明白KeyedProcessFunction函数

引言 KeyedProcessFunction是Flink用于处理KeyedStream的数据集合&#xff0c;它比ProcessFunction拥有更多特性&#xff0c;例如状态处理和定时器功能等。接下来就一起来了解下这个函数吧 正文 了解一个函数怎么用最权威的地方就是 官方文档 以及注解&#xff0c;KeyedProc…

stm32和嵌入式linux可以同步学习吗?

在开始前我有一些资料&#xff0c;是我根据网友给的问题精心整理了一份「stm3的资料从专业入门到高级教程」&#xff0c; 点个关注在评论区回复“888”之后私信回复“888”&#xff0c;全部无偿共享给大家&#xff01;&#xff01;&#xff01;如果需要使用STM32&#xff0c;建…

LeetCode 0106.从中序与后序遍历序列构造二叉树:分治(递归)——五彩斑斓的题解(若不是彩色的可以点击原文链接查看)

【LetMeFly】106.从中序与后序遍历序列构造二叉树&#xff1a;分治&#xff08;递归&#xff09;——五彩斑斓的题解&#xff08;若不是彩色的可以点击原文链接查看&#xff09; 力扣题目链接&#xff1a;https://leetcode.cn/problems/construct-binary-tree-from-inorder-an…