             }
         }
     }
+    
+//    * capture keys in containers corresponding to their units
+//    * units don't necessairly correspond to specific views
+//    * for example:
+//        * top: [left spacer][shift][space][key row][space][backspace][right spacer]
+//        * key row: [key][gap][key][gap]...
+//    
+//    promises
+//    for key in row {
+//        if key == special {
+//            promise(key.width = flexispecial)
+//        }
+//        else if key == character {
+//            row = capture()
+//            measure(row)
+//            promise(key.surroundings == equal)
+//        }
+//    }
+//    resolve(promises)
+//    
+    // at this point, we have "gaps" (flexi specials, surrounding gaps) that need to be resolved
+    
+    
+    
     
 //    private func addGapPair(nameFormat: String, page: Int, row: Int?, startIndex: Int, endIndex: Int, leftAnchor: String?, rightAnchor: String?, vertical: Bool, width: String?) {
 //        var allConstraints: [String] = []

                return currentMax
            }()
            
            // side edges
            let sideEdges = layoutConstants.sideEdges
            
            // top edge
            let topEdge: CGFloat = ((isLandscape ? layoutConstants.topEdgeLandscape : layoutConstants.topEdgePortrait) + self.topBanner)
            
            // row gaps
            let rowGaps: CGFloat = (isLandscape ? layoutConstants.rowGapsLandscape : layoutConstants.rowGapsPortrait)
            
            // key gaps
            let keyGaps: CGFloat = {
                let pastThreshhold = (CGFloat(mostKeysInRow) >= layoutConstants.keyGapsSmallThreshhold)
                return (pastThreshhold ? layoutConstants.keyGapsSmall : layoutConstants.keyGaps)
            }()
            
            // key height
            let totalGaps = sideEdges + topEdge + (rowGaps * CGFloat(numRows - 1))
            let keyHeight: CGFloat = (bounds.height - totalGaps) / CGFloat(numRows)
            
            // letter key width
            let letterKeyWidth: CGFloat = {
                let totalGaps = (sideEdges * CGFloat(2)) + (keyGaps * CGFloat(mostKeysInRow - 1))
                return (bounds.width - totalGaps) / CGFloat(mostKeysInRow)

                
                for (k, key) in enumerate(row) {
                    
                    // character range state processing
                    if !inCharacterRange {
                        if key.type == Key.KeyType.Character {
                            var endIndex = 0
