feat: Add low resolution character retrieval functionality

This commit is contained in:
2025-11-17 20:20:43 +08:00
parent 27bda316df
commit 5d1e43f88d
4 changed files with 135 additions and 4 deletions

View File

@@ -312,7 +312,7 @@ func handleUpdateCharacterImage(c fiber.Ctx) error {
if err != nil { if err != nil {
return model.NewRequestError("Invalid character ID") return model.NewRequestError("Invalid character ID")
} }
var params struct { var params struct {
ImageID uint `json:"image_id"` ImageID uint `json:"image_id"`
} }
@@ -321,17 +321,17 @@ func handleUpdateCharacterImage(c fiber.Ctx) error {
if err != nil { if err != nil {
return model.NewRequestError("Invalid request body") return model.NewRequestError("Invalid request body")
} }
uid, ok := c.Locals("uid").(uint) uid, ok := c.Locals("uid").(uint)
if !ok { if !ok {
return model.NewUnAuthorizedError("You must be logged in to update a character") return model.NewUnAuthorizedError("You must be logged in to update a character")
} }
err = service.UpdateCharacterImage(uid, uint(resourceId), uint(characterId), params.ImageID) err = service.UpdateCharacterImage(uid, uint(resourceId), uint(characterId), params.ImageID)
if err != nil { if err != nil {
return err return err
} }
return c.Status(fiber.StatusOK).JSON(model.Response[any]{ return c.Status(fiber.StatusOK).JSON(model.Response[any]{
Success: true, Success: true,
Data: nil, Data: nil,
@@ -339,6 +339,51 @@ func handleUpdateCharacterImage(c fiber.Ctx) error {
}) })
} }
func handleGetLowResolutionCharacters(c fiber.Ctx) error {
pageStr := c.Query("page")
if pageStr == "" {
pageStr = "1"
}
page, err := strconv.Atoi(pageStr)
if err != nil {
return model.NewRequestError("Invalid page number")
}
maxWidthStr := c.Query("max_width")
if maxWidthStr == "" {
maxWidthStr = "800" // 默认最大宽度800px
}
maxWidth, err := strconv.Atoi(maxWidthStr)
if err != nil {
return model.NewRequestError("Invalid max_width parameter")
}
maxHeightStr := c.Query("max_height")
if maxHeightStr == "" {
maxHeightStr = "800" // 默认最大高度800px
}
maxHeight, err := strconv.Atoi(maxHeightStr)
if err != nil {
return model.NewRequestError("Invalid max_height parameter")
}
characters, totalPages, err := service.GetLowResolutionCharacters(page, maxWidth, maxHeight)
if err != nil {
return err
}
if characters == nil {
characters = []model.LowResCharacterView{}
}
return c.Status(fiber.StatusOK).JSON(model.PageResponse[model.LowResCharacterView]{
Success: true,
Data: characters,
TotalPages: totalPages,
Message: "Low resolution characters retrieved successfully",
})
}
func AddResourceRoutes(api fiber.Router) { func AddResourceRoutes(api fiber.Router) {
resource := api.Group("/resource") resource := api.Group("/resource")
{ {
@@ -348,6 +393,7 @@ func AddResourceRoutes(api fiber.Router) {
resource.Get("/random", handleGetRandomResource) resource.Get("/random", handleGetRandomResource)
resource.Get("/pinned", handleGetPinnedResources) resource.Get("/pinned", handleGetPinnedResources)
resource.Get("/vndb/characters", handleGetCharactersFromVndb) resource.Get("/vndb/characters", handleGetCharactersFromVndb)
resource.Get("/characters/low-resolution", handleGetLowResolutionCharacters)
resource.Get("/:id", handleGetResource) resource.Get("/:id", handleGetResource)
resource.Delete("/:id", handleDeleteResource) resource.Delete("/:id", handleDeleteResource)
resource.Get("/tag/:tag", handleListResourcesWithTag) resource.Get("/tag/:tag", handleListResourcesWithTag)

View File

@@ -544,3 +544,52 @@ func UpdateCharacterImage(characterID, imageID uint) error {
} }
return nil return nil
} }
// GetLowResolutionCharacters 获取低清晰度的角色图片
// maxWidth和maxHeight定义了低清晰度的阈值
func GetLowResolutionCharacters(maxWidth, maxHeight int, limit int, offset int) ([]model.LowResCharacterView, error) {
var results []model.LowResCharacterView
query := `
SELECT
c.id as character_id,
c.resource_id as resource_id,
c.name as name,
i.id as image_id,
i.width as image_width,
i.height as image_height
FROM characters c
INNER JOIN images i ON c.image_id = i.id
WHERE (i.width <= ? OR i.height <= ?)
AND c.image_id IS NOT NULL
ORDER BY c.id
LIMIT ? OFFSET ?
`
err := db.Raw(query, maxWidth, maxHeight, limit, offset).Scan(&results).Error
if err != nil {
return nil, err
}
return results, nil
}
// GetLowResolutionCharactersCount 获取低清晰度角色的总数
func GetLowResolutionCharactersCount(maxWidth, maxHeight int) (int64, error) {
var count int64
query := `
SELECT COUNT(*)
FROM characters c
INNER JOIN images i ON c.image_id = i.id
WHERE (i.width <= ? OR i.height <= ?)
AND c.image_id IS NOT NULL
`
err := db.Raw(query, maxWidth, maxHeight).Scan(&count).Error
if err != nil {
return 0, err
}
return count, nil
}

View File

@@ -20,6 +20,15 @@ type CharacterView struct {
Image uint `json:"image"` Image uint `json:"image"`
} }
type LowResCharacterView struct {
CharacterID uint `json:"character_id"`
ResourceID uint `json:"resource_id"`
Name string `json:"name"`
ImageID uint `json:"image_id"`
ImageWidth int `json:"image_width"`
ImageHeight int `json:"image_height"`
}
func (c *Character) ToView() *CharacterView { func (c *Character) ToView() *CharacterView {
var imageID uint var imageID uint
if c.ImageID != nil { if c.ImageID != nil {

View File

@@ -801,3 +801,30 @@ func UpdateCharacterImage(uid, resourceID, characterID, imageID uint) error {
return nil return nil
} }
// GetLowResolutionCharacters 获取低清晰度的角色图片
func GetLowResolutionCharacters(page int, maxWidth, maxHeight int) ([]model.LowResCharacterView, int, error) {
const pageSize = 50 // 每页50个角色
if page <= 0 {
page = 1
}
offset := (page - 1) * pageSize
// 获取角色列表
characters, err := dao.GetLowResolutionCharacters(maxWidth, maxHeight, pageSize, offset)
if err != nil {
return nil, 0, err
}
// 获取总数
totalCount, err := dao.GetLowResolutionCharactersCount(maxWidth, maxHeight)
if err != nil {
return nil, 0, err
}
totalPages := int((totalCount + int64(pageSize) - 1) / int64(pageSize))
return characters, totalPages, nil
}