/* Library Machines * * Contains: * Borrowbook datum * Library Public Computer * Library Computer * Library Scanner * Book Binder */ /* * Borrowbook datum */ datum/borrowbook // Datum used to keep track of who has borrowed what when and for how long. var/bookname var/mobname var/getdate var/duedate /* * Library Public Computer */ /obj/machinery/librarypubliccomp name = "visitor computer" icon = 'icons/obj/library.dmi' icon_state = "computer" anchored = 1 density = 1 var/screenstate = 0 var/title var/category = "Any" var/author var/SQLquery /obj/machinery/librarypubliccomp/attack_hand(var/mob/user as mob) usr.set_machine(src) var/dat = "Library Visitor\n" // switch(screenstate) if(0) dat += {"

Search Settings


Filter by Title: [title]
Filter by Category: [category]
Filter by Author: [author]
\[Start Search\]
"} if(1) establish_old_db_connection() if(!dbcon_old.IsConnected()) dat += "ERROR: Unable to contact External Archive. Please contact your system administrator for assistance.
" else if(!SQLquery) dat += "ERROR: Malformed search request. Please contact your system administrator for assistance.
" else dat += {""} var/DBQuery/query = dbcon_old.NewQuery(SQLquery) query.Execute() while(query.NextRow()) var/author = query.item[1] var/title = query.item[2] var/category = query.item[3] var/id = query.item[4] dat += "" dat += "
AUTHORTITLECATEGORYSS13BN
[author][title][category][id]

" dat += "\[Go Back\]
" user << browse(dat, "window=publiclibrary") onclose(user, "publiclibrary") /obj/machinery/librarypubliccomp/Topic(href, href_list) if(..()) usr << browse(null, "window=publiclibrary") onclose(usr, "publiclibrary") return if(href_list["settitle"]) var/newtitle = input("Enter a title to search for:") as text|null if(newtitle) title = sanitize(newtitle) else title = null title = sanitizeSQL(title) if(href_list["setcategory"]) var/newcategory = input("Choose a category to search for:") in list("Any", "Fiction", "Non-Fiction", "Adult", "Reference", "Religion") if(newcategory) category = sanitize(newcategory) else category = "Any" category = sanitizeSQL(category) if(href_list["setauthor"]) var/newauthor = input("Enter an author to search for:") as text|null if(newauthor) author = sanitize(newauthor) else author = null author = sanitizeSQL(author) if(href_list["search"]) SQLquery = "SELECT author, title, category, id FROM library WHERE " if(category == "Any") SQLquery += "author LIKE '%[author]%' AND title LIKE '%[title]%'" else SQLquery += "author LIKE '%[author]%' AND title LIKE '%[title]%' AND category='[category]'" screenstate = 1 if(href_list["back"]) screenstate = 0 src.add_fingerprint(usr) src.updateUsrDialog() return /* * Library Computer */ // TODO: Make this an actual /obj/machinery/computer that can be crafted from circuit boards and such // It is August 22nd, 2012... This TODO has already been here for months.. I wonder how long it'll last before someone does something about it. // Nov 2019. Nope. /obj/machinery/librarycomp name = "Check-In/Out Computer" desc = "Print books from the archives! (You aren't quite sure how they're printed by it, though.)" icon = 'icons/obj/library.dmi' icon_state = "computer" anchored = 1 density = 1 var/arcanecheckout = 0 var/screenstate = 0 // 0 - Main Menu, 1 - Inventory, 2 - Checked Out, 3 - Check Out a Book var/sortby = "author" var/buffer_book var/buffer_mob var/upload_category = "Fiction" var/list/checkouts = list() var/list/inventory = list() var/checkoutperiod = 5 // In minutes var/obj/machinery/libraryscanner/scanner // Book scanner that will be used when uploading books to the Archive var/bibledelay = 0 // LOL NO SPAM (1 minute delay) -- Doohl var/static/list/all_books var/static/list/base_genre_books /obj/machinery/librarycomp/Initialize() ..() if(!base_genre_books || !base_genre_books.len) base_genre_books = list( /obj/item/weapon/book/custom_library/fiction, /obj/item/weapon/book/custom_library/nonfiction, /obj/item/weapon/book/custom_library/reference, /obj/item/weapon/book/custom_library/religious, /obj/item/weapon/book/bundle/custom_library/fiction, /obj/item/weapon/book/bundle/custom_library/nonfiction, /obj/item/weapon/book/bundle/custom_library/reference, /obj/item/weapon/book/bundle/custom_library/religious ) if(!all_books || !all_books.len) all_books = list() for(var/path in subtypesof(/obj/item/weapon/book/codex/lore)) var/obj/item/weapon/book/C = new path(null) all_books[C.name] = C for(var/path in subtypesof(/obj/item/weapon/book/custom_library) - base_genre_books) var/obj/item/weapon/book/B = new path(null) all_books[B.title] = B for(var/path in subtypesof(/obj/item/weapon/book/bundle/custom_library) - base_genre_books) var/obj/item/weapon/book/M = new path(null) all_books[M.title] = M /obj/machinery/librarycomp/attack_hand(var/mob/user as mob) usr.set_machine(src) var/dat = "Book Inventory Management\n" // switch(screenstate) if(0) // Main Menu dat += {"1. View General Inventory
2. View Checked Out Inventory
3. Check out a Book
4. Connect to NanoTrasen Archive
5. Upload New Title to Archive
6. Print a Bible
8. Access Deprecated Archive
"} if(src.emagged) dat += "7. Access the Forbidden Lore Vault
" if(src.arcanecheckout) new /obj/item/weapon/book/tome(src.loc) var/datum/gender/T = gender_datums[user.get_visible_gender()] to_chat(user, "Your sanity barely endures the seconds spent in the vault's browsing window. The only thing to remind you of this when you stop browsing is a dusty old tome sitting on the desk. You don't really remember printing it.") user.visible_message("\The [user] stares at the blank screen for a few moments, [T.his] expression frozen in fear. When [T.he] finally awakens from it, [T.he] looks a lot older.", 2) src.arcanecheckout = 0 if(1) // Inventory dat += "

