Greasy Fork

Greasy Fork is available in English.

我的文字修仙全靠刷之随身老爷爷

2024/7/31 10:36:02

当前为 2024-08-05 提交的版本,查看 最新版本

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴Greasemonkey 油猴子Violentmonkey 暴力猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴Violentmonkey 暴力猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴Userscripts ,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey 篡改猴,才能安装此脚本。

您需要先安装一款用户脚本管理器扩展后才能安装此脚本。

(我已经安装了用户脚本管理器,让我安装!)

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

(我已经安装了用户样式管理器,让我安装!)

// ==UserScript==
// @name        我的文字修仙全靠刷之随身老爷爷
// @namespace   Violentmonkey Scripts
// @match       https://xiuxian.jntm.cool/
// @grant       none
// @version     1.1
// @author      -
// @description 2024/7/31 10:36:02
// @license MIT
// ==/UserScript==
(function () {
  'use strict';

  class Interval {
    constructor(fun, speed) {
      this.fun = fun
      this.speed = speed
      this.id = null
      this.runing = false
    }

    start () {
      console.log('start')
      if (this.id) {
        return
      }
      this.runing = true
      this.id = setInterval(this.fun, this.speed)
    }

    stop () {
      console.log('Interval.stop()')
      if (this.id) {
        this.runing = false
        clearInterval(this.id)
        console.log(`Interval.stop() : clearInterval(${this.id})`)
        this.id = null
      }
    }
  }

  class LinkInterval extends Interval {
    constructor(linkList, speed, one = true, startClickButtonList = [], endClickButtonList = []) {
      super(null, speed)
      this._run = this._run.bind(this)
      super.fun = this._run

      this.startClickButtonList = startClickButtonList
      this.startClickButtonListLength = startClickButtonList.length
      this.startClickButtonListIndex = 0

      this.endClickButtonList = endClickButtonList
      this.endClickButtonListLength = endClickButtonList.length
      this.endClickButtonListIndex = 0

      this.linkList = linkList
      this.linkListLength = linkList.length

      this.one = one
      this.linkListIndex = 0
      this.next = null
      this._handleAfter = () => { }

      this.excNext = true

    }

    setHandleAfter (fun) {
      this._handleAfter = fun
      this._handleAfter = this._handleAfter.bind(this)
    }

    start (excNext = true) {
      this.excNext = excNext
      this.startClickButtonListIndex = 0
      this.endClickButtonListIndex = 0
      this.linkListIndex = 0
      super.start()
    }

    stop () {
      console.log('LinkInterval.stop()')
      if (this.endClickButtonListIndex < this.endClickButtonListLength) {
        this.runing = false
        return
      }
      super.stop()
      if (this.next && this.next.runing) {
        this.next.stop()
      }
    }

    linkNext (next) {
      this.next = next
      return this
    }

    nextInterval () {
      console.log(`执行下一定时器${this.next}`)
      this.stop()
      if (!super.runing && this.next) {
        this.next.start()
      }
    }

    _run () {
      if (!this.runing && this.endClickButtonListIndex >= this.endClickButtonListLength) {
        super.stop()
        return
      }
      let item = null, curIndex = 0
      if (this.startClickButtonListIndex < this.startClickButtonListLength) {
        item = this.startClickButtonList[this.startClickButtonListIndex++]
      } else if (!this.runing && this.endClickButtonListIndex < this.endClickButtonListLength) {
        item = this.endClickButtonList[this.endClickButtonListIndex++]
      } else {
        curIndex = (this.linkListIndex++) % this.linkListLength
        console.log(`当前次数:${this.linkListIndex}`)
        item = this.linkList[curIndex]
      }
      let cbs = findClickButton(item)
      if (cbs) {
        for (const cb of cbs) {
          console.log(`[${item}]元素点击。`)
          cb.click()
        }
      } else {
        console.warn(`未找到[${item}]元素。`)
      }
      this._handleAfter(this, this.linkListLength, this.linkListIndex)
      if (this.one == true && curIndex === (this.linkListLength - 1)) {
        if (this.excNext) {
          this.nextInterval()
        } else {
          this.stop()
          this.excNext = true
        }
      }
    }
  }
  let speed = 50
  let sellFrequency = 256

  const cultivateInterval = new LinkInterval(
    [
      'it>开始修炼',
      'it>继续修炼',
      'it>突破境界'
    ],
    speed,
    false
  )
  const autoInterval = new LinkInterval(
    [
      'it>探索秘境',
      'it>发起战斗',
      'it>继续探索'
    ],
    speed,
    false
  )
  const sellInterval = new LinkInterval(
    [
      'it>出售装备',
      'body > div.game-container-wrapper > div.game-container > div.index > div:nth-child(7) > div > div.el-dialog__body > div.dialog-footer > button',
      'body > div.game-container-wrapper > div.game-container > div.index > div:nth-child(7) > div > div.el-dialog__header > button'
    ],
    200,
    true,
    ['it>立马撤退', 'it>发起战斗', 'it>回家疗伤']
  )
  const petInterval = new LinkInterval(
    [
      'it>探索秘境',
      'it>收服对方',
      'it>发起战斗',
      'it>继续探索'
    ],
    speed,
    false
  )

  autoInterval.linkNext(sellInterval)
  petInterval.linkNext(sellInterval)


  function handleAfter (_this, linkListLength, linkListIndex) {
    if (sellFrequency <= 0) {
      return
    }
    if (linkListIndex % (linkListLength * sellFrequency) === 0) {
      _this.nextInterval()
    }
  }
  autoInterval.setHandleAfter(handleAfter)
  petInterval.setHandleAfter(handleAfter)

  class GroupLinkInterval {
    constructor(speed) {
      this.map = {}
      this.clickButtonList = [
        'it>点击炼器',
        'it>确定以及肯定'
      ]
      this.endClickButtonList = ['#el-drawer__title > button']
      this.frequency = 64
      this.speed = speed
    }

    add (key, startClickButtonList = []) {
      let interval = new LinkInterval(this.clickButtonList, this.speed, false, startClickButtonList, this.endClickButtonList)
      interval.setHandleAfter((linkListLength, linkListIndex) => {
        if (linkListIndex != 0 && linkListIndex % (linkListLength * this.frequency) == 0) {
          this.map[key].stop()
          unDisabled()
        }
      })
      this.map[key] = interval
    }

    start (key) {
      this.map[key].start()
    }

    setSpeed (speed) {
      this.speed = speed
      for (const key in this.map) {
        this.map[key].speed = this.speed
      }
    }
  }

  setTimeout(() => {
    let groupLinkInterval = new GroupLinkInterval(speed)
    let divBox = document.createElement('div')
    divBox.style = 'margin-bottom: 8px; padding-top: 16px;'
    const note = document.createElement('span')
    note.innerHTML = `<p style='margin: 2px 0; color: #ba0e0e;'>出售设置:使用前请先将出售的品级提前设置好,不自动出售将出售频率设置为0。</p>
                      <p style='margin: 2px 0; color: #ba0e0e;'>升级设置:提前勾选需要的设置,升级启动后无法停止只能刷新页面,请设置合适的升级次数。</p>
                      <p style='margin: 2px 0; color: #ba0e0e;'>如果启动后无效果请回到家里在重新启动。</p>`
    divBox.appendChild(note)
    addInput(divBox, '总速度', speed, (event) => {
      speed = Number(event.target.value)
      cultivateInterval.speed = speed
      autoInterval.speed = speed
      sellInterval.speed = speed
      petInterval.speed = speed
      groupLinkInterval.setSpeed(speed)
    })
    addInput(divBox, '出售频率', sellFrequency, (event) => {
      sellFrequency = Number(event.target.value)
    })
    addInput(divBox, '升级次数', groupLinkInterval.frequency, (event) => {
      groupLinkInterval.frequency = Number(event.target.value)
    })
    appendLine(divBox)
    // 修炼按钮
    const cultivateButtonText = ['开始修炼', '停止修炼']
    const cultivateButton = addButton(divBox, cultivateButtonText[0], ['el-button'], () => {
      if (cultivateButton.innerText === cultivateButtonText[0]) {
        disabled(cultivateButton)
        cultivateInterval.start()
        cultivateButton.innerText = cultivateButtonText[1]
        return
      }
      cultivateInterval.stop()
      cultivateButton.innerText = cultivateButtonText[0]
      unDisabled()
    })
    // 探索按钮
    const buttonText = ['开始探索', '停止探索']
    const autoButton = addButton(divBox, buttonText[0], ['el-button'], () => {
      if (autoButton.innerText === buttonText[0]) {
        disabled(autoButton)
        autoInterval.start()
        sellInterval.linkNext(autoInterval)
        autoButton.innerText = buttonText[1]
        return
      }
      autoInterval.stop()
      autoButton.innerText = buttonText[0]
      unDisabled()
    })
    // 抓宠按钮
    const petButtonText = ['开始抓宠', '停止抓宠']
    const petButton = addButton(divBox, petButtonText[0], ['el-button'], () => {
      if (petButton.innerText === petButtonText[0]) {
        disabled(petButton)
        petInterval.start()
        sellInterval.linkNext(petInterval)
        petButton.innerText = petButtonText[1]
        return
      }
      petInterval.stop()
      petButton.innerText = petButtonText[0]
      unDisabled()
    })
    // 出售按钮
    addButton(divBox, '快捷出售', ['el-button'], () => {
      sellInterval.start(false)
    })
    //appendLine(divBox)
    let groupButtonList = [
      {
        key: '升级神兵',
        rule: [
          'body > div > div.game-container > div.index > div.index-box > div.equip-box > div:nth-child(2) > span:nth-child(1) > span.el-tag.el-tag--danger.el-tag--light'
        ]
      },
      {
        key: '升级护甲',
        rule: [
          'body > div > div.game-container > div.index > div.index-box > div.equip-box > div:nth-child(2) > span:nth-child(2) > span.el-tag.el-tag--danger.el-tag--light'
        ]
      },
      {
        key: '升级灵宝',
        rule: [
          'body > div > div.game-container > div.index > div.index-box > div.equip-box > div:nth-child(3) > span:nth-child(1) > span.el-tag.el-tag--danger.el-tag--light'
        ]
      },
      {
        key: '升级法器',
        rule: [
          'body > div > div.game-container > div.index > div.index-box > div.equip-box > div:nth-child(3) > span:nth-child(2) > span.el-tag.el-tag--danger.el-tag--light'
        ]
      }
    ]
    for (const groupButton of groupButtonList) {
      groupLinkInterval.add(groupButton.key, groupButton.rule)
      addButton(divBox, groupButton.key, ['el-button'], (event) => {
        disabled(event.target)
        groupLinkInterval.start(groupButton.key)
      })
    }
    const gameBox = document.querySelector('.game-container')
    insertBefore(gameBox, divBox)
  }, 1000)

  function insertBefore (node, newElement) {
    node.insertBefore(newElement, node.firstChild)
  }

  function findClickButton (clickButton) {
    if (clickButton.startsWith('it>')) {
      clickButton = clickButton.replace('it>', '')
      let buttonList = document.querySelectorAll('.el-button')
      for (const node of buttonList) {
        if (node.innerText.replaceAll(' ', '') === clickButton) {
          return [node]
        }
      }
      return null
    }
    return document.querySelectorAll(clickButton)
  }

  function appendLine (divBox) {
    const p = document.createElement('p')
    p.style = 'margin: 2px 0'
    divBox.appendChild(p)
  }

  const buttonList = []
  function addButton (box, name, classNames, onClick) {
    let button = document.createElement("button")
    button.style = 'margin-left: 4px; padding: 10px 10px; margin-top: 6px;'
    button.classList.add(classNames)
    button.innerText = name
    button.addEventListener('click', onClick)
    box.appendChild(button)
    buttonList.push(button)
    return button
  }

  function disabled (button) {
    for (const item of buttonList) {
      item.disabled = true;
      item.style.cursor = "not-allowed"
    }
    button.disabled = false;
    button.style.cursor = "pointer"
  }

  function unDisabled () {
    for (const item of buttonList) {
      item.disabled = false;
      item.style.cursor = "pointer"
    }
  }

  function addInput (box, name, val, onInput) {
    let span = document.createElement("span")
    span.style = 'margin-left: 4px; margin-right: 4px; margin-top: 6px;'
    span.innerHTML = name
    let input = document.createElement("input")
    input.style = 'height: 21px; width: 8%; text-align: center; margin-top: 6px;'
    input.value = val
    input.addEventListener('input', onInput)
    box.appendChild(span)
    box.appendChild(input)
    return input
  }
})();