diff --git a/src/en/mangajar/build.gradle b/src/en/mangajar/build.gradle deleted file mode 100644 index b33024a82..000000000 --- a/src/en/mangajar/build.gradle +++ /dev/null @@ -1,8 +0,0 @@ -ext { - extName = 'MangaJar' - extClass = '.MangaJar' - extVersionCode = 9 - isNsfw = true -} - -apply from: "$rootDir/common.gradle" diff --git a/src/en/mangajar/res/mipmap-hdpi/ic_launcher.png b/src/en/mangajar/res/mipmap-hdpi/ic_launcher.png deleted file mode 100644 index e4347dfd3..000000000 Binary files a/src/en/mangajar/res/mipmap-hdpi/ic_launcher.png and /dev/null differ diff --git a/src/en/mangajar/res/mipmap-mdpi/ic_launcher.png b/src/en/mangajar/res/mipmap-mdpi/ic_launcher.png deleted file mode 100644 index d3b152730..000000000 Binary files a/src/en/mangajar/res/mipmap-mdpi/ic_launcher.png and /dev/null differ diff --git a/src/en/mangajar/res/mipmap-xhdpi/ic_launcher.png b/src/en/mangajar/res/mipmap-xhdpi/ic_launcher.png deleted file mode 100644 index de3f3ef87..000000000 Binary files a/src/en/mangajar/res/mipmap-xhdpi/ic_launcher.png and /dev/null differ diff --git a/src/en/mangajar/res/mipmap-xxhdpi/ic_launcher.png b/src/en/mangajar/res/mipmap-xxhdpi/ic_launcher.png deleted file mode 100644 index 23785eb1b..000000000 Binary files a/src/en/mangajar/res/mipmap-xxhdpi/ic_launcher.png and /dev/null differ diff --git a/src/en/mangajar/res/mipmap-xxxhdpi/ic_launcher.png b/src/en/mangajar/res/mipmap-xxxhdpi/ic_launcher.png deleted file mode 100644 index 365349fd7..000000000 Binary files a/src/en/mangajar/res/mipmap-xxxhdpi/ic_launcher.png and /dev/null differ diff --git a/src/en/mangajar/src/eu/kanade/tachiyomi/extension/en/mangajar/MangaJar.kt b/src/en/mangajar/src/eu/kanade/tachiyomi/extension/en/mangajar/MangaJar.kt deleted file mode 100644 index 361a9e06e..000000000 --- a/src/en/mangajar/src/eu/kanade/tachiyomi/extension/en/mangajar/MangaJar.kt +++ /dev/null @@ -1,275 +0,0 @@ -package eu.kanade.tachiyomi.extension.en.mangajar - -import eu.kanade.tachiyomi.network.GET -import eu.kanade.tachiyomi.network.asObservableSuccess -import eu.kanade.tachiyomi.source.model.Filter -import eu.kanade.tachiyomi.source.model.FilterList -import eu.kanade.tachiyomi.source.model.Page -import eu.kanade.tachiyomi.source.model.SChapter -import eu.kanade.tachiyomi.source.model.SManga -import eu.kanade.tachiyomi.source.online.ParsedHttpSource -import eu.kanade.tachiyomi.util.asJsoup -import okhttp3.HttpUrl.Companion.toHttpUrl -import okhttp3.OkHttpClient -import okhttp3.Request -import org.jsoup.nodes.Document -import org.jsoup.nodes.Element -import rx.Observable -import rx.Single -import java.text.SimpleDateFormat -import java.util.Calendar -import java.util.Locale - -class MangaJar : ParsedHttpSource() { - - override val name = "MangaJar" - - override val baseUrl = "https://mangajar.com" - - override val lang = "en" - - override val supportsLatest = true - - override val client: OkHttpClient = network.cloudflareClient - - // Popular - - override fun popularMangaRequest(page: Int): Request = GET("$baseUrl/manga?sortBy=popular&page=$page") - - override fun popularMangaSelector() = "article[class*=flex-item]" - - override fun popularMangaFromElement(element: Element) = SManga.create().apply { - setUrlWithoutDomain(element.select("a").attr("href")) - title = element.select("img").attr("title") - thumbnail_url = element.select("img").let { - if (it.hasAttr("data-src")) { - it.attr("data-src") - } else { - it.attr("src") - } - } - } - - override fun popularMangaNextPageSelector() = "a.page-link[rel=next]" - - // Latest - - override fun latestUpdatesRequest(page: Int): Request = GET("$baseUrl/manga?sortBy=-last_chapter_at&page=$page") - - override fun latestUpdatesSelector() = popularMangaSelector() - - override fun latestUpdatesFromElement(element: Element): SManga = popularMangaFromElement(element) - - override fun latestUpdatesNextPageSelector() = popularMangaNextPageSelector() - - // Search - - override fun searchMangaRequest(page: Int, query: String, filters: FilterList): Request { - val filterList = if (filters.isEmpty()) getFilterList() else filters - val genreFilter = filterList.findInstance() - val genre = genreFilter?.let { f -> f.values[f.state] } - - val url = (if (genre!!.isEmpty()) "$baseUrl/search" else "$baseUrl/genre/$genre").toHttpUrl().newBuilder() - - url.addQueryParameter("q", query) - url.addQueryParameter("page", page.toString()) - - for (filter in filterList) { - when (filter) { - is OrderBy -> { - url.addQueryParameter("sortBy", filter.toUriPart()) - } - is SortBy -> { - url.addQueryParameter("sortAscending", filter.toUriPart()) - } - else -> {} - } - } - return GET(url.build(), headers) - } - - override fun searchMangaSelector() = popularMangaSelector() - - override fun searchMangaFromElement(element: Element) = popularMangaFromElement(element) - - override fun searchMangaNextPageSelector() = popularMangaNextPageSelector() - - // Details - - override fun mangaDetailsParse(document: Document) = SManga.create().apply { - description = document.select("div.manga-description.entry").text() - thumbnail_url = document.select("div.row > div > img").attr("src") - genre = document.select("div.post-info > span > a[href*=genre]").joinToString { it.text() } - status = parseStatus(document.select("span:has(b)")[1].text()) - } - - private fun parseStatus(status: String) = when { - status.contains("Ongoing") -> SManga.ONGOING - status.contains("Ended") -> SManga.COMPLETED - else -> SManga.UNKNOWN - } - - // Chapters - - /** For the first page. Pagination is done in [findChapters] */ - override fun chapterListRequest(manga: SManga) = GET(baseUrl + manga.url + "/chaptersList") - - override fun fetchChapterList(manga: SManga): Observable> { - return findChapters(chapterListRequest(manga)).toObservable() - } - - private fun findChapters(request: Request): Single> { - return client.newCall(request).asObservableSuccess().toSingle().flatMap { response -> - val document = response.asJsoup() - val thisPage = document.select(chapterListSelector()).map { chapter -> - SChapter.create().apply { - val link = chapter.select("a") - url = link.attr("href") - name = link.text() - date_upload = parseChapterDate(chapter.select("span.chapter-date").text().trim()) - } - } - val nextPageLink = document.select("a.page-link[rel=\"next\"]").firstOrNull() - if (nextPageLink == null) { - Single.just(thisPage) - } else { - findChapters(GET("$baseUrl${nextPageLink.attr("href")}")).map { remainingChapters -> - thisPage + remainingChapters - } - } - } - } - - override fun chapterListSelector() = "li.list-group-item.chapter-item" - - override fun chapterFromElement(element: Element) = throw UnsupportedOperationException() - - private fun parseChapterDate(string: String): Long { - return if ("ago" in string) { - parseRelativeDate(string) - } else { - dateFormat.parse(string)?.time ?: 0L - } - } - - private fun parseRelativeDate(date: String): Long { - val trimmedDate = date.substringBefore(" ago").removeSuffix("s").split(" ") - - val calendar = Calendar.getInstance() - when (trimmedDate[1]) { - "month" -> calendar.apply { add(Calendar.MONTH, -trimmedDate[0].toInt()) } - "week" -> calendar.apply { add(Calendar.WEEK_OF_MONTH, -trimmedDate[0].toInt()) } - "day" -> calendar.apply { add(Calendar.DAY_OF_MONTH, -trimmedDate[0].toInt()) } - "hour" -> calendar.apply { add(Calendar.HOUR_OF_DAY, -trimmedDate[0].toInt()) } - "minute" -> calendar.apply { add(Calendar.MINUTE, -trimmedDate[0].toInt()) } - "second" -> calendar.apply { add(Calendar.SECOND, 0) } - } - - return calendar.timeInMillis - } - - // Page List - - override fun pageListParse(document: Document): List { - return document.select("img[data-page]").mapIndexed { i, element -> - Page(i, "", if (element.hasAttr("data-src")) element.attr("abs:data-src") else element.attr("abs:src")) - } - } - - override fun imageUrlParse(document: Document): String = throw UnsupportedOperationException() - - // Filters - - override fun getFilterList() = FilterList( - OrderBy(), - SortBy(), - GenreList(), - ) - - private class SortBy : UriPartFilter( - "Sort By", - arrayOf( - Pair("Descending", "0"), - Pair("Ascending", "1"), - ), - ) - - private class OrderBy : UriPartFilter( - "Order By", - arrayOf( - Pair("Popularity", "popular"), - Pair("Year", "year"), - Pair("Alphabet", "name"), - Pair("Date added", "published_at"), - Pair("Date updated", "last_chapter_at"), - ), - ) - - private class GenreList : Filter.Select( - "Select Genre", - arrayOf( - "", - "Fantasy", - "Adventure", - "Martial Arts", - "Action", - "Demons", - "Shounen", - "Drama", - "Isekai", - "School Life", - "Harem", - "Horror", - "Supernatural", - "Mystery", - "Sci-Fi", - "Webtoons", - "Romance", - "Magic", - "Slice of Life", - "Seinen", - "Historical", - "Ecchi", - "Comedy", - "Sports", - "Tragedy", - "Shounen Ai", - "Yaoi", - "Shoujo", - "Super Power", - "Food", - "Psychological", - "Gender Bender", - "Smut", - "Shoujo Ai", - "Yuri", - "4-koma", - "Mecha", - "Adult", - "Mature", - "Military", - "Vampire", - "Kids", - "Space", - "Police", - "Music", - "One Shot", - "Parody", - "Josei", - ), - ) - - private inline fun Iterable<*>.findInstance() = find { it is T } as? T - - private open class UriPartFilter(displayName: String, val vals: Array>) : - Filter.Select(displayName, vals.map { it.first }.toTypedArray()) { - fun toUriPart() = vals[state].second - } - - // The following date related code is taken directly from Genkan.kt - companion object { - val dateFormat by lazy { - SimpleDateFormat("dd MMM yyyy", Locale.ENGLISH) - } - } -}