Inventory


" for(var/obj/item/weapon/book/b in inventory) dat += "[b.name] (Delete)
" dat += "(Return to main menu)
" if(2) // Checked Out dat += "

Checked Out Books


" for(var/datum/borrowbook/b in checkouts) var/timetaken = world.time - b.getdate //timetaken *= 10 timetaken /= 600 timetaken = round(timetaken) var/timedue = b.duedate - world.time //timedue *= 10 timedue /= 600 if(timedue <= 0) timedue = "(OVERDUE) [timedue]" else timedue = round(timedue) dat += {"\"[b.bookname]\", Checked out to: [b.mobname]
--- Taken: [timetaken] minutes ago, Due: in [timedue] minutes
(Check In)

"} dat += "(Return to main menu)
" if(3) // Check Out a Book dat += {"

Check Out a Book


Book: [src.buffer_book] \[Edit\]
Recipient: [src.buffer_mob] \[Edit\]
Checkout Date : [world.time/600]
Due Date: [(world.time + checkoutperiod)/600]
(Checkout Period: [checkoutperiod] minutes) (+/-) (Commit Entry)
(Return to main menu)
"} if(4) <<<<<<< HEAD dat += "

External Archive

" //VOREStation Edit establish_old_db_connection() // dat += "

Warning: System Administrator has slated this archive for removal. Personal uploads should be taken to the NT board of internal literature.

" //VOREStation Removal TFF 29/1/20 - Redundant warning, we're not removing our library entries. if(!dbcon_old.IsConnected()) dat += "ERROR: Unable to contact External Archive. Please contact your system administrator for assistance." ======= dat += "

NT Internal Archive

" if(!all_books || !all_books.len) dat += "ERROR Something has gone seriously wrong. Contact System Administrator for more information." >>>>>>> b3f9ecd... Reorganized Library Computer Menu (#7334) else dat += {"" dat += "
TITLE\[Order\]
" dat += "
(Return to main menu)
" if(5) //dat += "

ERROR

" //VOREStation Removal //dat+= "Library Database is in Secure Management Mode.
\ //VOREStation Removal //Contact a System Administrator for more information.
" //VOREStation Removal //VOREstation Edit Start dat += "

Upload a New Title

" if(!scanner) for(var/obj/machinery/libraryscanner/S in range(9)) scanner = S break if(!scanner) dat += "No scanner found within wireless network range.
" else if(!scanner.cache) dat += "No data found in scanner memory.
" else dat += {"Data marked for upload...
Title: [scanner.cache.name]
"} if(!scanner.cache.author) scanner.cache.author = "Anonymous" dat += {"Author: [scanner.cache.author]
Category: [upload_category]
\[Upload\]
"} //VOREStation Edit End dat += "(Return to main menu)
" if(7) dat += {"

Accessing Forbidden Lore Vault v 1.3

Are you absolutely sure you want to proceed? EldritchTomes Inc. takes no responsibilities for loss of sanity resulting from this action.

Yes.
No.
"} if(8) dat += "

Deprecated Archive

" establish_old_db_connection() dat += "

Warning: System Administrator has slated this archive for removal. Personal uploads should be taken to the NT board of internal literature.

