tiefen_space_app/screeens/EditSpacePost/index.jsx

261 lines
7.5 KiB
React
Raw Normal View History

2024-04-18 22:58:59 +08:00
import {
View,
Text,
TextInput,
ScrollView,
ActivityIndicator,
} from "react-native";
import React, { useState, useEffect, useCallback } from "react";
import { useTailwind } from "tailwind-rn";
import { useSafeAreaInsets } from "react-native-safe-area-context";
import MediaPicker from "../../components/MediaPicker";
import Toast from "react-native-toast-message";
import { multiUpload } from "../../utils/upload";
import baseRequest from "../../utils/baseRequest";
import { generateSignature } from "../../utils/crypto";
import { Image } from "expo-image";
import { Icon } from "@rneui/themed";
export default function EditSpacePost({ navigation, route }) {
const data = route.params.data;
const tailwind = useTailwind();
const insets = useSafeAreaInsets();
const [content, setContent] = useState(data.text);
const [isSubmitting, setIsSubmitting] = useState(false);
//保存新添加的媒体
const [newMeidaAssets, setNewMediaAssets] = useState([]);
//展示旧媒体组件
const [oldMediaAssets, setOldMediaAssets] = useState(
data.m_type === 1
? data.media_component.images
: data.media_component.videos
);
const DisplayOldMedia = useCallback(
({ url, index }) => {
const handleDelete = () => {
const updatedAssets = [...oldMediaAssets];
updatedAssets.splice(index, 1);
setOldMediaAssets(updatedAssets);
};
return (
<View
style={{
aspectRatio: 1,
...tailwind("w-1/4 p-1"),
}}
>
<Image
style={tailwind("w-full h-full rounded-lg")}
source={url}
contentFit="cover"
cachePolicy="disk"
/>
<View style={tailwind("absolute top-2 right-2")}>
<Icon
type="ionicon"
name="close"
color="white"
size={18}
onPress={handleDelete}
style={tailwind("bg-black rounded-full opacity-70")}
/>
</View>
</View>
);
},
[oldMediaAssets]
);
//发布更新内容
const handleSubmit = async () => {
if (!content) {
Toast.show({
type: "error",
text1: "动态内容不能为空",
topOffset: 60,
});
return;
}
if (oldMediaAssets.length === 0 && newMeidaAssets.length === 0) {
Toast.show({
type: "error",
text1: "请选择要上传的图片或视频",
topOffset: 60,
});
return;
}
if (
data.m_type === 1 &&
oldMediaAssets.length + newMeidaAssets.length > 30
) {
Toast.show({
type: "error",
text1: "最多只能上传30张照片哦",
topOffset: 60,
});
return;
}
if (
data.m_type === 2 &&
oldMediaAssets.length + newMeidaAssets.length > 1
) {
Toast.show({
type: "error",
text1: "最多只能上传1个视频哦",
topOffset: 60,
});
return;
}
if (
data.c_type === 1 &&
data.m_type === 1 &&
oldMediaAssets.length + newMeidaAssets.length <= data.media_visible_range
) {
Toast.show({
type: "error",
text1: "预览图片数不得大于等于上传图片数",
topOffset: 60,
});
return;
}
//提交数据
if (isSubmitting) return;
setIsSubmitting(true);
const newMediaIds = await multiUpload(newMeidaAssets);
const oldMediaIds = oldMediaAssets.map((item) => item.id);
const media = {
image_ids:
data.m_type === 1 ? [...oldMediaIds, ...newMediaIds?.image_ids] : [],
video_ids:
data.m_type === 2 ? [...oldMediaIds, ...newMediaIds?.video_ids] : [],
};
const apiUrl = process.env.EXPO_PUBLIC_API_URL;
try {
const base = await baseRequest();
const body = {
...base,
id: data.id,
c_type: data.c_type,
m_type: data.m_type,
text: content,
media_component: media,
};
const signature = await generateSignature(body);
const _response = await fetch(
`${apiUrl}/api/zone_moment/update?signature=${signature}`,
{
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify(body),
}
);
const _data = await _response.json();
if (_data.ret === -1) {
Toast.show({
type: "error",
text1: _data.msg,
topOffset: 60,
});
return;
}
//提交成功后显示Toast并返回上一页
Toast.show({
type: "success",
text1: "编辑成功",
topOffset: 60,
});
navigation.goBack();
} catch (error) {
console.error(error);
} finally {
setIsSubmitting(false);
}
};
//发布按钮
useEffect(() => {
navigation.setOptions({
headerRight: () => (
<Text
onPress={handleSubmit}
style={tailwind("text-[#FF669E] text-base font-medium")}
>
{isSubmitting ? "" : "发布"}
{isSubmitting && <ActivityIndicator size="small" color="white" />}
</Text>
),
});
}, [isSubmitting, handleSubmit]);
return (
<ScrollView
style={{
paddingBottom: insets.bottom,
paddingLeft: insets.left,
paddingRight: insets.right,
...tailwind("flex-1"),
}}
>
<View style={tailwind("p-4")}>
<View style={tailwind("mb-4")}>
<Text style={tailwind("text-base font-medium text-[#F53030] mb-2")}>
违规详情
</Text>
<View style={tailwind("p-4 rounded-2xl bg-[#FFFFFF1A]")}>
{data.text_audit_opinion && (
<Text style={tailwind("text-sm font-medium text-white")}>
<Text style={tailwind("text-[#F53030]")}>文案违规原因</Text>
{data.text_audit_opinion}
</Text>
)}
{data.image_audit_opinion && (
<Text style={tailwind("text-sm font-medium text-white")}>
<Text style={tailwind("text-[#F53030]")}>
图片/视频违规原因
</Text>
{data.image_audit_opinion}
</Text>
)}
{data.manually_review_opinion && (
<Text style={tailwind("text-sm font-medium text-white")}>
<Text style={tailwind("text-[#F53030]")}>运营追加</Text>
{data.manually_review_opinion}
</Text>
)}
</View>
</View>
<Text style={tailwind("text-base font-medium text-white")}>
动态内容
</Text>
<TextInput
placeholder="请遵守平台准则,严禁发布违规内容"
placeholderTextColor="#FFFFFF80"
underlineColorAndroid="transparent"
multiline
textAlignVertical="top"
onChangeText={(value) => setContent(value)}
value={content}
style={tailwind(
"h-32 bg-[#FFFFFF1A] text-white rounded-2xl mt-2 mb-4 p-2"
)}
/>
<View style={tailwind("flex-row flex-wrap")}>
{oldMediaAssets.map((item, index) => (
<DisplayOldMedia key={index} url={item?.urls[0]} index={index} />
))}
</View>
<MediaPicker
maxCount={data.m_type === 1 ? 30 : 1}
type={data.m_type === 1 ? "image" : "video"}
setAssets={setNewMediaAssets}
/>
</View>
</ScrollView>
);
}