From 95aa2e3c65a3eb371b93cdb3dfeb4dbf05f929b5 Mon Sep 17 00:00:00 2001
From: awesomeYG <993631441@qq.com>
Date: Sun, 18 Feb 2024 18:32:19 +0800
Subject: [PATCH 1/3] feat: caesar pwd
---
src/components/MainContent/index.tsx | 2 +
src/pages/caesar.tsx | 159 +++++++++++++++++++++++++++
src/utils/tools.ts | 8 ++
3 files changed, 169 insertions(+)
create mode 100644 src/pages/caesar.tsx
diff --git a/src/components/MainContent/index.tsx b/src/components/MainContent/index.tsx
index 9a9adb5..17a5694 100644
--- a/src/components/MainContent/index.tsx
+++ b/src/components/MainContent/index.tsx
@@ -147,6 +147,7 @@ const MainContent: React.FC<{
direction='row'
alignItems='center'
justifyContent='space-between'
+ spacing={1}
sx={{
position: 'relative',
width: '100%',
@@ -175,6 +176,7 @@ const MainContent: React.FC<{
sx={{
borderRadius: '4px',
height: '24px',
+ minWidth: '80px',
}}
variant='outlined'
startIcon={}
diff --git a/src/pages/caesar.tsx b/src/pages/caesar.tsx
new file mode 100644
index 0000000..cf2dc08
--- /dev/null
+++ b/src/pages/caesar.tsx
@@ -0,0 +1,159 @@
+import React, { useState } from 'react';
+import { Container, Grid, TextField, Button, Box } from '@mui/material';
+import SendIcon from '@mui/icons-material/Send';
+import TranslateIcon from '@mui/icons-material/Translate';
+import MainContent from '@/components/MainContent';
+import alertActions from '@/components/Alert';
+
+const encode = (text: string, pwdOffest: number) => {
+ if (pwdOffest >= 26) pwdOffest = pwdOffest % 26;
+ return Array.from(text)
+ .map((item) => {
+ const count = item.charCodeAt(0);
+ if ((count >= 97 && count <= 122) || (count >= 65 && count <= 90)) {
+ if (
+ count + pwdOffest > 122 ||
+ (count <= 90 && count + pwdOffest > 90)
+ ) {
+ return String.fromCharCode(count + pwdOffest - 26);
+ }
+ return String.fromCharCode(count + pwdOffest);
+ }
+ return item;
+ })
+ .join('');
+};
+const decode = (pwd: string, pwdOffest: number) => {
+ if (pwdOffest > 25) pwdOffest = pwdOffest % 25;
+ return Array.from(pwd)
+ .map((item) => {
+ const count = item.charCodeAt(0);
+ if ((count >= 97 && count <= 122) || (count >= 65 && count <= 90)) {
+ if (count - pwdOffest < 65 || (count >= 97 && count - pwdOffest < 97)) {
+ return String.fromCharCode(count - pwdOffest + 26);
+ }
+ return String.fromCharCode(count - pwdOffest);
+ }
+ return item;
+ })
+ .join('');
+};
+const CaesarCodeTranslator = () => {
+ const [text, setText] = useState('');
+ const [pwd, setPwd] = useState('');
+ const [pwdOffest, setPwdOffest] = useState(3);
+
+ const onTextChange = (event: React.ChangeEvent) => {
+ setText(event.target.value);
+ };
+
+ const onPwdChange = (event: React.ChangeEvent) => {
+ setPwd(event.target.value);
+ };
+
+ const encodeToMorse = () => {
+ try {
+ const encoded = encode(text, pwdOffest);
+ setPwd(encoded);
+ } catch (error) {
+ const err = error as Error;
+ console.log(err);
+ alertActions.error('加密失败!');
+ }
+ };
+
+ const decodeFromMorse = () => {
+ try {
+ const decoded = decode(pwd, pwdOffest);
+ setText(decoded);
+ } catch (error) {
+ const err = error as Error;
+ console.log(err);
+ alertActions.error('解密失败!');
+ }
+ };
+
+ return (
+
+ <>
+ {
+ setPwdOffest(e.target.value as any);
+ }}
+ inputProps={{
+ style: { fontFamily: 'monospace' },
+ }}
+ sx={{ width: '200px', ml: 'auto' }}
+ />
+
+
+
+
+
+
+
+ }
+ sx={{ mb: 2 }}
+ >
+ 加密
+
+ }
+ >
+ 解密
+
+
+
+
+
+
+
+
+ >
+
+ );
+};
+
+export default CaesarCodeTranslator;
diff --git a/src/utils/tools.ts b/src/utils/tools.ts
index 36765e1..fefc5b3 100644
--- a/src/utils/tools.ts
+++ b/src/utils/tools.ts
@@ -598,4 +598,12 @@ export const allTools: Tool[] = [
key: [],
subTitle: '乱序文字生成器可以打乱文字和段落顺序,保持数量和出现次数不变。',
},
+ {
+ label: '凯撒密码在线加密解密',
+ tags: [Tags.SECURITY],
+ path: '/caesar',
+ key: [],
+ subTitle:
+ '凯撒密码最早由古罗马军事统帅盖乌斯·尤利乌斯·凯撒在军队中用来传递加密信息,故称凯撒密码。此为一种位移加密手段,只对26个(大小写)字母进行位移加密,规则相当简单,容易被破解',
+ },
];
From ac2b55ae5b4302ae1c6c58fa7bbf7991f016e831 Mon Sep 17 00:00:00 2001
From: awesomeYG <993631441@qq.com>
Date: Tue, 20 Feb 2024 10:29:19 +0800
Subject: [PATCH 2/3] feat: rail fence cipher
---
src/pages/caesar.tsx | 4 +-
src/pages/rail_fence_cipher.tsx | 189 ++++++++++++++++++++++++++++++++
src/utils/tools.ts | 10 +-
3 files changed, 200 insertions(+), 3 deletions(-)
create mode 100644 src/pages/rail_fence_cipher.tsx
diff --git a/src/pages/caesar.tsx b/src/pages/caesar.tsx
index cf2dc08..e46ec53 100644
--- a/src/pages/caesar.tsx
+++ b/src/pages/caesar.tsx
@@ -6,7 +6,7 @@ import MainContent from '@/components/MainContent';
import alertActions from '@/components/Alert';
const encode = (text: string, pwdOffest: number) => {
- if (pwdOffest >= 26) pwdOffest = pwdOffest % 26;
+ if (pwdOffest >= 26) pwdOffest %= 26;
return Array.from(text)
.map((item) => {
const count = item.charCodeAt(0);
@@ -24,7 +24,7 @@ const encode = (text: string, pwdOffest: number) => {
.join('');
};
const decode = (pwd: string, pwdOffest: number) => {
- if (pwdOffest > 25) pwdOffest = pwdOffest % 25;
+ if (pwdOffest >= 26) pwdOffest %= 26;
return Array.from(pwd)
.map((item) => {
const count = item.charCodeAt(0);
diff --git a/src/pages/rail_fence_cipher.tsx b/src/pages/rail_fence_cipher.tsx
new file mode 100644
index 0000000..610fd6e
--- /dev/null
+++ b/src/pages/rail_fence_cipher.tsx
@@ -0,0 +1,189 @@
+import React, { useState } from 'react';
+import { Container, Grid, TextField, Button, Box } from '@mui/material';
+import SendIcon from '@mui/icons-material/Send';
+import TranslateIcon from '@mui/icons-material/Translate';
+import MainContent from '@/components/MainContent';
+import alertActions from '@/components/Alert';
+
+const encode = (text: string, rails: number) => {
+ // 创建栅栏矩阵
+ const fence: string[][] = Array.from({ length: rails }, () => []);
+
+ // 将字符按照"W"字形排列到栅栏矩阵中
+ let rail = 0;
+ let direction = 1;
+ for (let i of text) {
+ fence[rail].push(i);
+ rail += direction;
+ if (rail === 0 || rail === rails - 1) {
+ direction = -direction;
+ }
+ }
+
+ // 按照特定顺序读取字符并拼接成密文
+ let pwd = '';
+ for (let i = 0; i < rails; i++) {
+ pwd += fence[i].join('');
+ }
+
+ return pwd;
+};
+
+const decode = (pwd: string, rails: number) => {
+ // 创建栅栏矩阵
+ const fence: string[][] = Array.from({ length: rails }, () => []);
+
+ // 计算栅栏中每行的字符数
+ const railCounts = Array.from({ length: rails }, () => 0);
+ let rail = 0;
+ let direction = 1;
+ for (let i = 0; i < pwd.length; i++) {
+ railCounts[rail]++;
+ rail += direction;
+ if (rail === 0 || rail === rails - 1) {
+ direction = -direction;
+ }
+ }
+
+ // 将密文中的字符填充到栅栏矩阵中
+ let index = 0;
+ for (let i = 0; i < rails; i++) {
+ for (let j = 0; j < railCounts[i]; j++) {
+ fence[i].push(pwd[index]);
+ index++;
+ }
+ }
+
+ // 按照"山"字形顺序读取字符并拼接成明文
+ let plaintext = '';
+ rail = 0;
+ direction = 1;
+ for (let i = 0; i < pwd.length; i++) {
+ plaintext += fence[rail].shift();
+ rail += direction;
+ if (rail === 0 || rail === rails - 1) {
+ direction = -direction;
+ }
+ }
+
+ return plaintext;
+};
+const RailFenceCipher = () => {
+ const [text, setText] = useState('');
+ const [pwd, setPwd] = useState('');
+ const [pwdOffest, setPwdOffest] = useState(3);
+
+ const onTextChange = (event: React.ChangeEvent) => {
+ setText(event.target.value);
+ };
+
+ const onPwdChange = (event: React.ChangeEvent) => {
+ setPwd(event.target.value);
+ };
+
+ const encodeToMorse = () => {
+ try {
+ const encoded = encode(text, pwdOffest);
+ setPwd(encoded);
+ } catch (error) {
+ const err = error as Error;
+ console.log(err);
+ alertActions.error('加密失败!');
+ }
+ };
+
+ const decodeFromMorse = () => {
+ try {
+ const decoded = decode(pwd, pwdOffest);
+ setText(decoded);
+ } catch (error) {
+ const err = error as Error;
+ console.log(err);
+ alertActions.error('解密失败!');
+ }
+ };
+
+ return (
+
+ <>
+ {
+ setPwdOffest(e.target.value as any);
+ }}
+ inputProps={{
+ style: { fontFamily: 'monospace' },
+ }}
+ sx={{ width: '200px', ml: 'auto' }}
+ />
+
+
+
+
+
+
+
+ }
+ sx={{ mb: 2 }}
+ >
+ 加密
+
+ }
+ >
+ 解密
+
+
+
+
+
+
+
+
+ >
+
+ );
+};
+
+export default RailFenceCipher;
diff --git a/src/utils/tools.ts b/src/utils/tools.ts
index fefc5b3..8007772 100644
--- a/src/utils/tools.ts
+++ b/src/utils/tools.ts
@@ -600,10 +600,18 @@ export const allTools: Tool[] = [
},
{
label: '凯撒密码在线加密解密',
- tags: [Tags.SECURITY],
+ tags: [Tags.ENCRYPT],
path: '/caesar',
key: [],
subTitle:
'凯撒密码最早由古罗马军事统帅盖乌斯·尤利乌斯·凯撒在军队中用来传递加密信息,故称凯撒密码。此为一种位移加密手段,只对26个(大小写)字母进行位移加密,规则相当简单,容易被破解',
},
+ {
+ label: '栅栏密码在线加密解密',
+ tags: [Tags.ENCRYPT],
+ path: '/rail_fence_cipher',
+ key: [],
+ subTitle:
+ '所谓栅栏密码,就是把要加密的明文分成N个一组,然后把每组的第1个字连起来,形成一段无规律的话。 不过栅栏密码本身有一个潜规则,就是组成栅栏的字母一般不会太多。(一般不超过30个,也就是一、两句话)',
+ },
];
From 6f36085136cfd652430a7e35d6930b046ddfaa6d Mon Sep 17 00:00:00 2001
From: awesomeYG <993631441@qq.com>
Date: Tue, 20 Feb 2024 11:02:57 +0800
Subject: [PATCH 3/3] =?UTF-8?q?feat:=20unicode=20=E7=BC=96=E8=A7=A3?=
=?UTF-8?q?=E7=A0=81?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
src/pages/unicode.tsx | 74 +++++++++++++++++++++++++++++++++++++++++++
src/utils/tools.ts | 8 +++++
2 files changed, 82 insertions(+)
create mode 100644 src/pages/unicode.tsx
diff --git a/src/pages/unicode.tsx b/src/pages/unicode.tsx
new file mode 100644
index 0000000..028e6b8
--- /dev/null
+++ b/src/pages/unicode.tsx
@@ -0,0 +1,74 @@
+import MainContent from '@/components/MainContent';
+import TextFieldWithClean from '@/components/TextFieldWithClean';
+import TextFieldWithCopy from '@/components/TextFieldWithCopy';
+import SendIcon from '@mui/icons-material/Send';
+import TranslateIcon from '@mui/icons-material/Translate';
+import { Box, Button, Stack } from '@mui/material';
+import { useState } from 'react';
+
+function UnicodeConverter() {
+ const [input, setInput] = useState(''); // 输入的普通文本或unicode码
+ const [output, setOutput] = useState(''); // 输出的unicode码或普通文本
+
+ // Unicode编码函数
+ const encodeToUnicode = (str: string) => {
+ let unicode_str = '';
+ for (let i = 0; i < str.length; i++) {
+ let unicode_code = str.charCodeAt(i).toString(16).toUpperCase();
+ unicode_str += '\\u' + ('0000' + unicode_code).slice(-4);
+ }
+ setOutput(unicode_str);
+ };
+
+ // Unicode解码函数
+ const decodeFromUnicode = (unicode_str: string) => {
+ let str = '';
+ unicode_str.replace(
+ /\\u([\da-f]{4})/gi,
+ (match, key) => (str += String.fromCharCode(parseInt(key, 16)))
+ );
+ setOutput(str);
+ };
+
+ // 渲染组件
+ return (
+
+
+ setInput('')}
+ onChange={(e) => setInput(e.target.value)}
+ />
+
+ }
+ sx={{ mb: 2 }}
+ onClick={() => encodeToUnicode(input)}
+ >
+ 转码
+
+ }
+ onClick={() => decodeFromUnicode(input)}
+ >
+ 解码
+
+
+ setOutput(e.target.value)}
+ variant={'outlined'}
+ />
+
+
+ );
+}
+
+export default UnicodeConverter;
diff --git a/src/utils/tools.ts b/src/utils/tools.ts
index 8007772..6cc14fa 100644
--- a/src/utils/tools.ts
+++ b/src/utils/tools.ts
@@ -614,4 +614,12 @@ export const allTools: Tool[] = [
subTitle:
'所谓栅栏密码,就是把要加密的明文分成N个一组,然后把每组的第1个字连起来,形成一段无规律的话。 不过栅栏密码本身有一个潜规则,就是组成栅栏的字母一般不会太多。(一般不超过30个,也就是一、两句话)',
},
+ {
+ label: 'Unicode 编码解码',
+ tags: [Tags.ENCODE],
+ path: '/unicode',
+ key: [],
+ subTitle:
+ 'Unicode,又译作万国码、统一字元码、统一字符编码,是信息技术领域的业界标准,其整理、编码了世界上大部分的文字系统,使得电脑能以通用划一的字符集来处理和显示文字,不但减轻在不同编码系统间切换和转换的困扰,更提供了一种跨平台的乱码问题解决方案。',
+ },
];