diff --git a/multisrc/overrides/madara/martialscans/src/MartialScans.kt b/multisrc/overrides/madara/martialscans/src/MartialScans.kt
deleted file mode 100644
index 7bd1b121b..000000000
--- a/multisrc/overrides/madara/martialscans/src/MartialScans.kt
+++ /dev/null
@@ -1,26 +0,0 @@
-package eu.kanade.tachiyomi.extension.en.martialscans
-
-import eu.kanade.tachiyomi.multisrc.madara.Madara
-import eu.kanade.tachiyomi.source.model.SManga
-import org.jsoup.nodes.Element
-
-class MartialScans : Madara("Martial Scans", "https://martialscans.com", "en") {
- override fun popularMangaFromElement(element: Element): SManga {
- val manga = SManga.create()
-
- with(element) {
- select(popularMangaUrlSelector).last()?.let {
- manga.setUrlWithoutDomain(it.attr("href"))
- manga.title = it.ownText()
- }
-
- select("img").last()?.let {
- manga.thumbnail_url = imageFromElement(it)
- }
- }
-
- return manga
- }
-
- override fun searchMangaFromElement(element: Element): SManga = popularMangaFromElement(element)
-}
diff --git a/multisrc/src/main/java/eu/kanade/tachiyomi/multisrc/madara/MadaraGenerator.kt b/multisrc/src/main/java/eu/kanade/tachiyomi/multisrc/madara/MadaraGenerator.kt
index 5a35f2e81..902192dbd 100644
--- a/multisrc/src/main/java/eu/kanade/tachiyomi/multisrc/madara/MadaraGenerator.kt
+++ b/multisrc/src/main/java/eu/kanade/tachiyomi/multisrc/madara/MadaraGenerator.kt
@@ -157,7 +157,6 @@ class MadaraGenerator : ThemeSourceGenerator {
SingleLang("ManyToonClub", "https://manytoon.club", "ko"),
SingleLang("ManyToon.me", "https://manytoon.me", "en", className = "ManyToonMe"),
SingleLang("Mark Scans", "https://markscans.online", "pt-BR"),
- SingleLang("Martial Scans", "https://martialscans.com", "en"),
SingleLang("MG Komik", "https://mgkomik.my.id", "id"),
SingleLang("Milftoon", "https://milftoon.xxx", "en", isNsfw = true, overrideVersionCode = 1),
SingleLang("Miracle Scans", "https://miraclescans.com", "en"),
diff --git a/src/en/martialscans/AndroidManifest.xml b/src/en/martialscans/AndroidManifest.xml
new file mode 100644
index 000000000..30deb7f79
--- /dev/null
+++ b/src/en/martialscans/AndroidManifest.xml
@@ -0,0 +1,2 @@
+
+
diff --git a/src/en/martialscans/build.gradle b/src/en/martialscans/build.gradle
new file mode 100644
index 000000000..3cb9518ff
--- /dev/null
+++ b/src/en/martialscans/build.gradle
@@ -0,0 +1,12 @@
+apply plugin: 'com.android.application'
+apply plugin: 'kotlin-android'
+
+ext {
+ extName = 'MartialScans'
+ pkgNameSuffix = 'en.martialscans'
+ extClass = '.MartialScans'
+ extVersionCode = 2
+ libVersion = '1.2'
+}
+
+apply from: "$rootDir/common.gradle"
diff --git a/src/en/martialscans/res/mipmap-hdpi/ic_launcher.png b/src/en/martialscans/res/mipmap-hdpi/ic_launcher.png
new file mode 100644
index 000000000..82b577d64
Binary files /dev/null and b/src/en/martialscans/res/mipmap-hdpi/ic_launcher.png differ
diff --git a/src/en/martialscans/res/mipmap-mdpi/ic_launcher.png b/src/en/martialscans/res/mipmap-mdpi/ic_launcher.png
new file mode 100644
index 000000000..df728a9fd
Binary files /dev/null and b/src/en/martialscans/res/mipmap-mdpi/ic_launcher.png differ
diff --git a/src/en/martialscans/res/mipmap-xhdpi/ic_launcher.png b/src/en/martialscans/res/mipmap-xhdpi/ic_launcher.png
new file mode 100644
index 000000000..65eb2d6b8
Binary files /dev/null and b/src/en/martialscans/res/mipmap-xhdpi/ic_launcher.png differ
diff --git a/src/en/martialscans/res/mipmap-xxhdpi/ic_launcher.png b/src/en/martialscans/res/mipmap-xxhdpi/ic_launcher.png
new file mode 100644
index 000000000..7b750c6ac
Binary files /dev/null and b/src/en/martialscans/res/mipmap-xxhdpi/ic_launcher.png differ
diff --git a/src/en/martialscans/res/mipmap-xxxhdpi/ic_launcher.png b/src/en/martialscans/res/mipmap-xxxhdpi/ic_launcher.png
new file mode 100644
index 000000000..2b1dd0d91
Binary files /dev/null and b/src/en/martialscans/res/mipmap-xxxhdpi/ic_launcher.png differ
diff --git a/src/en/martialscans/res/web_hi_res_512.png b/src/en/martialscans/res/web_hi_res_512.png
new file mode 100644
index 000000000..4e50381e2
Binary files /dev/null and b/src/en/martialscans/res/web_hi_res_512.png differ
diff --git a/src/en/martialscans/src/eu/kanade/tachiyomi/extension/en/martialscans/MartialScans.kt b/src/en/martialscans/src/eu/kanade/tachiyomi/extension/en/martialscans/MartialScans.kt
new file mode 100644
index 000000000..293c5a4f8
--- /dev/null
+++ b/src/en/martialscans/src/eu/kanade/tachiyomi/extension/en/martialscans/MartialScans.kt
@@ -0,0 +1,107 @@
+package eu.kanade.tachiyomi.extension.en.martialscans
+
+import eu.kanade.tachiyomi.network.GET
+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 okhttp3.Headers
+import okhttp3.OkHttpClient
+import okhttp3.Request
+import org.jsoup.nodes.Document
+import org.jsoup.nodes.Element
+
+class MartialScans : ParsedHttpSource() {
+
+ override val name = "MartialScans"
+
+ override val baseUrl = "https://martialscans.com"
+
+ override val lang = "en"
+
+ override val supportsLatest = true
+
+ override val client: OkHttpClient = network.cloudflareClient
+
+ override fun headersBuilder(): Headers.Builder = Headers.Builder()
+ .add("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:86.0) Gecko/20100101 Firefox/86.0")
+
+ // popular
+ override fun popularMangaRequest(page: Int) = GET("$baseUrl/comics", headers)
+
+ override fun popularMangaSelector() = "div.latestCards .row div"
+
+ override fun popularMangaFromElement(element: Element): SManga {
+ val manga = SManga.create()
+ manga.url = element.select("a").attr("abs:href").substringAfter(baseUrl)
+ manga.title = element.select("h2").text()
+ // to do
+// manga.thumbnail_url = element.select("img.card-img").attr("abs:src")
+ return manga
+ }
+
+ override fun popularMangaNextPageSelector(): String? = null
+
+ // latest
+ override fun latestUpdatesRequest(page: Int): Request = popularMangaRequest(page)
+
+ override fun latestUpdatesSelector() = popularMangaSelector()
+
+ override fun latestUpdatesFromElement(element: Element) = popularMangaFromElement(element)
+
+ override fun latestUpdatesNextPageSelector(): String? = null
+
+ // search
+ override fun searchMangaRequest(page: Int, query: String, filters: FilterList): Request = throw Exception("Not used")
+
+ override fun searchMangaSelector(): String = throw Exception("Not used")
+
+ override fun searchMangaFromElement(element: Element): SManga = throw Exception("Not used")
+
+ override fun searchMangaNextPageSelector(): String? = throw Exception("Not used")
+
+ // manga details
+ override fun mangaDetailsParse(document: Document) = SManga.create().apply {
+ thumbnail_url = document.select(".cover + div.center img").attr("abs:src")
+ title = document.select("h1").text()
+ author = document.select("h5:contains(Author) span").text()
+ artist = document.select("h5:contains(Artist) span").text()
+ // to do
+// status = parseStatus(document.select("").text())
+ description = document.select("p:contains(Description)").firstOrNull()?.ownText()
+ genre = document.select("p:contains(Tags) span").joinToString { it.text() }
+ }
+
+ private fun parseStatus(status: String?) = when {
+ status == null -> SManga.UNKNOWN
+ status.contains("ongoing", true) -> SManga.ONGOING
+ status.contains("completed", true) -> SManga.COMPLETED
+ else -> SManga.UNKNOWN
+ }
+
+ // chapters
+ override fun chapterListSelector() = ".row div.col-xl-9.col-lg-12.col-md-12.col-sm-12.col-12 div:has(> a)"
+
+ override fun chapterFromElement(element: Element): SChapter {
+ val urlElement = element.select("a").first()
+ val chapter = SChapter.create()
+ chapter.setUrlWithoutDomain(urlElement.attr("href"))
+ chapter.name = element.select("h6").text()
+ // to do
+// chapter.date_upload = element.select("").firstOrNull()?.text()?.let { parseChapterDate(it) } ?: 0
+
+ return chapter
+ }
+
+ // pages
+ override fun pageListParse(document: Document): List {
+ return document.select(
+ ".block.center:has(img) img"
+ ).mapIndexed { i, element ->
+ Page(i, "", element.attr("abs:src"))
+ }
+ }
+
+ override fun imageUrlParse(document: Document): String = throw UnsupportedOperationException("Not Used")
+}