2013-10-31 41 views
1

我已經創建了一個數獨謎題創建器/求解器,並且需要一些CSS幫助來設計它。造型數獨網格

通常,它們的風格是這樣的:

http://www.sudoku.4thewww.com/Grids/grid.jpg

我正在使用一些命名。

單元格 - 包含單個數字的每個單獨的單元格。

- 的9個框之一每個包含3×3個細胞

網格 - 整個9x9的播放區域。

我的HTML部分是由我的紅寶石/西納特拉的應用程序(至少重複DIV的是)和結構產生這樣:

#game { 
 
    margin-left: auto; 
 
    margin-right: auto; 
 
    width: 360px; 
 
} 
 
.cell input { 
 
    display: inline-block; 
 
    float: left; 
 
    width: 40px; 
 
    height: 40px; 
 
    border-style: solid; 
 
    border-width: 1px; 
 
    text-align: center; 
 
    font-size: 15px; 
 
}
<form action="/" method="post"> 
 
    <div id="game"> 
 
    <div class="cell"> 
 
     <input name="cell[0]" type="text" maxlength="1" value=<%=val%>> 
 
    </div> 
 

 
    <div class="cell"> 
 
     <input name="cell[1]" type="text" maxlength="1" value=<%=val%>> 
 
    </div> 
 

 
    <!-- ... --> 
 

 
    <div class="cell"> 
 
     <input name="cell[79]" type="text" maxlength="1" value=<%=val%>> 
 
    </div> 
 

 
    <div class="cell"> 
 
     <input name="cell[80]" type="text" maxlength="1" value=<%=val%>> 
 
    </div> 
 
    </div> 
 
</form>

這允許我創建的基本9x9的網格與我的第一個單元格(0)在左上角,並從左到右,一排一排,到右下角的最後一個單元格(80)。

難度在於設計每個單元的格式,以便網格不僅可以分成行和列,還可以分成9個較大的方框。再次參見this grid以供參考。

目前我有兩個選擇:

  1. 完全重寫我的數獨代碼,使我以不同的順序繪製出DIV的。用分組DIV包裝每個盒子。這將使CSS相對簡單。這將是一個重大改變,我真的不想走這條路。

  2. 手動標識每個單元格併爲所有81個單元格寫入相應的CSS。比上面好,但仍然是球疼,而不是特別光滑。

我確實有動態生成CSS樣式的選項(性能不是問題)。我正在尋找的是幫助設計一種算法,它將確定(基於它的線性索引0..80)應該如何對每個單元格進行樣式設置。

例如,頂行(0..8)中的所有單元格將具有厚頂邊(3px)和薄底邊(1px)。第3行(18..26)中所有單元格的底部都有一個厚邊框,但這些單元格的頂部會有一個薄邊框。第一列中所有單元格的左側將有一個厚邊框,但這些單元格的右側將有一個薄邊框。等等。

回答

2

以下是HTML5 CR中table element部分中示例的輕微修改,說明使用colgroup分組列和tbody分組行。這個分組可以讓你設置不同的邊框,而不是圍繞單元格。

<style> 
table { border-collapse: collapse; font-family: Calibri, sans-serif; } 
colgroup, tbody { border: solid medium; } 
td { border: solid thin; height: 1.4em; width: 1.4em; text-align: center; padding: 0; } 
</style> 
<table> 
    <caption>Sudoku of the day</caption> 
    <colgroup><col><col><col> 
    <colgroup><col><col><col> 
    <colgroup><col><col><col> 
    <tbody> 
    <tr> <td>1 <td> <td>3 <td>6 <td> <td>4 <td>7 <td> <td>9 
    <tr> <td> <td>2 <td> <td> <td>9 <td> <td> <td>1 <td> 
    <tr> <td>7 <td> <td> <td> <td> <td> <td> <td> <td>6 
    <tbody> 
    <tr> <td>2 <td> <td>4 <td> <td>3 <td> <td>9 <td> <td>8 
    <tr> <td> <td> <td> <td> <td> <td> <td> <td> <td> 
    <tr> <td>5 <td> <td> <td>9 <td> <td>7 <td> <td> <td>1 
    <tbody> 
    <tr> <td>6 <td> <td> <td> <td>5 <td> <td> <td> <td>2 
    <tr> <td> <td> <td> <td> <td>7 <td> <td> <td> <td> 
    <tr> <td>9 <td> <td> <td>8 <td> <td>2 <td> <td> <td>5 
</table> 
+0

表中的數據可能比DIV好,所以這是一個很好的解決方案。見下面我的實現(帶代碼)。 – dwkns

2

如果是我,我會用一個9行9列的表格。

然後在CSS選擇器中使用nth-type(3n)來設置每隔三行和一列的邊框。

+0

感謝邁克,而會很快解決的HTML/CSS的問題,它使數獨解決代碼要複雜得多。因此,這個問題。 – dwkns

0

偉大的解決方案Jukka。我用這個和下面的.erb代碼的組合來動態生成表格並彈出內容。

@current_solution是我的數組,它爲每個單元格保存值。

<table> 
    <colgroup><col><col><col> 
    <colgroup><col><col><col> 
    <colgroup><col><col><col> 

    <% 3.times do |all_box_rows_value|%> 
    <tbody> 
    <% 3.times do |box_row_value| %> 
     <% all_box_rows = all_box_rows_value * 27 %> 
     <% all_rows = ((box_row_value +1) * 9)-9 %> 
     <tr><%9.times do |row| %> 
      <% index = all_box_rows+all_rows+row %> 
      <% value = @current_solution[index] %><td> 
      <% colour_class = get_colour_class index %> 
      <input name="cell[]" type="text" maxlength="1" autocomplete="off" value=<%=value%> > 
     <% end %> 
     <% end %>  
    <% end %>  
