mirror of
https://github.com/lifegpc/pixiv_downloader.git
synced 2026-07-08 01:32:41 +08:00
Update
This commit is contained in:
@@ -7,6 +7,8 @@ use modular_bitfield::bitfield;
|
||||
use modular_bitfield::prelude::B30;
|
||||
use std::fmt::Debug;
|
||||
use std::fmt::Display;
|
||||
use std::io::Read;
|
||||
use std::io::Write;
|
||||
use std::sync::RwLock;
|
||||
|
||||
/// The data is out of bounds.
|
||||
@@ -62,11 +64,28 @@ impl PdFilePartStatus {
|
||||
Self { status: RwLock::new(status) }
|
||||
}
|
||||
|
||||
#[inline]
|
||||
/// Returns the downloaded size of this part
|
||||
pub fn downloaded_size(&self) -> u32 {
|
||||
self.status.get_ref().downloaded_size()
|
||||
}
|
||||
|
||||
#[inline]
|
||||
/// Returns the status of this part
|
||||
pub fn status(&self) -> PdFilePartStatus2 {
|
||||
self.status.get_ref().status()
|
||||
}
|
||||
|
||||
/// Set the new downloaded size
|
||||
pub fn set_downloaded_size(&self, new_size: u32) -> Result<(), PdFileError> {
|
||||
match self.status.get_mut().set_downloaded_size_checked(new_size) {
|
||||
Ok(_) => { Ok(()) }
|
||||
Err(_) => {
|
||||
Err(PdFileError::from(OutOfBoundsError::new("u32", new_size)))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Set the status of this part
|
||||
pub fn set_status(&self, status: PdFilePartStatus2) -> Result<(), PdFileError> {
|
||||
match self.status.get_mut().set_status_checked(status) {
|
||||
@@ -107,12 +126,48 @@ impl PdFilePartStatus {
|
||||
if (value.len() - offset) < 4 {
|
||||
Err(gettext("At least 4 bytes is needed."))?;
|
||||
}
|
||||
let st = (value[offset] & 0xC0) / 0x20;
|
||||
let st = (value[offset] & 0xC0) / 0x40;
|
||||
let mut status = PdFilePartStatusInternal::new();
|
||||
status.set_status(PdFilePartStatus2::from_int(st)?);
|
||||
// #TODO
|
||||
// Downloaded size
|
||||
let mut ds: u32 = (value[offset] & 0x3f) as u32;
|
||||
ds += (value[offset + 1] as u32) * 0x40;
|
||||
ds += (value[offset + 2] as u32) * 0x40_00;
|
||||
ds += (value[offset + 3] as u32) * 0x40_00_00;
|
||||
status.set_downloaded_size(ds);
|
||||
Ok(Self { status: RwLock::new(status) })
|
||||
}
|
||||
|
||||
/// Get bytes
|
||||
pub fn to_bytes(&self) -> Vec<u8> {
|
||||
let mut data = Vec::new();
|
||||
let mut tmp: u8 = self.status().int_value() * 0x40;
|
||||
let ds = self.downloaded_size();
|
||||
tmp += (ds & 0x3f) as u8;
|
||||
data.push(tmp);
|
||||
data.push(((ds & 0x3fc0) / 0x40) as u8);
|
||||
data.push(((ds & 0x3f_c0_00) / 0x40_00) as u8);
|
||||
data.push(((ds & 0x3f_c0_00_00) / 0x40_00_00) as u8);
|
||||
data
|
||||
}
|
||||
|
||||
/// Create a new instance of the [PdFilePartStatus] from reader
|
||||
/// * `reader` - The reader which implement the [Read] trait
|
||||
///
|
||||
/// Returns Error or [PdFilePartStatus] instance.
|
||||
pub fn read_from<R: Read>(reader: &mut R) -> Result<Self, PdFileError> {
|
||||
let mut buf = [0u8; 4];
|
||||
reader.read_exact(&mut buf)?;
|
||||
Self::from_bytes(&buf, 0)
|
||||
}
|
||||
|
||||
/// Write version bytes to writer.
|
||||
/// * `writer` - The writer which implement the [Write] trait
|
||||
///
|
||||
/// Returns io Result.
|
||||
pub fn write_to<W: Write>(&self, writer: &mut W) -> std::io::Result<()> {
|
||||
writer.write_all(&self.to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -121,6 +176,11 @@ fn test_part_status() {
|
||||
let status = PdFilePartStatus::new();
|
||||
assert_eq!(status.status(), PdFilePartStatus2::Waited);
|
||||
assert_eq!(status.is_waited(), true);
|
||||
let status = PdFilePartStatus::from_bytes(&[80u8, 0, 0, 0], 0).unwrap();
|
||||
let status = PdFilePartStatus::from_bytes(&[132u8, 23, 3, 2], 0).unwrap();
|
||||
assert_eq!(status.is_downloaded(), true);
|
||||
assert_eq!(status.downloaded_size(), 0x80c5c4);
|
||||
assert_eq!(status.to_bytes(), vec![132, 23, 3, 2]);
|
||||
status.set_downloaded_size(0x323133).unwrap();
|
||||
assert_eq!(status.downloaded_size(), 0x323133);
|
||||
assert_eq!(status.to_bytes(), vec![179, 196, 200, 0]);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user