" if(!dbcon_old.IsConnected()) dat += "ERROR: Unable to contact External Archive. Please contact your system administrator for assistance." else dat += {"(Order book by SS13BN)

" dat += "
TITLE\[Order\]
" dat += "
(Return to main menu)
" //dat += "Close

" user << browse(dat, "window=library") onclose(user, "library") /obj/machinery/librarycomp/emag_act(var/remaining_charges, var/mob/user) if (src.density && !src.emagged) src.emagged = 1 return 1 /obj/machinery/librarycomp/attackby(obj/item/weapon/W as obj, mob/user as mob) if(istype(W, /obj/item/weapon/barcodescanner)) var/obj/item/weapon/barcodescanner/scanner = W scanner.computer = src to_chat(user, "[scanner]'s associated machine has been set to [src].") for (var/mob/V in hearers(src)) V.show_message("[src] lets out a low, short blip.", 2) else ..() /obj/machinery/librarycomp/Topic(href, href_list) if(..()) usr << browse(null, "window=library") onclose(usr, "library") return if(href_list["switchscreen"]) switch(href_list["switchscreen"]) if("0") screenstate = 0 if("1") screenstate = 1 if("2") screenstate = 2 if("3") screenstate = 3 if("4") screenstate = 4 if("5") screenstate = 5 if("6") if(!bibledelay) var/obj/item/weapon/storage/bible/B = new /obj/item/weapon/storage/bible(src.loc) if(ticker && ( ticker.Bible_icon_state && ticker.Bible_item_state) ) B.icon_state = ticker.Bible_icon_state B.item_state = ticker.Bible_item_state B.name = ticker.Bible_name B.deity_name = ticker.Bible_deity_name bibledelay = 1 spawn(60) bibledelay = 0 else for (var/mob/V in hearers(src)) V.show_message("[src]'s monitor flashes, \"Bible printer currently unavailable, please wait a moment.\"") if("7") screenstate = 7 if("8") screenstate = 8 if(href_list["arccheckout"]) if(src.emagged) src.arcanecheckout = 1 src.screenstate = 0 if(href_list["increasetime"]) checkoutperiod += 1 if(href_list["decreasetime"]) checkoutperiod -= 1 if(checkoutperiod < 1) checkoutperiod = 1 if(href_list["editbook"]) buffer_book = sanitizeSafe(input("Enter the book's title:") as text|null) if(href_list["editmob"]) buffer_mob = sanitize(input("Enter the recipient's name:") as text|null, MAX_NAME_LEN) if(href_list["checkout"]) var/datum/borrowbook/b = new /datum/borrowbook b.bookname = sanitizeSafe(buffer_book) b.mobname = sanitize(buffer_mob) b.getdate = world.time b.duedate = world.time + (checkoutperiod * 600) checkouts.Add(b) if(href_list["checkin"]) var/datum/borrowbook/b = locate(href_list["checkin"]) checkouts.Remove(b) if(href_list["delbook"]) var/obj/item/weapon/book/b = locate(href_list["delbook"]) inventory.Remove(b) if(href_list["setauthor"]) var/newauthor = sanitize(input("Enter the author's name: ") as text|null) if(newauthor) scanner.cache.author = newauthor if(href_list["setcategory"]) var/newcategory = input("Choose a category: ") in list("Fiction", "Non-Fiction", "Adult", "Reference", "Religion") if(newcategory) upload_category = newcategory //VOREStation Edit Start if(href_list["upload"]) if(scanner) if(scanner.cache) var/choice = input("Are you certain you wish to upload this title to the Archive?") in list("Confirm", "Abort") if(choice == "Confirm") if(scanner.cache.unique) alert("This book has been rejected from the database. Aborting!") else establish_old_db_connection() if(!dbcon_old.IsConnected()) alert("Connection to Archive has been severed. Aborting.") else /* var/sqltitle = dbcon.Quote(scanner.cache.name) var/sqlauthor = dbcon.Quote(scanner.cache.author) var/sqlcontent = dbcon.Quote(scanner.cache.dat) var/sqlcategory = dbcon.Quote(upload_category) */ var/sqltitle = sanitizeSQL(scanner.cache.name) var/sqlauthor = sanitizeSQL(scanner.cache.author) var/sqlcontent = sanitizeSQL(scanner.cache.dat) var/sqlcategory = sanitizeSQL(upload_category) var/DBQuery/query = dbcon_old.NewQuery("INSERT INTO library (author, title, content, category) VALUES ('[sqlauthor]', '[sqltitle]', '[sqlcontent]', '[sqlcategory]')") if(!query.Execute()) to_chat(usr,query.ErrorMsg()) else log_game("[usr.name]/[usr.key] has uploaded the book titled [scanner.cache.name], [length(scanner.cache.dat)] signs") alert("Upload Complete.") //VOREStation Edit End if(href_list["targetid"]) var/sqlid = sanitizeSQL(href_list["targetid"]) establish_old_db_connection() if(!dbcon_old.IsConnected()) alert("Connection to Archive has been severed. Aborting.") if(bibledelay) for (var/mob/V in hearers(src)) V.show_message("[src]'s monitor flashes, \"Printer unavailable. Please allow a short time before attempting to print.\"") else bibledelay = 1 spawn(6) bibledelay = 0 var/DBQuery/query = dbcon_old.NewQuery("SELECT * FROM library WHERE id=[sqlid]") query.Execute() while(query.NextRow()) var/author = query.item[2] var/title = query.item[3] var/content = query.item[4] var/obj/item/weapon/book/B = new(src.loc) B.name = "Book: [title]" B.title = title B.author = author B.dat = content B.icon_state = "book[rand(1,16)]" B.item_state = B.icon_state src.visible_message("[src]'s printer hums as it produces a completely bound book. How did it do that?") break if(href_list["orderbyid"]) var/orderid = input("Enter your order:") as num|null if(orderid) if(isnum(orderid)) var/nhref = "src=\ref[src];targetid=[orderid]" spawn() src.Topic(nhref, params2list(nhref), src) if(href_list["sort"] in list("author", "title", "category")) sortby = href_list["sort"] if(href_list["hardprint"]) var/newpath = href_list["hardprint"] var/obj/item/weapon/book/NewBook = new newpath(get_turf(src)) NewBook.name = "Book: [NewBook.name]" src.add_fingerprint(usr) src.updateUsrDialog() return /* * Library Scanner */ /obj/machinery/libraryscanner name = "scanner" desc = "A scanner for scanning in books and papers." icon = 'icons/obj/library.dmi' icon_state = "bigscanner" anchored = 1 density = 1 var/obj/item/weapon/book/cache // Last scanned book /obj/machinery/libraryscanner/attackby(var/obj/O as obj, var/mob/user as mob) if(istype(O, /obj/item/weapon/book)) user.drop_item() O.loc = src /obj/machinery/libraryscanner/attack_hand(var/mob/user as mob) usr.set_machine(src) var/dat = "Scanner Control Interface\n" // if(cache) dat += "Data stored in memory.
" else dat += "No data stored in memory.
" dat += "\[Scan\]" if(cache) dat += " \[Clear Memory\]