</table> 
1

如下我會創造數獨板:

<section class="sudoku"> 
     <div class="sudoku-row"> 
      <div class="sudoku-square"> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value"></a></div> 
       <div class="cell"><a class="cell-value "></a></div> 
      </div> 

和不怎麼會這樣

@cell-size: 50px; 
.sudoku { 
    margin: 70px auto; 
    width: 478px; 
    background: #777;  
    border: 2px solid #000; 
    box-shadow: 15px 15px 20px #111; 

    .sudoku-row {  
    .sudoku-square {  
     float: left; 
     border: 1px solid #000; 

     .cell:nth-child(3n+1) { 
     clear: both; 
     } 
     .cell { 
     float: left;   
     position: relative; 
     height: @cell-size; 
     width: @cell-size; 
     background:#fff;   
     border: 1px solid #000; 
     box-sizing: content-box;   

     a { 
      margin: 0; 
      padding: 0; 
     } 
     a.cell-value { 
      display: block; 
      font-size: 30px;    
      color: #000; 
      width: @cell-size; 
      height: @cell-size; 
      text-align: center;   
     } 

     a.cell-value:hover { 
     text-decoration: none; 
     } 
     }  
    } 
    clear: both; 
    } 
} 

你可以找到一個現場演示here

3

通過結合Jukka K. Korpela's answerMike's answer並添加了一點jQuery魔術,我創建了tw o解決方案。

$(document).ready(function() { 
 
    var data = [ 
 
     1, 0, 3, 6, 0, 4, 7, 0, 9, // 0x0 
 
     0, 2, 0, 0, 9, 0, 0, 1, 0, // 0x1 
 
     7, 0, 0, 0, 0, 0, 0, 0, 6, // 0x2 
 
     2, 0, 4, 0, 3, 0, 9, 0, 8, // 1x0 
 
     0, 0, 0, 0, 0, 0, 0, 0, 0, // 1x1 
 
     5, 0, 0, 9, 0, 7, 0, 0, 1, // 1x2 
 
     6, 0, 0, 0, 5, 0, 0, 0, 2, // 2x0 
 
     0, 0, 0, 0, 7, 0, 0, 0, 0, // 2x1 
 
     9, 0, 0, 8, 0, 2, 0, 0, 5 // 2x2 
 
    ]; 
 

 
    // Build page content. 
 
    $('body').append($('<div>').addClass('wrapper') 
 
     .append($('<div>').addClass('col') 
 
      .append($('<h1>').html('First Method')) 
 
      .append(generateSudokuGrid())) 
 
     .append($('<div>').addClass('col') 
 
      .append($('<h1>').html('Second Method')) 
 
      .append(generateSudokuGrid2()))); 
 

 
    // Populate grids with data. 
 
    $('table[class^="sudoku"]').each(function (index, grid) { 
 
     populateGrid($(grid), data); 
 
    }); 
 
}); 
 

 
function populateGrid(grid, data) { 
 
    grid.find('td').each(function (index, td) { 
 
     $(td).text(data[index] || ''); 
 
    }); 
 
} 
 

 
/* First Method */ 
 
function generateSudokuGrid(data) { 
 
    return $('<table>').append(multiPush(3, function() { 
 
     return $('<colgroup>').append(multiPush(3, function() { 
 
      return $('<col>'); 
 
     })); 
 
    })).append(multiPush(3, function() { 
 
     return $('<tbody>').append(multiPush(3, function() { 
 
      return $('<tr>').append(multiPush(9, function() { 
 
       return $('<td>'); 
 
      })); 
 
     })); 
 
    })).addClass('sudoku'); 
 
} 
 

 
/* Second Method */ 
 
function generateSudokuGrid2(data) { 
 
    return $('<table>').append(multiPush(9, function() { 
 
     return $('<tr>').append(multiPush(9, function() { 
 
      return $('<td>'); 
 
     })); 
 
    })).addClass('sudoku2'); 
 
} 
 

 
function multiPush(count, func, scope) { 
 
    var arr = []; 
 
    for (var i = 0; i < count; i++) { 
 
     arr.push(func.call(scope, i)); 
 
    } 
 
    return arr; 
 
}
/* First Method */ 
 
table.sudoku { 
 
    border-collapse: collapse; 
 
    font-family: Calibri, sans-serif; 
 
} 
 
.sudoku colgroup, tbody { 
 
    border: solid medium; 
 
} 
 
.sudoku td { 
 
    border: solid thin; 
 
    height: 1.4em; 
 
    width: 1.4em; 
 
    text-align: center; 
 
    padding: 0; 
 
} 
 

 
/* Second Method */ 
 
table.sudoku2 { 
 
    border-collapse: collapse; 
 
    font-family: Calibri, sans-serif; 
 
} 
 
.sudoku2 tr:nth-of-type(3n) { 
 
    border-bottom: solid medium; 
 
} 
 
.sudoku2 td:nth-of-type(3n) { 
 
    border-right: solid medium; 
 
} 
 
.sudoku2 td { 
 
    border: solid thin; 
 
    height: 1.4em; 
 
    width: 1.4em; 
 
    text-align: center; 
 
    padding: 0; 
 
} 
 

 
/* Presentation Formatting [Ignore] */ 
 
table[class^="sudoku"] { 
 
    margin: 0 auto; 
 
} 
 
.wrapper { 
 
    width: 100%; 
 
} 
 
.col { 
 
    display: inline-block; 
 
    width: 50%; 
 
    text-align: center; 
 
    margin: 0 auto; 
 
    padding: 0; 
 
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>