github.com/df-mc/dragonfly@v0.9.13/server/item/book_and_quill.go (about) 1 package item 2 3 import "slices" 4 5 // BookAndQuill is an item used to write WrittenBook(s). 6 type BookAndQuill struct { 7 // Pages represents the pages within the book. 8 Pages []string 9 } 10 11 // MaxCount always returns 1. 12 func (BookAndQuill) MaxCount() int { 13 return 1 14 } 15 16 // TotalPages returns the total number of pages in the book. 17 func (b BookAndQuill) TotalPages() int { 18 return len(b.Pages) 19 } 20 21 // Page returns a specific page from the book and true when the page exists. It will otherwise return an empty string 22 // and false. 23 func (b BookAndQuill) Page(page int) (string, bool) { 24 if page < 0 || len(b.Pages) <= page { 25 return "", false 26 } 27 return b.Pages[page], true 28 } 29 30 // DeletePage attempts to delete a page from the book. 31 func (b BookAndQuill) DeletePage(page int) BookAndQuill { 32 if page < 0 || page >= 50 { 33 panic("invalid page number") 34 } 35 if _, ok := b.Page(page); !ok { 36 panic("cannot delete nonexistent page") 37 } 38 b.Pages = slices.Delete(b.Pages, page, page+1) 39 return b 40 } 41 42 // InsertPage attempts to insert a page within the book 43 func (b BookAndQuill) InsertPage(page int, text string) BookAndQuill { 44 if page < 0 || page >= 50 { 45 panic("invalid page number") 46 } 47 if len(text) > 256 { 48 panic("text longer then 256 bytes") 49 } 50 if page > len(b.Pages) { 51 panic("unable to insert page at invalid position") 52 } 53 b.Pages = slices.Insert(b.Pages, page, text) 54 return b 55 } 56 57 // SetPage writes a page to the book, if the page doesn't exist it will be created. It will panic if the 58 // text is longer then 256 characters. It will return a new book representing this data. 59 func (b BookAndQuill) SetPage(page int, text string) BookAndQuill { 60 if page < 0 || page >= 50 { 61 panic("invalid page number") 62 } 63 if len(text) > 256 { 64 panic("text longer then 256 bytes") 65 } 66 if _, ok := b.Page(page); !ok { 67 pages := make([]string, page+1) 68 copy(pages, b.Pages) 69 b.Pages = pages 70 } 71 b.Pages[page] = text 72 return b 73 } 74 75 // SwapPages swaps two different pages, it will panic if the largest of the two numbers doesn't exist. It will 76 // return the newly updated pages. 77 func (b BookAndQuill) SwapPages(pageOne, pageTwo int) BookAndQuill { 78 if pageOne < 0 || pageTwo < 0 { 79 panic("negative page number") 80 } 81 if _, ok := b.Page(max(pageOne, pageTwo)); !ok { 82 panic("invalid page number") 83 } 84 temp := b.Pages[pageOne] 85 b.Pages[pageOne] = b.Pages[pageTwo] 86 b.Pages[pageTwo] = temp 87 return b 88 } 89 90 // DecodeNBT ... 91 func (b BookAndQuill) DecodeNBT(data map[string]any) any { 92 pages, _ := data["pages"].([]any) 93 for _, page := range pages { 94 if pageData, ok := page.(map[string]any); ok { 95 if text, ok := pageData["text"].(string); ok { 96 b.Pages = append(b.Pages, text) 97 } 98 } 99 } 100 return b 101 } 102 103 // EncodeNBT ... 104 func (b BookAndQuill) EncodeNBT() map[string]any { 105 pages := make([]any, 0, len(b.Pages)) 106 for _, page := range b.Pages { 107 pages = append(pages, map[string]any{"text": page}) 108 } 109 return map[string]any{"pages": pages} 110 } 111 112 // EncodeItem ... 113 func (BookAndQuill) EncodeItem() (name string, meta int16) { 114 return "minecraft:writable_book", 0 115 } 116 117 // max ... 118 func max(a, b int) int { 119 if a > b { 120 return a 121 } 122 return b 123 }