Support parsing Tinyboard posts.
This commit is contained in:
parent
b26a1806cf
commit
ffdb2cbd5c
@ -63,8 +63,3 @@ Get =
|
|||||||
quotelinks.filter (quotelink) ->
|
quotelinks.filter (quotelink) ->
|
||||||
{boardID, postID} = Get.postDataFromLink quotelink
|
{boardID, postID} = Get.postDataFromLink quotelink
|
||||||
boardID is post.board.ID and postID is post.ID
|
boardID is post.board.ID and postID is post.ID
|
||||||
|
|
||||||
scriptData: ->
|
|
||||||
for script in $$ 'script:not([src])', d.head
|
|
||||||
return script.textContent if /\bcooldowns *=/.test script.textContent
|
|
||||||
''
|
|
||||||
|
|||||||
@ -11,10 +11,10 @@ Post.Clone = class extends Post
|
|||||||
@cloneWithoutVideo nodes.root
|
@cloneWithoutVideo nodes.root
|
||||||
else
|
else
|
||||||
nodes.root.cloneNode true
|
nodes.root.cloneNode true
|
||||||
Post.Clone.prefix or= 0
|
Post.Clone.suffix or= 0
|
||||||
for node in [root, $$('[id]', root)...]
|
for node in [root, $$('[id]', root)...]
|
||||||
node.id = Post.Clone.prefix + node.id
|
node.id += "_#{Post.Clone.suffix}"
|
||||||
Post.Clone.prefix++
|
Post.Clone.suffix++
|
||||||
|
|
||||||
@nodes = @parseNodes root
|
@nodes = @parseNodes root
|
||||||
|
|
||||||
@ -44,12 +44,10 @@ Post.Clone = class extends Post
|
|||||||
@file = {}
|
@file = {}
|
||||||
for key, val of @origin.file
|
for key, val of @origin.file
|
||||||
@file[key] = val
|
@file[key] = val
|
||||||
{fileRoot} = @nodes
|
for key, selector of Site.selectors.file
|
||||||
@file.text = fileRoot.firstElementChild
|
@file[key] = $ selector, @nodes.root
|
||||||
@file.link = $ '.fileText > a, .fileText-original', fileRoot
|
|
||||||
@file.thumb = $ 'a.fileThumb > [data-md5]', fileRoot
|
|
||||||
@file.thumbLink = @file.thumb?.parentNode
|
@file.thumbLink = @file.thumb?.parentNode
|
||||||
@file.fullImage = $ '.full-image', fileRoot
|
@file.fullImage = $ '.full-image', @file.thumbLink if @file.thumbLink
|
||||||
@file.videoControls = $ '.video-controls', @file.text
|
@file.videoControls = $ '.video-controls', @file.text
|
||||||
|
|
||||||
@file.thumb.muted = true if @file.videoThumb
|
@file.thumb.muted = true if @file.videoThumb
|
||||||
|
|||||||
@ -6,7 +6,7 @@ class Post
|
|||||||
@normalizedOriginal = Build.Test.normalize root
|
@normalizedOriginal = Build.Test.normalize root
|
||||||
<% } %>
|
<% } %>
|
||||||
|
|
||||||
@ID = +root.id[2..]
|
@ID = +root.id.match(/\d*$/)[0]
|
||||||
@threadID = @thread.ID
|
@threadID = @thread.ID
|
||||||
@boardID = @board.ID
|
@boardID = @board.ID
|
||||||
@fullID = "#{@board}.#{@ID}"
|
@fullID = "#{@board}.#{@ID}"
|
||||||
@ -16,12 +16,13 @@ class Post
|
|||||||
|
|
||||||
@nodes = @parseNodes root
|
@nodes = @parseNodes root
|
||||||
|
|
||||||
if not (@isReply = $.hasClass @nodes.post, 'reply')
|
if not (@isReply = @ID isnt @threadID)
|
||||||
@thread.OP = @
|
@thread.OP = @
|
||||||
@thread.isArchived = !!$ '.archivedIcon', @nodes.info
|
for key in ['isSticky', 'isClosed', 'isArchived']
|
||||||
@thread.isSticky = !!$ '.stickyIcon', @nodes.info
|
@thread[key] = if (selector = Site.selectors.icons[key]) then !!$(selector, @nodes.info) else false
|
||||||
@thread.isClosed = @thread.isArchived or !!$ '.closedIcon', @nodes.info
|
if @thread.isArchived
|
||||||
@thread.kill() if @thread.isArchived
|
@thread.isClosed = true
|
||||||
|
@thread.kill()
|
||||||
|
|
||||||
@info =
|
@info =
|
||||||
subject: @nodes.subject?.textContent or undefined
|
subject: @nodes.subject?.textContent or undefined
|
||||||
@ -32,7 +33,7 @@ class Post
|
|||||||
pass: @nodes.pass?.title.match(/\d*$/)[0]
|
pass: @nodes.pass?.title.match(/\d*$/)[0]
|
||||||
flagCode: @nodes.flag?.className.match(/flag-(\w+)/)?[1].toUpperCase()
|
flagCode: @nodes.flag?.className.match(/flag-(\w+)/)?[1].toUpperCase()
|
||||||
flag: @nodes.flag?.title
|
flag: @nodes.flag?.title
|
||||||
date: if @nodes.date then new Date(@nodes.date.dataset.utc * 1000)
|
date: if @nodes.date then new Date(@nodes.date.getAttribute('datetime') or (@nodes.date.dataset.utc * 1000))
|
||||||
|
|
||||||
if Conf['Anonymize']
|
if Conf['Anonymize']
|
||||||
@info.nameBlock = 'Anonymous'
|
@info.nameBlock = 'Anonymous'
|
||||||
@ -62,29 +63,20 @@ class Post
|
|||||||
g.posts.push @fullID, @
|
g.posts.push @fullID, @
|
||||||
|
|
||||||
parseNodes: (root) ->
|
parseNodes: (root) ->
|
||||||
post = $ '.post', root
|
s = Site.selectors
|
||||||
info = $ '.postInfo', post
|
post = $(s.post, root) or root
|
||||||
|
info = $ s.infoRoot, post
|
||||||
nodes =
|
nodes =
|
||||||
root: root
|
root: root
|
||||||
post: post
|
post: post
|
||||||
info: info
|
info: info
|
||||||
subject: $ '.subject', info
|
comment: $ s.comment, post
|
||||||
name: $ '.name', info
|
quotelinks: []
|
||||||
email: $ '.useremail', info
|
|
||||||
tripcode: $ '.postertrip', info
|
|
||||||
uniqueIDRoot: $ '.posteruid', info
|
|
||||||
uniqueID: $ '.posteruid > .hand', info
|
|
||||||
capcode: $ '.capcode.hand', info
|
|
||||||
pass: $ '.n-pu', info
|
|
||||||
flag: $ '.flag, .countryFlag', info
|
|
||||||
date: $ '.dateTime', info
|
|
||||||
nameBlock: $ '.nameBlock', info
|
|
||||||
quote: $ '.postNum > a:nth-of-type(2)', info
|
|
||||||
reply: $ '.replylink', info
|
|
||||||
fileRoot: $ '.file', post
|
|
||||||
comment: $ '.postMessage', post
|
|
||||||
quotelinks: []
|
|
||||||
archivelinks: []
|
archivelinks: []
|
||||||
|
for key, selector of s.info
|
||||||
|
nodes[key] = $ selector, info
|
||||||
|
Site.parseNodes?(@, nodes)
|
||||||
|
nodes.uniqueIDRoot or= nodes.uniqueID
|
||||||
|
|
||||||
# XXX Edge invalidates HTMLCollections when an ancestor node is inserted into another node.
|
# XXX Edge invalidates HTMLCollections when an ancestor node is inserted into another node.
|
||||||
# https://developer.microsoft.com/en-us/microsoft-edge/platform/issues/7560353/
|
# https://developer.microsoft.com/en-us/microsoft-edge/platform/issues/7560353/
|
||||||
@ -108,7 +100,7 @@ class Post
|
|||||||
# 'Comment too long'...
|
# 'Comment too long'...
|
||||||
# EXIF data. (/p/)
|
# EXIF data. (/p/)
|
||||||
@nodes.commentClean = bq = @nodes.comment.cloneNode true
|
@nodes.commentClean = bq = @nodes.comment.cloneNode true
|
||||||
@cleanComment bq
|
Site.cleanComment?(bq)
|
||||||
@info.comment = @nodesToText bq
|
@info.comment = @nodesToText bq
|
||||||
|
|
||||||
commentDisplay: ->
|
commentDisplay: ->
|
||||||
@ -121,7 +113,7 @@ class Post
|
|||||||
# Trailing spaces.
|
# Trailing spaces.
|
||||||
bq = @nodes.commentClean.cloneNode true
|
bq = @nodes.commentClean.cloneNode true
|
||||||
@cleanSpoilers bq unless Conf['Remove Spoilers'] or Conf['Reveal Spoilers']
|
@cleanSpoilers bq unless Conf['Remove Spoilers'] or Conf['Reveal Spoilers']
|
||||||
@cleanCommentDisplay bq
|
Site.cleanCommentDisplay?(bq)
|
||||||
@nodesToText(bq).trim().replace(/\s+$/gm, '')
|
@nodesToText(bq).trim().replace(/\s+$/gm, '')
|
||||||
|
|
||||||
nodesToText: (bq) ->
|
nodesToText: (bq) ->
|
||||||
@ -132,29 +124,15 @@ class Post
|
|||||||
text += node.data or '\n'
|
text += node.data or '\n'
|
||||||
text
|
text
|
||||||
|
|
||||||
cleanComment: (bq) ->
|
|
||||||
if (abbr = $ '.abbr', bq) # 'Comment too long' or 'EXIF data available'
|
|
||||||
for node in $$ '.abbr + br, .exif', bq
|
|
||||||
$.rm node
|
|
||||||
for i in [0...2]
|
|
||||||
$.rm br if (br = abbr.previousSibling) and br.nodeName is 'BR'
|
|
||||||
$.rm abbr
|
|
||||||
|
|
||||||
cleanSpoilers: (bq) ->
|
cleanSpoilers: (bq) ->
|
||||||
spoilers = $$ 's', bq
|
spoilers = $$ Site.selectors.spoiler, bq
|
||||||
for node in spoilers
|
for node in spoilers
|
||||||
$.replace node, $.tn '[spoiler]'
|
$.replace node, $.tn '[spoiler]'
|
||||||
return
|
return
|
||||||
|
|
||||||
cleanCommentDisplay: (bq) ->
|
|
||||||
$.rm b if (b = $ 'b', bq) and /^Rolled /.test(b.textContent)
|
|
||||||
$.rm $('.fortune', bq)
|
|
||||||
|
|
||||||
parseQuotes: ->
|
parseQuotes: ->
|
||||||
@quotes = []
|
@quotes = []
|
||||||
# XXX https://github.com/4chan/4chan-JS/issues/77
|
for quotelink in $$ Site.selectors.quotelink, @nodes.comment
|
||||||
# 4chan currently creates quote links inside [code] tags; ignore them
|
|
||||||
for quotelink in $$ ':not(pre) > .quotelink', @nodes.comment
|
|
||||||
@parseQuote quotelink
|
@parseQuote quotelink
|
||||||
return
|
return
|
||||||
|
|
||||||
@ -165,13 +143,7 @@ class Post
|
|||||||
# - catalog links. (>>>/b/catalog or >>>/b/search)
|
# - catalog links. (>>>/b/catalog or >>>/b/search)
|
||||||
# - rules links. (>>>/a/rules)
|
# - rules links. (>>>/a/rules)
|
||||||
# - text-board quotelinks. (>>>/img/1234)
|
# - text-board quotelinks. (>>>/img/1234)
|
||||||
match = quotelink.href.match ///
|
match = quotelink.href.match Site.regexp.quotelink
|
||||||
^https?://boards\.4chan\.org/+
|
|
||||||
([^/]+) # boardID
|
|
||||||
/+(?:res|thread)/+\d+(?:[/?][^#]*)?#p
|
|
||||||
(\d+) # postID
|
|
||||||
$
|
|
||||||
///
|
|
||||||
return unless match or (@isClone and quotelink.dataset.postID) # normal or resurrected quote
|
return unless match or (@isClone and quotelink.dataset.postID) # normal or resurrected quote
|
||||||
|
|
||||||
@nodes.quotelinks.push quotelink
|
@nodes.quotelinks.push quotelink
|
||||||
@ -183,32 +155,24 @@ class Post
|
|||||||
@quotes.push fullID unless fullID in @quotes
|
@quotes.push fullID unless fullID in @quotes
|
||||||
|
|
||||||
parseFile: ->
|
parseFile: ->
|
||||||
{fileRoot} = @nodes
|
file = {}
|
||||||
return unless fileRoot
|
for key, selector of Site.selectors.file
|
||||||
return if not (link = $ '.fileText > a, .fileText-original > a', fileRoot)
|
file[key] = $ selector, @nodes.root
|
||||||
return if not (info = link.nextSibling?.textContent.match /\(([\d.]+ [KMG]?B).*\)/)
|
file.thumbLink = file.thumb?.parentNode
|
||||||
fileText = fileRoot.firstElementChild
|
|
||||||
@file =
|
return if not (file.text and file.link)
|
||||||
text: fileText
|
return if not Site.parseFile @, file
|
||||||
link: link
|
|
||||||
url: link.href
|
$.extend file,
|
||||||
name: fileText.title or link.title or link.textContent
|
url: file.link.href
|
||||||
size: info[1]
|
isImage: /(jpg|png|gif)$/i.test file.link.href
|
||||||
isImage: /(jpg|png|gif)$/i.test link.href
|
isVideo: /(webm|mp4)$/i.test file.link.href
|
||||||
isVideo: /webm$/i.test link.href
|
size = +file.size.match(/[\d.]+/)[0]
|
||||||
dimensions: info[0].match(/\d+x\d+/)?[0]
|
unit = ['B', 'KB', 'MB', 'GB'].indexOf file.size.match(/\w+$/)[0]
|
||||||
tag: info[0].match(/,[^,]*, ([a-z]+)\)/i)?[1]
|
|
||||||
size = +@file.size.match(/[\d.]+/)[0]
|
|
||||||
unit = ['B', 'KB', 'MB', 'GB'].indexOf @file.size.match(/\w+$/)[0]
|
|
||||||
size *= 1024 while unit-- > 0
|
size *= 1024 while unit-- > 0
|
||||||
@file.sizeInBytes = size
|
file.sizeInBytes = size
|
||||||
if (thumb = $ 'a.fileThumb > [data-md5]', fileRoot)
|
|
||||||
$.extend @file,
|
@file = file
|
||||||
thumb: thumb
|
|
||||||
thumbLink: thumb.parentNode
|
|
||||||
thumbURL: if m = link.href.match(/\d+(?=\.\w+$)/) then "#{location.protocol}//i.4cdn.org/#{@board}/#{m[0]}s.jpg"
|
|
||||||
MD5: thumb.dataset.md5
|
|
||||||
isSpoiler: $.hasClass thumb.parentNode, 'imgspoiler'
|
|
||||||
|
|
||||||
@deadMark =
|
@deadMark =
|
||||||
# \u00A0 is nbsp
|
# \u00A0 is nbsp
|
||||||
|
|||||||
@ -274,15 +274,18 @@ Main =
|
|||||||
$.event '4chanXInitFinished'
|
$.event '4chanXInitFinished'
|
||||||
|
|
||||||
initThread: ->
|
initThread: ->
|
||||||
if (board = $ '.board')
|
s = Site.selectors
|
||||||
|
if (board = $ s.board)
|
||||||
threads = []
|
threads = []
|
||||||
posts = []
|
posts = []
|
||||||
|
|
||||||
for threadRoot in $$ '.board > .thread', board
|
for threadRoot in $$(s.thread, board)
|
||||||
thread = new Thread +threadRoot.id[1..], g.BOARD
|
thread = new Thread +threadRoot.id.match(/\d*$/)[0], g.BOARD
|
||||||
thread.nodes.root = threadRoot
|
thread.nodes.root = threadRoot
|
||||||
threads.push thread
|
threads.push thread
|
||||||
for postRoot in $$('.thread > .postContainer', threadRoot) when $('.postMessage', postRoot)
|
postRoots = $$ s.postContainer, threadRoot
|
||||||
|
postRoots.unshift threadRoot if Site.isOPContainerThread
|
||||||
|
for postRoot in postRoots when $(s.comment, postRoot)
|
||||||
try
|
try
|
||||||
posts.push new Post postRoot, thread, g.BOARD
|
posts.push new Post postRoot, thread, g.BOARD
|
||||||
catch err
|
catch err
|
||||||
@ -295,17 +298,7 @@ Main =
|
|||||||
Main.handleErrors errors if errors
|
Main.handleErrors errors if errors
|
||||||
|
|
||||||
if g.VIEW is 'thread'
|
if g.VIEW is 'thread'
|
||||||
scriptData = Get.scriptData()
|
Site.parseThreadMetadata?(threads[0])
|
||||||
threads[0].postLimit = /\bbumplimit *= *1\b/.test scriptData
|
|
||||||
threads[0].fileLimit = /\bimagelimit *= *1\b/.test scriptData
|
|
||||||
threads[0].ipCount = if m = scriptData.match /\bunique_ips *= *(\d+)\b/ then +m[1]
|
|
||||||
|
|
||||||
if g.BOARD.ID is 'f' and g.VIEW is 'thread'
|
|
||||||
$.ajax "//a.4cdn.org/f/thread/#{g.THREADID}.json",
|
|
||||||
timeout: $.MINUTE
|
|
||||||
onloadend: ->
|
|
||||||
if @response and posts[0].file
|
|
||||||
posts[0].file.text.dataset.md5 = posts[0].file.MD5 = @response.posts[0].md5
|
|
||||||
|
|
||||||
Main.callbackNodes 'Thread', threads
|
Main.callbackNodes 'Thread', threads
|
||||||
Main.callbackNodesDB 'Post', posts, ->
|
Main.callbackNodesDB 'Post', posts, ->
|
||||||
|
|||||||
@ -1 +1,68 @@
|
|||||||
SW.tinyboard = {}
|
SW.tinyboard =
|
||||||
|
isOPContainerThread: true
|
||||||
|
|
||||||
|
selectors:
|
||||||
|
board: 'form[name="postcontrols"]'
|
||||||
|
thread: 'div[id^="thread_"]'
|
||||||
|
postContainer: '.reply' # postContainer is thread for OP
|
||||||
|
infoRoot: '.intro'
|
||||||
|
info:
|
||||||
|
subject: '.subject'
|
||||||
|
name: '.name'
|
||||||
|
email: '.email'
|
||||||
|
tripcode: '.trip'
|
||||||
|
uniqueID: '.poster_id'
|
||||||
|
capcode: '.capcode'
|
||||||
|
flag: '.flag'
|
||||||
|
date: 'time'
|
||||||
|
nameBlock: 'label'
|
||||||
|
quote: 'a[href*="#q"]'
|
||||||
|
reply: 'a[href*="/res/"]:not([href*="#"])'
|
||||||
|
icons:
|
||||||
|
isSticky: '.fa-thumb-tack'
|
||||||
|
isClosed: '.fa-lock'
|
||||||
|
file:
|
||||||
|
text: '.fileinfo'
|
||||||
|
link: '.fileinfo > a'
|
||||||
|
thumb: 'a > .post-image'
|
||||||
|
comment: '.body'
|
||||||
|
spoiler: '.spoiler'
|
||||||
|
quotelink: 'a[onclick^="highlightReply("]'
|
||||||
|
|
||||||
|
regexp:
|
||||||
|
quotelink:
|
||||||
|
///
|
||||||
|
/
|
||||||
|
([^/]+) # boardID
|
||||||
|
/res/\d+\.html#
|
||||||
|
(\d+) # postID
|
||||||
|
$
|
||||||
|
///
|
||||||
|
|
||||||
|
parseNodes: (post, nodes) ->
|
||||||
|
# Add vichan's span.poster_id around the ID if not already present.
|
||||||
|
return if nodes.uniqueID
|
||||||
|
nodes.info.normalize()
|
||||||
|
{nextSibling} = nodes.nameBlock
|
||||||
|
if nextSibling.nodeType is 3 and (m = nextSibling.textContent.match /(\s*ID:\s*)(\S+)/)
|
||||||
|
nextSibling = nextSibling.splitText m[1].length
|
||||||
|
nextSibling.splitText m[2].length
|
||||||
|
nodes.uniqueID = uniqueID = $.el 'span', {className: 'poster_id'}
|
||||||
|
$.replace nextSibling, uniqueID
|
||||||
|
$.add uniqueID, nextSibling
|
||||||
|
|
||||||
|
parseFile: (post, file) ->
|
||||||
|
{text, link, thumb} = file
|
||||||
|
return false if text.parentNode isnt post.nodes.root # file belongs to a reply
|
||||||
|
return false if not (infoNode = $ '.unimportant', text)
|
||||||
|
return false if not (info = infoNode.textContent.match /\((Spoiler Image, )?([\d.]+ [KMG]?B).*\)/)
|
||||||
|
nameNode = $ '.postfilename', text
|
||||||
|
$.extend file,
|
||||||
|
name: if nameNode then (nameNode.title or nameNode.textContent) else link.pathname.match(/[^/]*$/)[0]
|
||||||
|
size: info[2]
|
||||||
|
dimensions: info[0].match(/\d+x\d+/)?[0]
|
||||||
|
if thumb
|
||||||
|
$.extend file,
|
||||||
|
thumbURL: if '/static/' in thumb.src then link.href else thumb.src
|
||||||
|
isSpoiler: !!info[1]
|
||||||
|
true
|
||||||
|
|||||||
@ -1,6 +1,96 @@
|
|||||||
SW.yotsuba =
|
SW.yotsuba =
|
||||||
|
isOPContainerThread: false
|
||||||
|
|
||||||
|
selectors:
|
||||||
|
board: '.board'
|
||||||
|
thread: '.thread'
|
||||||
|
postContainer: '.postContainer'
|
||||||
|
post: '.post'
|
||||||
|
infoRoot: '.postInfo'
|
||||||
|
info:
|
||||||
|
subject: '.subject'
|
||||||
|
name: '.name'
|
||||||
|
email: '.useremail'
|
||||||
|
tripcode: '.postertrip'
|
||||||
|
uniqueIDRoot: '.posteruid'
|
||||||
|
uniqueID: '.posteruid > .hand'
|
||||||
|
capcode: '.capcode.hand'
|
||||||
|
pass: '.n-pu'
|
||||||
|
flag: '.flag, .countryFlag'
|
||||||
|
date: '.dateTime'
|
||||||
|
nameBlock: '.nameBlock'
|
||||||
|
quote: '.postNum > a:nth-of-type(2)'
|
||||||
|
reply: '.replylink'
|
||||||
|
icons:
|
||||||
|
isSticky: '.stickyIcon'
|
||||||
|
isClosed: '.closedIcon'
|
||||||
|
isArchived: '.archivedIcon'
|
||||||
|
file:
|
||||||
|
text: '.file > :first-child'
|
||||||
|
link: '.fileText > a'
|
||||||
|
thumb: 'a.fileThumb > [data-md5]'
|
||||||
|
comment: '.postMessage'
|
||||||
|
spoiler: 's'
|
||||||
|
quotelink: ':not(pre) > .quotelink' # XXX https://github.com/4chan/4chan-JS/issues/77: 4chan currently creates quote links inside [code] tags; ignore them
|
||||||
|
|
||||||
|
regexp:
|
||||||
|
quotelink:
|
||||||
|
///
|
||||||
|
^https?://boards\.4chan\.org/+
|
||||||
|
([^/]+) # boardID
|
||||||
|
/+thread/+\d+(?:[/?][^#]*)?#p
|
||||||
|
(\d+) # postID
|
||||||
|
$
|
||||||
|
///
|
||||||
|
|
||||||
isThisPageLegit: ->
|
isThisPageLegit: ->
|
||||||
# not 404 error page or similar.
|
# not 404 error page or similar.
|
||||||
location.hostname is 'boards.4chan.org' and
|
location.hostname is 'boards.4chan.org' and
|
||||||
!$('link[href*="favicon-status.ico"]', d.head) and
|
!$('link[href*="favicon-status.ico"]', d.head) and
|
||||||
d.title not in ['4chan - Temporarily Offline', '4chan - Error', '504 Gateway Time-out']
|
d.title not in ['4chan - Temporarily Offline', '4chan - Error', '504 Gateway Time-out']
|
||||||
|
|
||||||
|
scriptData: ->
|
||||||
|
for script in $$ 'script:not([src])', d.head
|
||||||
|
return script.textContent if /\bcooldowns *=/.test script.textContent
|
||||||
|
''
|
||||||
|
|
||||||
|
parseThreadMetadata: (thread) ->
|
||||||
|
scriptData = @scriptData()
|
||||||
|
thread.postLimit = /\bbumplimit *= *1\b/.test scriptData
|
||||||
|
thread.fileLimit = /\bimagelimit *= *1\b/.test scriptData
|
||||||
|
thread.ipCount = if (m = scriptData.match /\bunique_ips *= *(\d+)\b/) then +m[1]
|
||||||
|
|
||||||
|
if g.BOARD.ID is 'f' and thread.OP.file
|
||||||
|
{file} = thread.OP
|
||||||
|
$.ajax "//a.4cdn.org/f/thread/#{thread}.json",
|
||||||
|
timeout: $.MINUTE
|
||||||
|
onloadend: ->
|
||||||
|
if @response
|
||||||
|
file.text.dataset.md5 = file.MD5 = @response.posts[0].md5
|
||||||
|
|
||||||
|
parseFile: (post, file) ->
|
||||||
|
{text, link, thumb} = file
|
||||||
|
return false if not (info = link.nextSibling?.textContent.match /\(([\d.]+ [KMG]?B).*\)/)
|
||||||
|
$.extend file,
|
||||||
|
name: text.title or link.title or link.textContent
|
||||||
|
size: info[1]
|
||||||
|
dimensions: info[0].match(/\d+x\d+/)?[0]
|
||||||
|
tag: info[0].match(/,[^,]*, ([a-z]+)\)/i)?[1]
|
||||||
|
if thumb
|
||||||
|
$.extend file,
|
||||||
|
thumbURL: if (m = link.href.match /\d+(?=\.\w+$)/) then "#{location.protocol}//i.4cdn.org/#{post.board}/#{m[0]}s.jpg"
|
||||||
|
MD5: thumb.dataset.md5
|
||||||
|
isSpoiler: $.hasClass thumb.parentNode, 'imgspoiler'
|
||||||
|
true
|
||||||
|
|
||||||
|
cleanComment: (bq) ->
|
||||||
|
if (abbr = $ '.abbr', bq) # 'Comment too long' or 'EXIF data available'
|
||||||
|
for node in $$ '.abbr + br, .exif', bq
|
||||||
|
$.rm node
|
||||||
|
for i in [0...2]
|
||||||
|
$.rm br if (br = abbr.previousSibling) and br.nodeName is 'BR'
|
||||||
|
$.rm abbr
|
||||||
|
|
||||||
|
cleanCommentDisplay: (bq) ->
|
||||||
|
$.rm b if (b = $ 'b', bq) and /^Rolled /.test(b.textContent)
|
||||||
|
$.rm $('.fortune', bq)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user