\[Remove Book\]" else dat += "
" user << browse(dat, "window=scanner") onclose(user, "scanner") /obj/machinery/libraryscanner/Topic(href, href_list) if(..()) usr << browse(null, "window=scanner") onclose(usr, "scanner") return if(href_list["scan"]) for(var/obj/item/weapon/book/B in contents) cache = B break if(href_list["clear"]) cache = null if(href_list["eject"]) for(var/obj/item/weapon/book/B in contents) B.loc = src.loc src.add_fingerprint(usr) src.updateUsrDialog() return /* * Book binder */ /obj/machinery/bookbinder name = "Book Binder" desc = "Bundles up a stack of inserted paper into a convenient book format." icon = 'icons/obj/library.dmi' icon_state = "binder" anchored = 1 density = 1 /obj/machinery/bookbinder/attackby(var/obj/O as obj, var/mob/user as mob) if(istype(O, /obj/item/weapon/paper) || istype(O, /obj/item/weapon/paper_bundle)) if(istype(O, /obj/item/weapon/paper)) user.drop_item() O.loc = src user.visible_message("[user] loads some paper into [src].", "You load some paper into [src].") src.visible_message("[src] begins to hum as it warms up its printing drums.") sleep(rand(200,400)) src.visible_message("[src] whirs as it prints and binds a new book.") var/obj/item/weapon/book/b = new(src.loc) b.dat = O:info b.name = "Print Job #" + "[rand(100, 999)]" b.icon_state = "book[rand(1,7)]" qdel(O) else user.drop_item() O.loc = src user.visible_message("[user] loads some paper into [src].", "You load some paper into [src].") src.visible_message("[src] begins to hum as it warms up its printing drums.") sleep(rand(300,500)) src.visible_message("[src] whirs as it prints and binds a new book.") var/obj/item/weapon/book/bundle/b = new(src.loc) b.pages = O:pages for(var/obj/item/weapon/paper/P in O.contents) P.forceMove(b) for(var/obj/item/weapon/photo/P in O.contents) P.forceMove(b) b.name = "Print Job #" + "[rand(100, 999)]" b.icon_state = "book[rand(1,7)]" qdel(O) else ..()