Proyek ini dikembangkan berdasarkan kerangka Wafer2. Backend menggunakan Node.js SDK yang disediakan oleh Tencent Cloud untuk mengakses API penyimpanan objek. Kode inti front-end mengimplementasikan fungsi editor gambar dan mendukung pergerakan, rotasi, penskalaan , pembuatan pratinjau dan pengeditan gambar dan teks. Status disimpan dan bagian animasi diimplementasikan menggunakan animasi CSS.
Kotak input modal di applet adalah komponen InputBox yang dikemas secara terpisah.
Informasi sensitif seperti AppId telah dihapus dari kode. Anda dapat menambahkan AppId dan AppSecret Anda sendiri untuk mengonfigurasi lingkungan latar belakang dan menerapkan pengujian login. Untuk metode penambahan mendetail, lihat "Penggunaan" di bawah bidang page
di file app.json
. Lihat halaman yang berbeda secara berurutan
git clone https://github.com/yeliudev/LemonJournal.git
LemonJournal
di Alat Pengembang WeChat appid
project.config.json
/client/utils/util.js
<image>
(sesuai dengan gambar) dan tag <text>
(sesuai dengan teks) dalam komponen khusus yang sama <sticker>
, melakukan rendering bersyarat berdasarkan apakah variabel text
yang diekspos kosong , lalu ikat tiga peristiwa onTouchStart()
, onTouchEnd()
dan onTouchMove()
untuk mengoperasikan posisi, sudut, ukuran, level seluruh komponen serta perilaku tombol "putar" dan "hapus". onTouchStart: function ( e ) {
// 若未选中则直接返回
if ( ! this . data . selected ) {
return
}
switch ( e . target . id ) {
case 'sticker' : {
this . touch_target = e . target . id
this . start_x = e . touches [ 0 ] . clientX * 2
this . start_y = e . touches [ 0 ] . clientY * 2
break
}
case 'handle' : {
// 隐藏移除按钮
this . setData ( {
hideRemove : true
} )
this . touch_target = e . target . id
this . start_x = e . touches [ 0 ] . clientX * 2
this . start_y = e . touches [ 0 ] . clientY * 2
this . sticker_center_x = this . data . stickerCenterX ;
this . sticker_center_y = this . data . stickerCenterY ;
this . remove_center_x = this . data . removeCenterX ;
this . remove_center_y = this . data . removeCenterY ;
this . handle_center_x = this . data . handleCenterX ;
this . handle_center_y = this . data . handleCenterY ;
this . scale = this . data . scale ;
this . rotate = this . data . rotate ;
break
}
}
} ,
onTouchEnd : function ( e ) {
this . active ( )
this . touch_target = ''
// 显示移除按钮
this . setData ( {
removeCenterX : 2 * this . data . stickerCenterX - this . data . handleCenterX ,
removeCenterY : 2 * this . data . stickerCenterY - this . data . handleCenterY ,
hideRemove : false
} )
// 若点击移除按钮则触发移除事件,否则触发刷新数据事件
if ( e . target . id === 'remove' ) {
this . triggerEvent ( 'removeSticker' , this . data . sticker_id )
} else {
this . triggerEvent ( 'refreshData' , this . data )
}
} ,
onTouchMove : function ( e ) {
// 若无选中目标则返回
if ( ! this . touch_target ) {
return
}
var current_x = e . touches [ 0 ] . clientX * 2
var current_y = e . touches [ 0 ] . clientY * 2
var diff_x = current_x - this . start_x
var diff_y = current_y - this . start_y
switch ( e . target . id ) {
case 'sticker' : {
// 拖动组件则所有控件同时移动
this . setData ( {
stickerCenterX : this . data . stickerCenterX + diff_x ,
stickerCenterY : this . data . stickerCenterY + diff_y ,
removeCenterX : this . data . removeCenterX + diff_x ,
removeCenterY : this . data . removeCenterY + diff_y ,
handleCenterX : this . data . handleCenterX + diff_x ,
handleCenterY : this . data . handleCenterY + diff_y
} )
break
}
case 'handle' : {
// 拖动操作按钮则原地旋转缩放
this . setData ( {
handleCenterX : this . data . handleCenterX + diff_x ,
handleCenterY : this . data . handleCenterY + diff_y
} )
var diff_x_before = this . handle_center_x - this . sticker_center_x ;
var diff_y_before = this . handle_center_y - this . sticker_center_y ;
var diff_x_after = this . data . handleCenterX - this . sticker_center_x ;
var diff_y_after = this . data . handleCenterY - this . sticker_center_y ;
var distance_before = Math . sqrt ( diff_x_before * diff_x_before + diff_y_before * diff_y_before ) ;
var distance_after = Math . sqrt ( diff_x_after * diff_x_after + diff_y_after * diff_y_after ) ;
var angle_before = Math . atan2 ( diff_y_before , diff_x_before ) / Math . PI * 180 ;
var angle_after = Math . atan2 ( diff_y_after , diff_x_after ) / Math . PI * 180 ;
this . setData ( {
scale : distance_after / distance_before * this . scale ,
rotate : angle_after - angle_before + this . rotate
} )
break
}
}
this . start_x = current_x ;
this . start_y = current_y ;
}
sticker
(stiker yang disertakan dengan perangkat lunak), image
(gambar yang diunggah oleh pengguna) dan text
(teks khusus), yang semuanya disimpan dalam objek json dalam format berikut Semua berisi ID unik dan informasi terkait. Saat menyimpan, objek dihasilkan oleh klien dan dikodekan ke dalam string json dan disimpan dalam database. Saat status pengeditan dipulihkan, objek diperoleh dengan menguraikan string json dan kemudian dirender oleh halaman pengeditan. {
"backgroundId" : "5" , 背景图id
"assemblies" : [
{
"id" : "jhjg" , 组件id
"component_type" : "image" , 组件类型(自定义图片)
"image_url" : "https://example.com/jhjg.png" , 图片地址
"stickerCenterX" : 269 , 中心横坐标
"stickerCenterY" : 664 , 中心纵坐标
"scale" : 1.7123667831396403 , 缩放比例
"rotate" : - 3.0127875041833434 , 旋转角度
"wh_scale" : 1 , 图片宽高比
"z_index" : 19 组件层级
} ,
{
"id" : "gs47" ,
"component_type" : "text" , 组件类型(文字)
"text" : "test" , 文字内容
"stickerCenterX" : 479 ,
"stickerCenterY" : 546 ,
"scale" : 1.808535318980528 ,
"rotate" : 29.11614626607893 ,
"z_index" : 10
} ,
{
"id" : "chjn" ,
"component_type" : "sticker" , 组件类型(贴纸)
"sticker_type" : "food" , 贴纸类型
"sticker_id" : "1" , 贴纸id
"image_url" : "https://example.com/weapp/stickers/food/1.png" ,
"stickerCenterX" : 277 ,
"stickerCenterY" : 260 ,
"scale" : 1.3984276885130673 ,
"rotate" : - 16.620756913892055 ,
"z_index" : 5
}
]
}
Lisensi MIT
Hak Cipta (c) 2021 Ye Liu