diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml new file mode 100644 index 000000000..17af62cb1 --- /dev/null +++ b/.github/workflows/build.yml @@ -0,0 +1,106 @@ +name: Build + +on: [push, pull_request] + +jobs: + build: + runs-on: ubuntu-18.04 + steps: + - name: Install dependencies + run: | + sudo apt-get update + sudo apt-get install \ + libsdl-image1.2-dev \ + libsdl-ttf2.0-dev \ + libsdl1.2-dev \ + libxml-libxml-perl \ + libxml-libxslt-perl \ + lua5.3 \ + ninja-build \ + zlib1g-dev + sudo pip3 install --system sphinx + - name: Clone DFHack + uses: actions/checkout@v1 + with: + submodules: true + - name: Set up environment + run: | + echo export DF_VERSION="$(sh travis/get-df-version.sh)" >> "$HOME/.df-env" + echo export DF_FOLDER="$HOME/DF/$DF_VERSION/df_linux" >> "$HOME/.df-env" + - name: Download DF + run: | + source "$HOME/.df-env" + sh travis/download-df.sh + - name: Build docs + run: | + sphinx-build -qW -j3 . docs/html + - name: Upload docs + uses: actions/upload-artifact@v1 + with: + name: docs + path: docs/html + - name: Build DFHack + run: | + source "$HOME/.df-env" + cmake \ + -S . \ + -B build-ci \ + -G Ninja \ + -DDFHACK_BUILD_ARCH=64 \ + -DBUILD_DOCS:BOOL=ON \ + -DBUILD_TESTS:BOOL=ON \ + -DCMAKE_INSTALL_PREFIX="$DF_FOLDER" + ninja -C build-ci install + - name: Run tests + run: | + source "$HOME/.df-env" + export TERM=dumb + mv "$DF_FOLDER"/dfhack.init-example "$DF_FOLDER"/dfhack.init + script -qe -c "python travis/run-tests.py --headless --keep-status \"$DF_FOLDER\"" + python travis/check-rpc.py "$DF_FOLDER/dfhack-rpc.txt" + mkdir -p artifacts + cp "$DF_FOLDER/test_status.json" "$DF_FOLDER"/*.log artifacts + - name: Upload test artifacts + uses: actions/upload-artifact@v1 + if: success() || failure() + with: + name: test-artifacts + path: artifacts + lint: + runs-on: ubuntu-18.04 + steps: + - name: Install dependencies + run: | + sudo apt-get update + sudo apt-get install \ + lua5.3 \ + ruby + - name: Clone DFHack + uses: actions/checkout@v1 + with: + submodules: true + - name: Check whitespace + run: | + python travis/lint.py + - name: Check Authors.rst + run: | + python travis/authors-rst.py + - name: Check for missing documentation + run: | + python travis/script-docs.py + - name: Check Lua syntax + run: | + python travis/script-syntax.py --ext=lua --cmd="luac5.3 -p" + - name: Check Ruby syntax + run: | + python travis/script-syntax.py --ext=rb --cmd="ruby -c" + check-pr: + runs-on: ubuntu-latest + if: github.event_name == 'pull_request' + steps: + - name: Check that PR is based on develop branch + env: + BASE_BRANCH: ${{ github.base_ref }} + run: | + echo "PR base branch: $BASE_BRANCH" + test "$BASE_BRANCH" = develop diff --git a/.travis.yml b/.travis.yml deleted file mode 100644 index c096552bc..000000000 --- a/.travis.yml +++ /dev/null @@ -1,64 +0,0 @@ -sudo: false -language: cpp -cache: - pip: true - directories: - - $HOME/DF-travis - - $HOME/lua53 -addons: - apt: - packages: &default_packages - - libsdl-image1.2-dev - - libsdl-ttf2.0-dev - - libsdl1.2-dev - - libxml-libxml-perl - - libxml-libxslt-perl - - ninja-build - - zlib1g-dev -matrix: - include: - - env: GCC_VERSION=4.8 - addons: - apt: - sources: - - ubuntu-toolchain-r-test - packages: - - *default_packages - - gcc-4.8 - - g++-4.8 -before_install: -- export DF_VERSION=$(sh travis/get-df-version.sh) -- export DF_FOLDER="$HOME/DF-travis/$DF_VERSION/df_linux" -- pip install --user "sphinx==1.4" "requests[security]" -- sh travis/build-lua.sh -- sh travis/download-df.sh -script: -- export PATH="$PATH:$HOME/lua53/bin" -- git tag tmp-travis-build -- sh travis/git-info.sh -- sphinx-build -qW -j3 . docs/html -- python travis/pr-check-base.py -- python travis/lint.py -- python travis/authors-rst.py -- python travis/script-docs.py -- python travis/script-syntax.py --ext=lua --cmd="luac5.3 -p" -- python travis/script-syntax.py --ext=rb --cmd="ruby -c" -- mkdir build-travis -- cd build-travis -- cmake .. -G Ninja -DCMAKE_C_COMPILER=gcc-$GCC_VERSION -DCMAKE_CXX_COMPILER=g++-$GCC_VERSION -DDFHACK_BUILD_ARCH=64 -DBUILD_DOCS:BOOL=ON -DBUILD_TESTS:BOOL=ON -DCMAKE_INSTALL_PREFIX="$DF_FOLDER" -- ninja -j3 install -- mv "$DF_FOLDER"/dfhack.init-example "$DF_FOLDER"/dfhack.init -- cd .. -- python travis/run-tests.py --headless --keep-status "$DF_FOLDER" -- python travis/check-rpc.py "$DF_FOLDER/dfhack-rpc.txt" -- cat "$DF_FOLDER/test_status.json" -before_cache: -- cat "$DF_FOLDER/stderr.log" -- rm -rf "$DF_FOLDER" -notifications: - email: false - irc: - channels: - - "chat.freenode.net#dfhack" - on_success: change - on_failure: always diff --git a/README.md b/README.md index fd95e1e5e..a0499a333 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # DFHack Readme -[![Build Status](https://travis-ci.org/DFHack/dfhack.svg?branch=develop)](https://travis-ci.org/DFHack/dfhack) +[![Build Status](https://github.com/DFHack/dfhack/workflows/Build/badge.svg)](https://github.com/DFHack/dfhack/actions?query=workflow%3ABuild) [![Documentation Status](https://readthedocs.org/projects/dfhack/badge)](https://dfhack.readthedocs.org) [![License](https://img.shields.io/badge/license-ZLib-blue.svg)](https://en.wikipedia.org/wiki/Zlib_License) diff --git a/conf.py b/conf.py index bfd69d828..2f47d5644 100644 --- a/conf.py +++ b/conf.py @@ -174,7 +174,7 @@ def all_keybinds_documented(): plugin_binds = set(re.findall(':dfhack-keybind:`(.*?)`', f.read())) undocumented_binds = configured_binds - script_commands - plugin_binds if undocumented_binds: - raise ValueError('The following DFHack commands have undocumented' + raise ValueError('The following DFHack commands have undocumented ' 'keybindings: {}'.format(sorted(undocumented_binds))) diff --git a/docs/Authors.rst b/docs/Authors.rst index 1bfcf051b..72d61de06 100644 --- a/docs/Authors.rst +++ b/docs/Authors.rst @@ -34,6 +34,7 @@ Clayton Hughes Clément Vuchener cvuchener Dan Amlund danamlund Daniel Brooks db48x +David Nilsolm David Corbett dscorbett David Seguin dseguin David Timm dtimm diff --git a/docs/changelog.txt b/docs/changelog.txt index 34f5c3660..11734d9f7 100644 --- a/docs/changelog.txt +++ b/docs/changelog.txt @@ -40,8 +40,14 @@ changelog.txt uses a syntax similar to RST, with a few special sequences: # Future ## Fixes +- Fixed translation of certain types of in-game names +- `autogems`: fixed an issue with binned gems being ignored in linked stockpiles - `tweak` embark-profile-name: fixed handling of the native shift+space key +## Misc Improvements +- `manipulator`: added intrigue to displayed skills +- `search`: added support for the fortress mode justice screen + ## Lua - ``pairs()`` now returns available class methods for DF types diff --git a/library/modules/Translation.cpp b/library/modules/Translation.cpp index d836e6122..e05154b44 100644 --- a/library/modules/Translation.cpp +++ b/library/modules/Translation.cpp @@ -180,14 +180,11 @@ string Translation::TranslateName(const df::language_name * name, bool inEnglish word.append(*world->raws.language.translations[name->language]->words[name->words[1]]); addNameWord(out, word); } - if (name->words[5] >= 0) - { - word.clear(); - for (int i = 2; i <= 5; i++) - if (name->words[i] >= 0) - word.append(*world->raws.language.translations[name->language]->words[name->words[i]]); - addNameWord(out, word); - } + word.clear(); + for (int i = 2; i <= 5; i++) + if (name->words[i] >= 0) + word.append(*world->raws.language.translations[name->language]->words[name->words[i]]); + addNameWord(out, word); if (name->words[6] >= 0) { word.clear(); @@ -206,18 +203,17 @@ string Translation::TranslateName(const df::language_name * name, bool inEnglish word.append(world->raws.language.words[name->words[1]]->forms[name->parts_of_speech[1]]); addNameWord(out, word); } - if (name->words[5] >= 0) + if (name->words[2] >= 0 || name->words[3] >= 0 || name->words[4] >= 0 || name->words[5] >= 0) { if (out.length() > 0) out.append(" the"); else out.append("The"); - - for (int i = 2; i <= 5; i++) - { - if (name->words[i] >= 0) - addNameWord(out, world->raws.language.words[name->words[i]]->forms[name->parts_of_speech[i]]); - } + } + for (int i = 2; i <= 5; i++) + { + if (name->words[i] >= 0) + addNameWord(out, world->raws.language.words[name->words[i]]->forms[name->parts_of_speech[i]]); } if (name->words[6] >= 0) { diff --git a/library/xml b/library/xml index b585e182c..f185d0b22 160000 --- a/library/xml +++ b/library/xml @@ -1 +1 @@ -Subproject commit b585e182c404a14130d42bf87a60f94aebbfd1fd +Subproject commit f185d0b22acb1daf36b3a017f7a30b48994ee42c diff --git a/plugins/autogems.cpp b/plugins/autogems.cpp index 4121b562f..f22d20d30 100644 --- a/plugins/autogems.cpp +++ b/plugins/autogems.cpp @@ -167,6 +167,16 @@ void create_jobs() { stockpiled.insert(item->id); piled[item->getMaterialIndex()] += 1; } + else if (item->flags.bits.container) { + std::vector binneditems; + Items::getContainedItems(item, &binneditems); + for (df::item *it : binneditems) { + if (valid_gem(it)) { + stockpiled.insert(it->id); + piled[it->getMaterialIndex()] += 1; + } + } + } } // Decrement current jobs from all linked workshops, not just this one. diff --git a/plugins/manipulator.cpp b/plugins/manipulator.cpp index 33d5ff884..e9206dc0f 100644 --- a/plugins/manipulator.cpp +++ b/plugins/manipulator.cpp @@ -242,6 +242,7 @@ const SkillColumn columns[] = { {16, 3, profession::NONE, unit_labor::NONE, job_skill::FLATTERY, "Fl"}, {16, 3, profession::NONE, unit_labor::NONE, job_skill::CONSOLE, "Cs"}, {16, 3, profession::NONE, unit_labor::NONE, job_skill::PACIFY, "Pc"}, + {16, 3, profession::NONE, unit_labor::NONE, job_skill::INTRIGUE, "Sc"}, // Noble {17, 5, profession::TRADER, unit_labor::NONE, job_skill::APPRAISAL, "Ap"}, {17, 5, profession::ADMINISTRATOR, unit_labor::NONE, job_skill::ORGANIZATION, "Or"}, diff --git a/plugins/search.cpp b/plugins/search.cpp index 43e14996a..7e72c2c1c 100644 --- a/plugins/search.cpp +++ b/plugins/search.cpp @@ -25,6 +25,7 @@ #include "df/viewscreen_buildinglistst.h" #include "df/viewscreen_dwarfmodest.h" #include "df/viewscreen_joblistst.h" +#include "df/viewscreen_justicest.h" #include "df/viewscreen_kitchenprefst.h" #include "df/viewscreen_layer_militaryst.h" #include "df/viewscreen_layer_noblelistst.h" @@ -2327,6 +2328,85 @@ IMPLEMENT_HOOKS(df::viewscreen_layer_stone_restrictionst, stone_search); // END: Stone status screen search // +// +// START: Justice screen conviction search +// + +typedef search_generic justice_conviction_search_base; +class justice_conviction_search : public justice_conviction_search_base +{ +public: + bool can_init (df::viewscreen_justicest *screen) + { + return screen->cur_column == df::viewscreen_justicest::ConvictChoices; + } + + string get_element_description (df::unit *unit) const + { + return get_unit_description(unit); + } + + void render() const + { + print_search_option(37); + } + + vector *get_primary_list() + { + return &viewscreen->convict_choices; + } + + virtual int32_t *get_viewscreen_cursor() + { + return &viewscreen->cursor_right; + } +}; + +IMPLEMENT_HOOKS(df::viewscreen_justicest, justice_conviction_search); + +// +// END: Justice screen conviction search +// + +// +// START: Justice screen interrogation search +// + +typedef search_generic justice_interrogation_search_base; +class justice_interrogation_search : public justice_interrogation_search_base +{ +public: + bool can_init (df::viewscreen_justicest *screen) + { + return screen->cur_column == df::viewscreen_justicest::InterrogateChoices; + } + + string get_element_description (df::unit *unit) const + { + return get_unit_description(unit); + } + + void render() const + { + print_search_option(37); + } + + vector *get_primary_list() + { + return &viewscreen->interrogate_choices; + } + + virtual int32_t *get_viewscreen_cursor() + { + return &viewscreen->cursor_right; + } +}; + +IMPLEMENT_HOOKS(df::viewscreen_justicest, justice_interrogation_search); + +// +// END: Justice screen conviction search +// #define SEARCH_HOOKS \ HOOK_ACTION(unitlist_search_hook) \ @@ -2350,6 +2430,8 @@ IMPLEMENT_HOOKS(df::viewscreen_layer_stone_restrictionst, stone_search); HOOK_ACTION(location_assign_occupation_search_hook) \ HOOK_ACTION(kitchen_pref_search_hook) \ HOOK_ACTION(stone_search_hook) \ + HOOK_ACTION(justice_conviction_search_hook) \ + HOOK_ACTION(justice_interrogation_search_hook) \ DFhackCExport command_result plugin_enable ( color_ostream &out, bool enable) diff --git a/scripts b/scripts index 8618cd0b0..b3ce8fa65 160000 --- a/scripts +++ b/scripts @@ -1 +1 @@ -Subproject commit 8618cd0b0a17935fe07f329b249726cda61f5bdf +Subproject commit b3ce8fa650f86c7a1dbd5329d72c3d73dd76d05d diff --git a/travis/build-lua.sh b/travis/build-lua.sh deleted file mode 100644 index e29d7ce87..000000000 --- a/travis/build-lua.sh +++ /dev/null @@ -1,54 +0,0 @@ -#!/bin/sh - -set -e - -LUA_ROOT="$HOME/lua53" -LUA_URL="http://www.lua.org/ftp/lua-5.3.3.tar.gz" -LUA_TAR=$(basename "$LUA_URL") -LUA_DIR="$LUA_ROOT/${LUA_TAR%.tar.*}" -LUA_SHA1="a0341bc3d1415b814cc738b2ec01ae56045d64ef" - -echo LUA_ROOT $LUA_ROOT -echo LUA_TAR $LUA_TAR -echo LUA_DIR $LUA_DIR - -sha1() { - python -c 'import hashlib, sys; print(hashlib.sha1(open(sys.argv[1],"rb").read()).hexdigest())' "$1" -} - -download() { - echo "Downloading $LUA_URL" - wget -O "$LUA_ROOT/$LUA_TAR" "$LUA_URL" - tar xvf "$LUA_ROOT/$LUA_TAR" -} - -build() { - cd "$LUA_DIR/src" - make generic -} - -main() { - mkdir -p "$LUA_ROOT" - cd "$LUA_ROOT" - mkdir -p bin - - if [ "$(sha1 "$LUA_ROOT/$LUA_TAR" 2>/dev/null)" != "$LUA_SHA1" ]; then - download - build - else - echo "Already downloaded" - - if [ -x "$LUA_DIR/src/luac" ]; then - echo "Already built" - else - build - fi - fi - - echo "Linking" - ln -sf "$LUA_DIR/src/lua" "$LUA_ROOT/bin/lua5.3" - ln -sf "$LUA_DIR/src/luac" "$LUA_ROOT/bin/luac5.3" - echo "Done" -} - -main diff --git a/travis/git-info.sh b/travis/git-info.sh deleted file mode 100644 index 333d13bc1..000000000 --- a/travis/git-info.sh +++ /dev/null @@ -1,2 +0,0 @@ -#!/bin/sh -git log --pretty="commit %h (parents: %p): %s" -1 diff --git a/travis/pr-check-base.py b/travis/pr-check-base.py deleted file mode 100644 index 47605b051..000000000 --- a/travis/pr-check-base.py +++ /dev/null @@ -1,18 +0,0 @@ -import os, sys -repo = os.environ.get('TRAVIS_REPO_SLUG', 'dfhack/dfhack').lower() -branch = os.environ.get('TRAVIS_BRANCH', 'master') -try: - pr_id = int(os.environ.get('TRAVIS_PULL_REQUEST', 'false')) -except ValueError: - print('Not a pull request') - sys.exit(0) -print('Pull request %s#%i' % (repo, pr_id)) -if repo != 'dfhack/dfhack': - print('Not in dfhack/dfhack') - sys.exit(0) -if branch != 'develop': - print('Not based on develop branch') - sys.exit(1) -else: - print('Ok') - sys.exit(0)