diff --git a/CONTRIBUTIONS.md b/CONTRIBUTIONS.md
index 0a4492b..cca2da7 100644
--- a/CONTRIBUTIONS.md
+++ b/CONTRIBUTIONS.md
@@ -46,7 +46,7 @@ Many thanks to these additional authors:
* "bale-go" for development and continued work on the 'calibrated rank' AI and rank estimation algorithm.
* "Dontbtme" for detailed feedback and early testing of v1.0+.
* "nowoowoo" for a fix to the parser for SGF files with extra line breaks.
-* "nimets123" for the timer sound effects and stone graphics.
+* "nimets123" for the timer sound effects and board/stone graphics.
* Jordan Seaward for the stone sound effects.
* "fohristiwhirl" for the Gibo format parsing code.
diff --git a/README.md b/README.md
index 8a8c254..41488b6 100644
--- a/README.md
+++ b/README.md
@@ -99,6 +99,8 @@ Further technical details and discussion on these AIs can be found on [this](htt
## Analysis
+Analysis options in KaTrain allow you to explore variations and request more in-depth analysis from the engine at any point in the game.
+
Keyboard shortcuts are shown with **[key]**.
* **[Tab]**: Switch between analysis and play modes.
@@ -123,6 +125,12 @@ Keyboard shortcuts are shown with **[key]**.
* **[spacebar]**: Turn continuous analysis on/off.
* **[enter]** AI move. Makes the AI move for the current player regardless of current player selection.
+### Rank Estimation
+
+A new feature in v1.3 is the rank estimation panel. This adds an extra graph which uses a statistical model to estimate the playing strength
+of both players for every 80 move segment. It can be used for determining which part of your game needs extra attention,
+but keep in mind the estimation is based purely on how well moves correspond to the 'shape sense' of KataGo and can be very inaccurate at times.
+
## Keyboard and mouse shortcuts
In addition to shortcuts mentioned above and those shown in the main menu:
@@ -158,7 +166,7 @@ In addition to shortcuts mentioned above and those shown in the main menu:
[](https://github.com/sanderland/katrain/issues)
[](CONTRIBUTIONS.md)
[](https://liberapay.com/sanderbaduk/)
-[](https://github.com/sponsors/sanderland)
+[](https://github.com/sponsors/sanderland)
* Ideas, feedback, and contributions to code or translations are all very welcome.
* For suggestions and planned improvements, see [open issues](https://github.com/sanderland/katrain/issues) on github to check if the functionality is already planned.
diff --git a/katrain/core/ai.py b/katrain/core/ai.py
index 3cffc8f..67bd9db 100644
--- a/katrain/core/ai.py
+++ b/katrain/core/ai.py
@@ -195,9 +195,11 @@ def generate_ai_move(game: Game, ai_mode: str, ai_settings: Dict) -> Tuple[Move,
if policy_moves[0][0] > override:
aimove = top_policy_move
ai_thoughts += f"Top policy move has weight > {override:.1%}, so overriding other strategies."
- elif policy_moves[0][0]+policy_moves[1][0] > overridetwo:
+ elif policy_moves[0][0] + policy_moves[1][0] > overridetwo:
aimove = top_policy_move
- ai_thoughts += f"Top two policy moves have cumulative weight > {overridetwo:.1%}, so overriding other strategies."
+ ai_thoughts += (
+ f"Top two policy moves have cumulative weight > {overridetwo:.1%}, so overriding other strategies."
+ )
elif ai_mode == AI_WEIGHTED:
aimove, ai_thoughts = policy_weighted_move(
policy_moves, ai_settings["lower_bound"], ai_settings["weaken_fac"]
diff --git a/katrain/core/game_node.py b/katrain/core/game_node.py
index 4a51d23..a4f8676 100644
--- a/katrain/core/game_node.py
+++ b/katrain/core/game_node.py
@@ -230,7 +230,13 @@ class GameNode(SGFNode):
polmoves = self.policy_ranking
top_polmove = polmoves[0][1] if polmoves else Move(None) # if no info at all, pass
return [
- {**self.analysis["root"], "pointsLost": 0, "order": 0, "move": top_polmove.gtp(),"pv":[top_polmove.gtp()]}
+ {
+ **self.analysis["root"],
+ "pointsLost": 0,
+ "order": 0,
+ "move": top_polmove.gtp(),
+ "pv": [top_polmove.gtp()],
+ }
] # single visit -> go by policy/root
root_score = self.analysis["root"]["scoreLead"]
diff --git a/katrain/gui/badukpan.py b/katrain/gui/badukpan.py
index 4c36c71..07bb3c1 100644
--- a/katrain/gui/badukpan.py
+++ b/katrain/gui/badukpan.py
@@ -138,7 +138,7 @@ class BadukPanWidget(Widget):
def draw_stone(self, x, y, player, alpha=1, innercol=None, evalcol=None, evalscale=1.0, scale=1.0):
stone_size = self.stone_size * scale
- Color(1,1,1,alpha)
+ Color(1, 1, 1, alpha)
Rectangle(
pos=(self.gridpos_x[x] - stone_size, self.gridpos_y[y] - stone_size),
size=(2 * stone_size, 2 * stone_size),
@@ -148,9 +148,11 @@ class BadukPanWidget(Widget):
eval_radius = math.sqrt(evalscale) # scale area by evalscale
evalsize = self.stone_size * (EVAL_DOT_MIN_SIZE + eval_radius * (EVAL_DOT_MAX_SIZE - EVAL_DOT_MIN_SIZE))
Color(*evalcol)
- Rectangle( pos=(self.gridpos_x[x] - evalsize, self.gridpos_y[y] - evalsize),
- size=(2 * evalsize, 2 * evalsize),
- source=f"img/dot.png")
+ Rectangle(
+ pos=(self.gridpos_x[x] - evalsize, self.gridpos_y[y] - evalsize),
+ size=(2 * evalsize, 2 * evalsize),
+ source=f"img/dot.png",
+ )
if innercol:
Color(*innercol)
inner_size = stone_size * 0.8
@@ -194,10 +196,11 @@ class BadukPanWidget(Widget):
for i in range(board_size_y)
]
- Color(*BOARD_COLOR)
+ Color(1, 0.95, 0.8, 1) # image is a bit too light
Rectangle(
pos=(self.gridpos_x[0] - self.grid_size * 1.5, self.gridpos_y[0] - self.grid_size * 1.5),
size=(self.grid_size * x_grid_spaces, self.grid_size * y_grid_spaces),
+ source="img/board.png",
)
Color(*LINE_COLOR)
@@ -452,7 +455,7 @@ class BadukPanWidget(Widget):
hide_node = cn
while hide_node and hide_node.move and hide_node != node:
if not hide_node.move.is_pass:
- pos = (self.gridpos_x[hide_node.move.coords[0]],self.gridpos_y[hide_node.move.coords[1]])
+ pos = (self.gridpos_x[hide_node.move.coords[0]], self.gridpos_y[hide_node.move.coords[1]])
draw_circle(pos, self.stone_size, [0.85, 0.68, 0.40, 0.8])
hide_node = hide_node.parent
for i, gtpmove in enumerate(pv):
@@ -473,9 +476,9 @@ class BadukPanWidget(Widget):
sizefac = 1
stone_size = self.stone_size * sizefac
- Color(1,1,1,1)
+ Color(1, 1, 1, 1)
Rectangle(
- pos=(board_coords[0]-stone_size,board_coords[1]-stone_size),
+ pos=(board_coords[0] - stone_size, board_coords[1] - stone_size),
size=(2 * stone_size, 2 * stone_size),
source=f"img/{move_player}_stone.png",
)
diff --git a/katrain/gui/style.py b/katrain/gui/style.py
index 4141077..a4a3222 100644
--- a/katrain/gui/style.py
+++ b/katrain/gui/style.py
@@ -46,7 +46,7 @@ LINE_COLOR = [0, 0, 0]
POLICY_COLOR = [0.9, 0.2, 0.8]
STARPOINT_SIZE = 0.1
BOARD_COLOR = [0.85, 0.68, 0.40, 1]
-STONE_SIZE = 0.505 # texture edge is transparent
+STONE_SIZE = 0.505 # texture edge is transparent
VISITS_FRAC_SMALL = 0.1
GHOST_ALPHA = 0.5
diff --git a/katrain/img/board.png b/katrain/img/board.png
new file mode 100644
index 0000000..fb4bfd2
Binary files /dev/null and b/katrain/img/board.png differ