From a68575757562bb6694c50ec82cfb9e1f8a92e7ce Mon Sep 17 00:00:00 2001 From: Mook Date: Fri, 20 Sep 2019 06:07:30 -0700 Subject: [PATCH] all/webtoons: Add additonal languages (#1510) * all/webtoons: Add additonal languages This adds more languages where webtoons has official comics: - Chinese (Traditional) - Indonesian - Thai Closes #1492 Note that Webtoons also has Chinese (Simplified) pages, but those go off into a separate host name, so we're not touching that for now. * all/webtoons: Fix build error One file was not checked in by accident. * all/webtoons: Bump extVersionCode --- src/all/webtoons/build.gradle | 2 +- .../extension/all/webtoons/Webtoons.kt | 13 ++++++------ .../extension/all/webtoons/WebtoonsDefault.kt | 10 +++++++--- .../extension/all/webtoons/WebtoonsFactory.kt | 10 ++++++++-- .../all/webtoons/WebtoonsTranslate.kt | 4 ++-- .../id/webtoons/WebtoonsIndonesian.kt | 20 +++++++++++++++++++ .../extension/th/webtoons/WebtoonsThai.kt | 11 ++++++++++ .../zh/webtoons/WebtoonsChineseTraditional.kt | 11 ++++++++++ 8 files changed, 67 insertions(+), 14 deletions(-) create mode 100644 src/all/webtoons/src/eu/kanade/tachiyomi/extension/id/webtoons/WebtoonsIndonesian.kt create mode 100644 src/all/webtoons/src/eu/kanade/tachiyomi/extension/th/webtoons/WebtoonsThai.kt create mode 100644 src/all/webtoons/src/eu/kanade/tachiyomi/extension/zh/webtoons/WebtoonsChineseTraditional.kt diff --git a/src/all/webtoons/build.gradle b/src/all/webtoons/build.gradle index 85c5bc15a..7e7d47bbc 100644 --- a/src/all/webtoons/build.gradle +++ b/src/all/webtoons/build.gradle @@ -5,7 +5,7 @@ ext { appName = 'Tachiyomi: Webtoons' pkgNameSuffix = 'all.webtoons' extClass = '.WebtoonsFactory' - extVersionCode = 7 + extVersionCode = 8 libVersion = '1.2' } diff --git a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/Webtoons.kt b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/Webtoons.kt index baf63662f..f2a98155d 100644 --- a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/Webtoons.kt +++ b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/Webtoons.kt @@ -11,7 +11,7 @@ import org.jsoup.nodes.Document import org.jsoup.nodes.Element import java.util.* -abstract class Webtoons(override val lang: String) : ParsedHttpSource() { +abstract class Webtoons(override val lang: String, open val langCode: String = lang) : ParsedHttpSource() { override val name = "Webtoons.com" @@ -40,21 +40,22 @@ abstract class Webtoons(override val lang: String) : ParsedHttpSource() { override fun latestUpdatesSelector() = "div#dailyList > $day li > a:has(span:contains(UP))" override fun headersBuilder() = super.headersBuilder() - .add("Referer", "http://www.webtoons.com/en/") + .add("Referer", "http://www.webtoons.com/$langCode/") protected val mobileHeaders = super.headersBuilder() .add("Referer", "http://m.webtoons.com") .build() - override fun popularMangaRequest(page: Int) = GET("$baseUrl/en/top", headers) + override fun popularMangaRequest(page: Int) = GET("$baseUrl/$langCode/top", headers) - override fun latestUpdatesRequest(page: Int) = GET("$baseUrl/en/dailySchedule?sortOrder=UPDATE&webtoonCompleteType=ONGOING", headers) + override fun latestUpdatesRequest(page: Int) = GET("$baseUrl/$langCode/dailySchedule?sortOrder=UPDATE&webtoonCompleteType=ONGOING", headers) private fun mangaFromElement(query: String, element: Element): SManga { val manga = SManga.create() element.select(query).first().let { manga.setUrlWithoutDomain(it.attr("href")) manga.title = it.select("p.subj").text() + manga.thumbnail_url = it.select(".pic_area > img")?.attr("src") } return manga } @@ -117,8 +118,8 @@ abstract class Webtoons(override val lang: String) : ParsedHttpSource() { val discoverPic = document.select("#content > div.cont_box > div.detail_header > span.thmb") val manga = SManga.create() - manga.author = detailElement.select(".author:nth-of-type(1)").text().substringBefore("author info") - manga.artist = detailElement.select(".author:nth-of-type(2)").first()?.text()?.substringBefore("author info") ?: manga.author + manga.author = detailElement.select(".author:nth-of-type(1)").first()?.ownText() + manga.artist = detailElement.select(".author:nth-of-type(2)").first()?.ownText() ?: manga.author manga.genre = detailElement.select(".genre").map { it.text() }.joinToString(", ") manga.description = infoElement.select("p.summary").text() manga.status = infoElement.select("p.day_info").text().orEmpty().let { parseStatus(it) } diff --git a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsDefault.kt b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsDefault.kt index 4510263c5..8d915f534 100644 --- a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsDefault.kt +++ b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsDefault.kt @@ -9,7 +9,7 @@ import org.jsoup.nodes.Element import java.text.SimpleDateFormat import java.util.* -open class WebtoonsDefault(override val lang: String) : Webtoons(lang) { +open class WebtoonsDefault(override val lang: String, override val langCode: String = lang) : Webtoons(lang, langCode) { override fun chapterListSelector() = "ul#_episodeList > li[id*=episode]" @@ -26,11 +26,15 @@ open class WebtoonsDefault(override val lang: String) : Webtoons(lang) { if (element.select(".ico_bgm").isNotEmpty()) { chapter.name += " ♫" } - chapter.date_upload = element.select("a > div.row > div.info > p.date").text()?.let { SimpleDateFormat("MMM d, yyyy", Locale.ENGLISH).parse(it).time } ?: 0 + chapter.date_upload = element.select("a > div.row > div.info > p.date").text()?.let { chapterParseDate(it) } ?: 0 return chapter } + open fun chapterParseDate(date: String): Long { + return SimpleDateFormat("MMM d, yyyy", Locale.ENGLISH).parse(date).time + } + override fun chapterListRequest(manga: SManga) = GET("http://m.webtoons.com" + manga.url, mobileHeaders) override fun pageListParse(document: Document) = document.select("div#_imageList > img").mapIndexed { i, element -> Page(i, "", element.attr("data-url")) } -} \ No newline at end of file +} diff --git a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsFactory.kt b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsFactory.kt index c77c03533..09a0c48e9 100644 --- a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsFactory.kt +++ b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsFactory.kt @@ -2,6 +2,9 @@ package eu.kanade.tachiyomi.extension.all.webtoons import eu.kanade.tachiyomi.extension.en.webtoons.WebtoonsEnglish import eu.kanade.tachiyomi.extension.fr.webtoons.WebtoonsFrench +import eu.kanade.tachiyomi.extension.id.webtoons.WebtoonsIndonesian +import eu.kanade.tachiyomi.extension.th.webtoons.WebtoonsThai +import eu.kanade.tachiyomi.extension.zh.webtoons.WebtoonsChineseTraditional import eu.kanade.tachiyomi.source.Source import eu.kanade.tachiyomi.source.SourceFactory @@ -12,6 +15,9 @@ class WebtoonsFactory : SourceFactory { fun getAllWebtoons(): List { return listOf( WebtoonsEnglish(), - WebtoonsFrench() + WebtoonsChineseTraditional(), + WebtoonsFrench(), + WebtoonsIndonesian(), + WebtoonsThai() ) -} \ No newline at end of file +} diff --git a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsTranslate.kt b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsTranslate.kt index 00ca26126..59bc3bd2f 100644 --- a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsTranslate.kt +++ b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/all/webtoons/WebtoonsTranslate.kt @@ -10,7 +10,7 @@ import org.jsoup.nodes.Document import org.jsoup.nodes.Element import java.util.* -open class WebtoonsTranslate(override val lang: String, private val langCode: String) : Webtoons(lang) { +open class WebtoonsTranslate(override val lang: String, private val translationLangCode: String) : Webtoons(lang) { private val apiBaseUrl = "https://global.apis.naver.com" @@ -29,7 +29,7 @@ open class WebtoonsTranslate(override val lang: String, private val langCode: St val titleRegex = Regex("title_?[nN]o=([0-9]*)") val titleNo = titleRegex.find(original)!!.groupValues[1].toInt() - val chapterUrl = String.format("$apiBaseUrl$chapterListUrlPattern", titleNo, langCode) + val chapterUrl = String.format("$apiBaseUrl$chapterListUrlPattern", titleNo, translationLangCode) return GET(chapterUrl, headers) } diff --git a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/id/webtoons/WebtoonsIndonesian.kt b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/id/webtoons/WebtoonsIndonesian.kt new file mode 100644 index 000000000..415334d31 --- /dev/null +++ b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/id/webtoons/WebtoonsIndonesian.kt @@ -0,0 +1,20 @@ +package eu.kanade.tachiyomi.extension.id.webtoons + +import eu.kanade.tachiyomi.extension.all.webtoons.WebtoonsDefault +import java.util.* + +class WebtoonsIndonesian: WebtoonsDefault("en", "id") { + override val name: String = "Webtoons.com (Indonesian)" + + // Android seems to be unable to parse Indonesian dates; we'll use a short hard-coded table + // instead. + private val DATE_MAP: Array = arrayOf( + "Jan", "Feb", "Mar", "Apr", "Mei", "Jun", "Jul", "Agu", "Sep", "Okt", "Nov", "Des") + + override fun chapterParseDate(date: String): Long { + val expr = Regex("""(\d{4}) ([A-Z][a-z]{2}) (\d{1,})""").find(date) ?: return 0 + val (_, year, monthString, day) = expr.groupValues + val monthIndex = DATE_MAP.indexOf(monthString) + return GregorianCalendar(year.toInt(), monthIndex, day.toInt()).time.time + } +} diff --git a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/th/webtoons/WebtoonsThai.kt b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/th/webtoons/WebtoonsThai.kt new file mode 100644 index 000000000..eeb3ce0f7 --- /dev/null +++ b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/th/webtoons/WebtoonsThai.kt @@ -0,0 +1,11 @@ +package eu.kanade.tachiyomi.extension.th.webtoons + +import eu.kanade.tachiyomi.extension.all.webtoons.WebtoonsDefault +import java.text.SimpleDateFormat +import java.util.* + +class WebtoonsThai: WebtoonsDefault("th") { + override fun chapterParseDate(date: String): Long { + return SimpleDateFormat("d MMM yyyy", Locale("th")).parse(date).time + } +} diff --git a/src/all/webtoons/src/eu/kanade/tachiyomi/extension/zh/webtoons/WebtoonsChineseTraditional.kt b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/zh/webtoons/WebtoonsChineseTraditional.kt new file mode 100644 index 000000000..36a4bdce3 --- /dev/null +++ b/src/all/webtoons/src/eu/kanade/tachiyomi/extension/zh/webtoons/WebtoonsChineseTraditional.kt @@ -0,0 +1,11 @@ +package eu.kanade.tachiyomi.extension.zh.webtoons + +import eu.kanade.tachiyomi.extension.all.webtoons.WebtoonsDefault +import java.text.SimpleDateFormat +import java.util.* + +class WebtoonsChineseTraditional: WebtoonsDefault("zh", "zh-hant") { + override fun chapterParseDate(date: String): Long { + return SimpleDateFormat("yyyy/MM/dd", Locale.TRADITIONAL_CHINESE).parse(date).time + } +}