Repository: zhiburt/tabled (rust)

Issue:
Fix `Panel` style rendering on tables with more than 2 columns
Running this code will result in the following.

```rust
use tabled::{Style, Table};

fn main() {
    let table = Table::new(&[(0, 1)])
        .with(tabled::Panel("Numbers", 0))
        .with(Style::modern());

    println!("{}", table);
}
```

```rust
┌───────────┬
│Numbers    │
├───────────┼
│ i32 │ i32 │
├─────┼─────┤
│  0  │  1  │
└─────┴─────┘
```

As you may see the styles on the right side is not exactly correct.
It would be good to be fixed.

Pull request description:
tabled/ Fix an issue with a panel rendering
close #66 

Patch:
diff --git a/Cargo.toml b/Cargo.toml
index d4b1006..b4d35c6 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -25,7 +25,7 @@ color = ["papergrid/color", "ansi-str"]
 
 [dependencies]
 tabled_derive = "0.2.0"
-papergrid = "0.2.1"
+papergrid = { path = "./papergrid" }
 ansi-str = { version = "0.1.1", optional = true }
 
 [dev-dependencies]
@@ -36,4 +36,4 @@ quickcheck_macros = "1.0.0"
 
 [[bench]]
 name = "table_build"
-harness = false
\ No newline at end of file
+harness = false
diff --git a/papergrid/src/lib.rs b/papergrid/src/lib.rs
index 010ff34..b275760 100644
--- a/papergrid/src/lib.rs
+++ b/papergrid/src/lib.rs
@@ -518,7 +518,7 @@ impl SplitLine {
     }
 }
 
-#[derive(Debug, Clone, Default)]
+#[derive(Debug, Clone, Default, Eq, PartialEq)]
 pub struct Border {
     pub top: Option<char>,
     pub bottom: Option<char>,
@@ -653,10 +653,10 @@ impl EntityFrame {
 
 #[derive(Debug, Clone)]
 pub struct Style {
-    indent: Indent,
-    alignment_h: AlignmentHorizontal,
-    alignment_v: AlignmentVertical,
-    span: usize,
+    pub indent: Indent,
+    pub alignment_h: AlignmentHorizontal,
+    pub alignment_v: AlignmentVertical,
+    pub span: usize,
 }
 
 impl Default for Style {
diff --git a/src/style.rs b/src/style.rs
index 9646164..ff478a5 100644
--- a/src/style.rs
+++ b/src/style.rs
@@ -368,7 +368,8 @@ impl TableOption for StyleSettings {
         let count_columns = grid.count_columns();
         for row in 0..count_rows {
             for column in 0..count_columns {
-                let border = make_style(self, row, column, count_rows, count_columns);
+                let mut border = make_style(self, row, column, count_rows, count_columns);
+                make_style_header(&mut border, self, row, column, count_rows, count_columns);
 
                 grid.set(
                     &Entity::Cell(row, column),
@@ -376,6 +377,15 @@ impl TableOption for StyleSettings {
                 );
             }
         }
+
+        if count_columns > 0 {
+            for row in 0..count_rows {
+                let cell = grid.style(&Entity::Cell(row, 0));
+                if cell.span == count_columns {
+                    fix_full_span_row(grid, row, count_columns);
+                }
+            }
+        }
     }
 }
 
@@ -391,7 +401,7 @@ fn make_style(
     let is_first_column = column == 0;
     let is_last_column = column + 1 == count_columns;
 
-    let mut border = match (is_first_row, is_last_row, is_first_column, is_last_column) {
+    match (is_first_row, is_last_row, is_first_column, is_last_column) {
         // A table with a single cell
         (true, true, true, true) => Border {
             top: style.frame.top.as_ref().map(|l| l.main),
@@ -556,9 +566,20 @@ fn make_style(
             right_top_corner: style.split.as_ref().and_then(|l| l.intersection),
             right_bottom_corner: style.split.as_ref().and_then(|l| l.intersection),
         },
-    };
+    }
+}
+
+fn make_style_header(
+    border: &mut Border,
+    style: &StyleSettings,
+    row: usize,
+    column: usize,
+    _count_rows: usize,
+    count_columns: usize,
+) {
+    let is_first_column = column == 0;
+    let is_last_column = column + 1 == count_columns;
 
-    // override header style
     if style.header_split_line.is_some() {
         if row == 1 {
             border.top = style.header_split_line.as_ref().map(|l| l.main);
@@ -624,8 +645,22 @@ fn make_style(
             border.left_bottom_corner = None;
         }
     }
+}
+
+fn fix_full_span_row(grid: &mut Grid, row: usize, count_columns: usize) {
+    let mut first_cell_border = grid.get_border(row, 0);
+    let last_cell_border = grid.get_border(row, count_columns - 1);
 
-    border
+    first_cell_border.right = last_cell_border.right;
+    first_cell_border.right_top_corner = last_cell_border.right_top_corner;
+    first_cell_border.right_bottom_corner = last_cell_border.right_bottom_corner;
+
+    grid.set(
+        &Entity::Cell(row, 0),
+        Settings::default()
+            .border(first_cell_border)
+            .border_restriction(false),
+    );
 }
 
 /// Style is responsible for a look of a [Table].


Test patch:
diff --git a/tests/panel_test.rs b/tests/panel_test.rs
index deda024..771f446 100644
--- a/tests/panel_test.rs
+++ b/tests/panel_test.rs
@@ -156,3 +156,23 @@ fn footer() {
 
     assert_eq!(table, expected);
 }
+
+#[test]
+fn panel_style_uses_most_left_and_right_cell_styles() {
+    let table = Table::new(&[(0, 1)])
+        .with(tabled::Panel("Numbers", 0))
+        .with(Style::modern())
+        .to_string();
+
+    let expected = concat!(
+        "┌───────────┐\n",
+        "│Numbers    │\n",
+        "├───────────┤\n",
+        "│ i32 │ i32 │\n",
+        "├─────┼─────┤\n",
+        "│  0  │  1  │\n",
+        "└─────┴─────┘\n",
+    );
+
+    assert_eq!(table, expected);
+}