Objectsheets

A Simple Object Environment

Considerations/Issues

Back to White Paper


The Object Model

Split Objectsheets vs Classes Multiple Objectsheets can hold objects of the same class. This can be created either by explicitly splitting an existing sheet, or entering an existing Objectsheet name for a newly created sheet. In either case, the result is logically coherent as a single Objectsheet, but graphically distinct. It is envisioned that this capability will be required for layout flexibility.

All of the objects of a particular class could then be treated as a whole, while still leaving the instantiated objects in separable, manageable chunks. Of course, there are consistency issues-- we might want to change an Objectsheet's name to refer to a different class, for instance. Under what circumstances would one want to do this, and how should the behavior be written? And how treat the resulting mapping of properties from old to new. One approach is to just eliminate all formulaic properties, attempt to transfer literal properties from origin to destination Objectsheet, and then add in the formulaic properties of the new Objectsheet. But then, how deal with overrides to function-based properties? Should we provide a mapping of all properties? Wouldn't that result in a messy GUI?

Disadvantage of Split Objectsheets: they form an intermediate level between the object and its class. That would make object groups different from their Class, at least for multiple Objectgroups of the same class. It's ok to split an Objectsheet if all that we've really done is catch via us[] an array reference to a subset of the entire Objectsheet. Unfortunately, the goal of separating visual and logical organization breaks if we do this. Splitting and combining an Objectsheet should not effect its internal logical structure. Having an us[] separate from the Objectsheet as a whole would violate this.

One approach seems to be to keep the split pieces of an Objectsheet un-referenceable: us[] invariably addresses the Objectsheet in its entirety. One could argue that pieces of a split Objectsheet are "less coherent", both visually and logically, than a single, whole chunk of an Objectsheet, and that one would be able to distinctly manipulate things at the level they can be seen, but I consider the rule of visual layout not damaging the logical structure to be paramount.

Inheritance Simple inheritance, either from other Objectsheets on a page, or from other Objectsheets in other files should be straightforward. All of the Template information is copied over into the new Objectsheet, while leaving the instance section blank (although cloning one, multiple, or all objects (i.e. their instance properties) should be a reasonably simple extension of cut/copy/paste).

In the current concept, there are two "forms of inheritance". Replicating an existing Objectsheet name in a newly created sheet merely extends the set of instances of a given sheet into a new GUI element. The original object's template is copied by reference, and is frozen, unmodifiable (or alternatively, modifiable, but instantly reflected in the rest of the Objectsheet).

The second form is true inheritance. A new class can inherit from an existing class via the Objectsheet's Extends dropdown list box (If it's not shown in the above GUI examples, the approach is that each Objectsheet show follow its name in the title bar with an "extends" label, followed by a dropdown list box). The dropdown list box defaults to Object (top level inheritance), or can drop down to show all existing Classes defined within that particular sheet. Possible additions to the dropdown list are "File...", which would bring up a file dialog, and allow to inherit from an object on another sheet, and "Web...", which could allow to inherit from an object across the Internet.

The problem with outside-the-file inheritance is consistency and synchronization. The environment of the Objectsheet uses dynamic reference updating; changes propagate as they occur. For instance, when we rename a property, all references to that property (on that Objectsheet, peer Objectsheets, on inherited and referenced objects within the file) should receive the new name, and show the new reference. Similarly, a superclass' Template change should be reflected down the class heierarchy. Extending that reference knowledge beyond the individual file requires two-way linking or a registry. While this seems like a future possibility, it seeems to impart a severe complexity on the object model. We therefore won't concern ourselves with implementing it just yet.

Summary Properties

Instance-based and Template-based Properties have each associated formulas applied to each non-overridden, instantiated object. Summary properties are logically different from Template-based properties in that they do not reference individual objects, and are not evaluated for each row of the Objectsheet. Summary properties can contain true constants, or values making no reference to the properties of individual objects. The second are those that operate on entire arrays of objects. This is akin to spreadsheet functions that average and sum "cell ranges". Summary properties can do things like sum up numeric property values in an Objectsheet, find maximums, averages, and the like, and provide lookup and indexing functions.

Summary properties take up their own row on an Objectsheet; they can be placed anywhere in the Template or instance section. As with other row entities in the Objectsheet, they are referenced by the name given in the first column of the sheet. As summary properties are not part of the population of instantiated objects, they can be placed anywhere within the instance section without disrupting the calculation flow; the calculating engine skips over (in both calculation and relative reference) any summary properties, and comes back and calculates them only after evaluating all the instantiated objects in the sheet. An Objectsheets "row index" column does not count rows containing summary properties.

The structure of the Objectsheet thus allows us to associate summarizing properties in a simple fashion. The structure places a strong separation between logical flow and visual presentation: we can add, move, and delete these elements within a contiguous table without affecting the Objectsheet's logic.

Objectsheet size control The size of traditional spreadsheets is controlled by the size of the area in which a user chooses to paste a value or formula. There is no obvious direct analog with Objectsheets. There is also a slight complexity in that objects are different from properties, and probably require different functionality to manage the extent of each.

There are two ways in general to set Objectsheet size. The first is to have the size of the Objectsheet set to the number of objects one can see or scroll to. When a new Objectsheet is created, it has a defaulat number of objects and properties. Extender bars and Insert... commands are provided to allow insertion of objects in the sheet. This is the most direct (and intuitive) way of providing size control. Object and property deletion is accomplished akin to the method used in traditional spreadsheets, by heading selection and executing a delete command.

This approach is in fact analogous to the approach used in traditional spreadsheets, where interacting with the GUI sets the size of the table. Being visual, it is also the least powerful. The only way in which Objectsheet size can be set is visually, by the user. All Objectsheets are fixed in length. There are two alternative approaches for setting the size of an Objectsheet by expression, thus allowing variable-length arrays. Assuming there is some value to such a feature, and that it wouldn't damage the simplicity of the fixed, direct sizing method, it can be provided in a straightforward fashion.

One approach is to provide "done" and "last" reserved variables. In any property formula, when last is set to true, the Objectsheet caculating engine finishes calculating the current object stops. When done is set to true, the Objectsheet caculating engine removes the object currently being calculated and stops. So long as last and done are both false, processing continues.

This approach allows the length of the Objectsheet to be set directly via property formula, but requires some kind of safety valve. If by logical error there is nothing to ever set last and done to true, the calculating engine will try to generate an infinite list. Note that this closely parallels the programming construct do{} until() or while () {}, with done set to the boolean expression contained within until or while.

Another approach is to have a class-level variable named length that may be explicitly set by value or by formula. This seems more directly parallels Javascript (and OO languages in general), with size awareness. In fact, the behavior of the "done" and "last" reserved variables described above can be approximated by executing the expression length=thisIndex within a property formula (which appoximates "last") by executing the expression length=thisIndex-1 to appoximate "done".



Referencing

Named and index referencing in Javascript It's important to be able to refer to an object (and even its properties) by both numeric index and by name. Alas, the current Javascript language permits either, but not both. I wonder why? It was actually part of an earlier version of the language, but not currently. Did it create problems, or was it declared of insufficient value?

Referencing Template Information-- See Generalized Template Rows

Unnamed Object Referencing As useful as named references are, they are not always available (for instance, when objects are not explicitly named and can only be referenced through their row index) or applicable (as for relative referencing). Since objects are fundamentally different from properties in the Objectsheet model, we will consider each independently. Objects are the most important and will be treated first.

To start, we consider the traditional spreadsheet. The first consideration is how to show an offset. In spreadsheets, a direct cell reference is modified for the formula as it is replicated; as a result, each formula is different. The formula in cell D4 of '=D3+1' would replicate into cell D5 as '=D4+1'.

Another, less used scheme for spreadsheets is the R[ ]C[ ] notation. This approach replicates formulas without change. With this method, the formula '=R[-1]C+1' in cell R4C3 (which adds one to the value in (row-1) and the current column) would replicate without change into the cell below. Unfortunately, the intermingling of letters and numbers is more difficult to follow, especially when the numeric offsets are large (i.e. when referencing another area of the spreadsheet). This effect is especially severe with absolute references (How about this for a formula? =R34C19*20-R10C66+5+R[-13]C39)

For Objectsheet referencing, we (are actually required to) use the latter approach, since Template formulas are singular entities, and should apply to each object without change. Fortunately, we avoid the ugliness of the literal R[ ]C[ ] notation since a) nearly in nearly all cases, at least one of the dimensions uses a named reference and b) when matrix referencing is used, we should be able to find a cleaner notation. This is discussed further, below.

The (seemingly) obvious approach to unnamed object referencing is to treat an individual Objectsheet as an array of objects, referenced to the Objectsheet's name or with the generic us[ ] (a reference to this Objectsheet). In the Rooms example above, the Area property of the MasterBath could be referenced as as Rooms[2].Area from anywhere within the current file, or us[2].Area from within the Rooms Objectsheet. Both the Objectsheet name and us serves as a referenceable array, with the index corresponding to the object's row.

Relative Object Addressing One important need is to provide an entity that represents "the current row, whatever that may be". From the programming perspective, this is akin to the index variable in a "for loop". When a property formula in the Template is evaluated, this entity would change to reflect the row currently evaluated.

Indeed, there are several ways to proceed.

  1. Provide a "thisIndex" or "currentRow" reserved variable that simply reflects the number of the current row. This would be combined with the Objectsheet-as-object-array construct to refer to neighboring rows. As a trivial for instance, given a Objectsheet named "Numbers" we wish to count up by two's, and capture that in a property named "n". This is illustrated below. First, we would override the "n" cell in the first object/row with the literal value "0". We would then place the following formula in the template: "=Numbers[thisIndex-1].n+2" (or "=us[thisIndex-1].n+2"). The Objectsheet engine would ignore this rule for the first row (thisIndex=1), since that instance cell was overridden with a "0". For the next row (thisIndex=2), the formula would evaluate as "=Numbers[1].n+2" (or "=us[1].n+2"), giving 2.

    While this is the simplest approach (and probably a necessary provision in any case), the typing involved is fairly complex.

  2. A minor simplification to the above would be to abbreviate "thisIndex", perhaps to "~". When the engine finds the tilde in array reference, it would evaluate it as "thisIndex". In the above example, the formulas would become "=Numbers[~-1].n+2" (or "=us[~-1].n+2"). This provides a cleaner, more concise notation than full words. (While that character appropriately connotes "home" to Unix users, it also means logical negation, and is probably ambiguous. One might think of using a different character, like @ or ^. @ has cognitive significance; "=us[@-1].n+2". corresponding to "the row at -1".)

  3. Provide a reserved array of the objects on the Objectsheet whose zero value always corresponds to the current row. We call this array 'this[ ]' , where this[0] corresponds to the current object, this[-1] corresponds to the object one row above, etc. With the "even numbers" example above, the corresponding Template formula would be "=this[-1].n+2". It is similar to approach number 2 above. A difficulty is that from a programming language standpoint, it appears as a negative index to an array, which is generally forbidden. While concern might be somewhat alleviated by imagining the Objectsheet engine adding the index of the current row to the {this[·]}expression, using relative offsets in an array might still appear discomforting.

  4. Provide two reserved words, one to refer back and the other to refer forward. The reserved word prev[ ] would refer to objects above the current one, and the single object 'prev' would refer to object immediately. In the above even numbers example, the reference would be made as "=prev.n+2". This has the disadvantage of requiring separate arrays for looking ahead and looking back, but since the vast majority of relative references are to "the entry immediately preceeding this one", we might forgo the prev[ ] and next[ ] arrays, and just retain the single object "prev".

Remember as well that all these constructs are objects. The property is still explicitly named, and reference can be made to any property of the target object.

Next, we consider relative property addressing. The notion of referring to "this property" is valuable, referring to offset and indirect properties is less so. It is envisioned that indirect property referencing is useful when enumerating through all the properties of a given object, as well as when the we wish to use an Objectsheet as 2-dimensional matrix (as opposed to a set of 1-dimensional arrays).

Unnamed Property and Matrix-based Addressing For absolute referencing of properties, the Javascript language provides that access by treating the object itself as an array (and an associative array at that). This directly provides a familiar (at least to programmers, and hopefully not too complex to the layperson) representation of the matrix as dual-indexed array. In the Numbers example just above, we could refer to the value of n in row 1 as Numbers[1][1] or Numbers[1]["n"].

Likewise, we could extend the this variable to accomodate relative indexing in 2 dimensions, with this[0][0] representing the current cell, this[0][-1] for the cell immediately to the left, etc.

One slight complexity with matrix-based addressing appears when we decide to transpose an Objectsheet. The question is whether we wish to transpose visually, logically, or both? This is generally not a problem (I don't think) with Objects and their properties, but when we are dealing with a true matrix, it is. See the discussion on Visual transposition.

We also need to provide mixing of relative and absolute indices with the matrix representation (is this clearly the case? We can easily enough mix reference types using the object-based notation-- should we really provide this for matrix use?). This need favors using the thisIndex/thisProperty variable (or its shorthand "~") instead, since it can be applied at will to a either or both indices.

Relative Property Addressing The question here is how to capture the awareness of an individual cell. For example, formula references across Objectsheets would be: "=thatOtherSheet.Formula[thisProperty]"?

Parameterization and What-if Exploration In a spreadsheet, it is possible, although cumbersome, to take a simple set of scalar-related formulas (as one might generate in rough fashion as the first steps in crafting the solution to a problem) and parameterize a chosen variable for what-if questions or sensitivity analysis. But it is possible to do this, and seems to be a fairly popular use for spreadsheets. Still, it requires re-laying out the spreadsheet.

In the Objectsheet model, there are two approaches to this, both straightforward. First, one can change between formulas and constants merely by commenting out the existing formula or value and prefixing it with another.

The other, more powerful approach, is to change a property from instance-based to Template-based. Instance based properties are shown in the instance section, with the values of each calculated object having their own cell. A Template-based formula has a formula only (and maybe a single value, if there are no relative references contained in its expression). When a Template-based formula refers to other instance variables, nothing is shown. If it is a constant value or not dependent on thisIndex, its value can be shown.

The difference between Template-based and instance-based formulas is strictly visual (although see also the next paragraph). Any property may be transferred from being instance-based to being Template-based, without otherwise affecting the layout of the Objectsheet. This not only takes care of the visual row/column hiding of traditional spreadsheets, but it allow one to change a variable from a scalar (i.e. otherwise not dependent on thisIndex) to an array (distinct for each instance in the Objectsheet). The result is that parameterization is now a simple, two step process: moving a property between the instance section and Template, and actually changing the formula.

One difference between template- and instance- based properties that we might institute is to differentiate how the different properties are calculated. We might calculate all instance-based property values upon each Objectsheet modification, while calculating Template-based property values only as needed (i.e. only when referenced). This (may) provide opportunities for optimizing calculation efficiency.

One consideration is dealing with overridden cells. This can be added as conditional expressions appended to the existing base formula (alternatively it could be placed in a separate container; while providing a cleaner formula, it would not be as logically direct). Properties without formulas (i.e. those with manually entered cells, when dragged up to the Template, would turn the cell references into a literal array (names= {"MasterBedroom","MasterBathroom",...}). Actual cell values are reinstated when that property is dragged back into the Instance Section.


Functions and Calculation

Moving Cells One challenge is summary Cells. One approach is to override the entire bottom row of an Objectsheet, to provide totals or summaries of some or all properties. this would tend to damage the semantic coherence of the OS, unless that row could be individually dissassociated from the rest of the rows on the OS (like a comment row). One way of signifying this would be to comment out the name column (and to do so in such a way to keep the rest of the cells in that row in tact). But we do want to keep that row and its cells referenceable, and we want to maintain an "all" reference that would exclude this row. So we would like a way to override the whole row, but keep its semantic references. An advantage of this approach is a natural referencing (Rooms.total.area). Overridden rows could have a default background shading.

Another approach would be to go through (the headache of) creating class members that total up or summarize the desired properties, then rip that section off the OS display and drag it below the columns (and also transpose it(?)). This approach is inherent in our OS system, but would be a more cumbersome approach.

Summary Functions It seems reasonable to supply a sum() function that automatically operate over all (or some range of?) property cells within an OS. Area.sum(). or Area.sumAll() (these expressions prefixed by "Rooms." for reference outside the containing OS). Other functions would include min, max, stdev, avg, median, etc. Then we could consider functions to pare down arrays per some test: Rooms.select(floor==2 ).Area.sumAll(). In this case, the expression select(floor==2) would take the array of objects in Rooms and generate a new array of objects subject to the constraint floor==2. Rooms.Area.sum().

Order of Calculation It is unknown by the author how important this is. It is certainly imaginable that some order is useful, and in fact that that order can be controlled much easier than with a traditional spreadsheet. One approach would be to have the order of entries in the Class browser denote the evaluation order.

Another related issue is order of calculation within a spreadsheet. In traditional spreadsheet, it turns out that order of calculation does not allow one to place a summary formula (AVERAGE(), SUM(), etc.) above the data it totals. With Objectsheet structure, we can set a rule to calculate all class-level (summary) properties after calculating all instance properties. This ensures that summary calculations are summaries of already-calcuated instance data, not affected by the spatial placement of a property. One challenge with this approach is that a means is required to scan through and detect, and calculate all class-level constants in an Objectsheet before calculating the instance properties (they most probably would use such calculations. This requires the engine to scan all class-level (summary) properties before instance-property calculation and evaluate all of those that make no reference to instantiated objects (or other non-constant summary properties). This shouldn't be difficult, but it requiresan extra scan/processing step.

The above calculation strategy does not allow us to use subtotal calculations within instance formulas since subtotals are calculated only after instance properties (although it's not clear that there's any use for this at all). There is an alternative approach: to flow calculation completely through the instance section, including any embedded class-level properties.

Conditional Referencing Traditional spreadsheets have index and lookup functions that allow extraction of associative information from a table. Objectsheets provide that basic functionality within the object structure itself (through indirect, named references (where an object can be referenced by a string value: if the value of a MyHouse.RoomIAmIn has the value "Kitchen", the Property SizeOfRoomIAmIn can have the formula "=Rooms[RoomIAmIn].Area" to return the area of the Kitchen).

---discussion on SelectIf(condition)

One capability to consider that does not exist in spreadsheets is conditional lookup. the not only in the absolute sense (i.e. treating the lookup domain as a static object), but to find

Measurement Units While this is probably most specific to science and engineering, there is a fundamental problem of visual versus analytical represention of numbers with unit prefixes (like 50ml, 12 cm, etc.). The numeric part is what's shown in the GUI, and any calculations must know to multiply by the correct power of 10. The model designer must manually incorporate these units into calculations. Mis-maintenance of units is a common source of errors in spreadsheets. (This question can be expanded to the broader range of general units translations (cm. to in., for instance), but let's start by considering powers of 10 translations).

Is there a reasonably general way to specify units and automate the translation process? That automation must be done within the object model and the framework of the Objectsheet, not by adding to it. An example of how not to proceed is Visio units. It appears to capture units in a straightforward manner, by allowing them to be typed in along with a number. But Visio does not know many units (it knows spatial, but not electrical), nor does it allow overriding them(?how say this?).

One approach would be to provide a named object called Units within an Objectsheet. A method called num() would operate on a number (if we can blur distinction between number primitives and number objects-- if not, it would take a numeric argument) by getting the property name, then getting the value of the "Units" cell for that property (specified as String: "GHz", "ml", etc.). That value would be mapped to the appropriate multiplier ("GHz" to 1e9 and "ml" to 1e-3), the property multiplied by it and the result returned for continued calculation.

That multiplier mapping can proceed in one of 3 ways, the first 2 being aware of the units syntax. The Units class could have a predefined collection (modifiable, in its own Objectsheet), to do a (literal, but maybe case insensitive) match. That would require lots of units to be incorporated within. The other approach would be to do a "first match to a non-whitespace character". If that character is "k", multiply by 1000; if it's M, multiply by 1e6, etc. That would keep the procedure itself fairly simple, but would lack robustness since there are basic units that would get confused: m is meter or milli? MM is manmonth or Megamonth?...

The third way is to directly specify the multiplier in its own template row. That requires a little more work by the user, but does make the translation process much more direct.

Another use is if the units cell has "dB" in it. the function. dec() could turn it into units and dbs() could turn it back into dBs, or something like that.

A second question is that of units checking. If we can associate units in some fashion with any kind of parameter, then can we devise a syntax for representing, and an engine for checking unit consistency (again, within the bounds of the object model, not specializing the framework for it)? This would be a significant boon for spreadsheet quality and error checking-- provide a function that takes a formula (or entire methods?) as argument, parses it, and finds out what units are implied by it.

Also see discussion on Generalized Template Rows.


Visual Formatting and Data Views

Formatting Basic character and cell formatting within an Objectsheet is similar to that of a traditional spreadsheet. Things like background and foreground color, cell borderline color, size, and style, and font formats can be changed

The Objectsheet makes formatting a much simpler, robust process. Since Objectsheets are graphically independent of each other, sheet-based formatting (i.e. bordering the entire sheet, rows only, columns only, etc.) is not affected by manipulating other sheets on the page.

Format-oriented objects are associated with classes and objects; these include the Border, Font, and Background objects. Borders have width, direction (set by bit flags LEFT, RIGHT, TOP, BOTTOM, ALL, OUTLINE), color, (and whatever else); fonts have family, size and style (with bit flags), etc. Formatting can be specified within the class template itself (how? by what mechanism? within the ClassPage? as separate section, a la visio shapesheet?-- yuck). Formatting can also be set by traditional menu and dialog boxes.

Conditional Formatting This approach inherently allows for formatting characteristics to be embedded in a property's (or overridden cell's) formula. The most straightforward way to do this would be to use multiple statement formulas, separated by ";", but this might give more messy/programmer-looking formulas. An Example (setting both a property's formula and its border to blue for the 5th and succeeding rows) would be "=index*3-4; if (index>5) me.format.bordercolor=Blue" (aside: do we need a me variable that automatically refers to "the property of this currently being calculated"?). One could accomplish the familiar "draw me red if I'm a negative number" with the formula: if(me<0) me.format.fontColor=Red.(Note that this is better than "me<0? Red: Black" since this forces positive numbers to be black, overriding any higher-level formatting).

Unfortunately this formula driven approach is only useful by geeks; we'd still need menu-driven formatting to provide more user friendly access to this functionality. But maybe that's just the traditional formatting dialog box (accessed from a Format>Cell Properties menu selection) that includes a Condition: textbox. But how specify if only want some formatting to be conditional, or to use distinct conditions for two formatting attributes? Its makes for an interesting investigation into operational complexity and cognitive flow. Maybe its just not important enough to worry about too much.

The Formatting Container Should formatting information be properties of each individual object or cell, should there be Formatting objects that indirectly provide formatting (like a Style), or should there be formatting classes a la Cascading Style Sheets?

Explicit formatting objects seems more efficient and effective than creating object/property-specific formatting attributes, but it does abstract the process of assigning formatting. One approach would be to automatically create (or override) formatting objects as one changes a specific piece of formatting. It would be useful to have a named formats listbox that come up within a formatting dialog box. Named formats (like CSS styles) do not necessarily capture all formatting, just specific ones.

The advantage of CSS is that this stuff has already been thought through. Is CSS formatting at the different levels of objects and properties and individual cells consistent with both Javascript and the CSS standard? How incorporate conditional formatting?

Plotting A means of graphing data is similar to that in a traditional spreadsheet.

Enumerated Properties Enumerated properties (True/False, Yes/No, AA/A/B/C/D) are available. This is important since it would be useful to have radio buttons, check boxes and fixed and drop-down lists (or editable drop-down box) as a means of selection(see "Other Types", above). We break it down to the logical and the user-interface.

The logical challenge is to create a framework for easily defining and associating enumerated lists with a given property. This can be done consistent with Javascript's instant array definition (e.g. var USDAGrade=new Array("AA", "A", "B", "C", "D")). We would automatically define a middleman enumerated variable that we would use to access that particular property.

That leaves the question of how to dymanically extend the possibilities in a simple GUI. Can we make it straightforward to pop a set of gui widgets into a spreadsheet cell in response to a change in the property's "Display" field? Notionally, we should also compare existing Format fields to all others, and if this format exists already then just reference that (although that brings up the complexifying possibility of leaving it manual, define the array object separately, and just reference it in the class' Format field. Is it worth the extra step, or can we subsume both approaches (we could have a separate Enumerators object for the Page, which holds all these, and we can rename them and change them in a central location).

Row/Column Transposition The above discussion and example Objectsheets have treated objects in rows and properties in columns. By simple switch, they can be transposed, showing properties in rows and objects in columns. Since there is no explicit "row" and "column" notation for referencing, the logical and semantic structure remain intact; only the visual presentation changes. But some things need to be dealt with: preset row heights and column widths have little translatable meaning when transposed. Also, the analytical engine must (it seems) transpose all matrix-based referencing, which indeed can be interpreted as a row[]column[] format.


The Template

Hidden versus shown Properties By hiding properties in the Objectsheet, we also switch the processing burden from being per-object to being per-reference. The Objectsheet's analytical engine calculates the value of every "shown" property for every object in the object sheet every time the user changes the Objectsheet (as is the case with a traditional spreadsheet). For each hidden property, the analytical engine treats the formula more like a spreadsheet macro, calculating it only when called, or referred to by another cell. Again, unlike spreadsheet macros and formulas, this all occurs with the same syntax and in a single, unified environment.

This hidden/shown distinction can therefore be used not only to optimize the graphical layout of the problem, but can also tailor for efficient processing. More static formulas and more frequently referenced formulas lend themselves to being calculated once and displayed. More dynamic formulas that are not as frequently referenced lend themselves to be hidden

For instance, we can define a property isBathroom, returning true when the room's name contains "Bathroom", and false when it doesn't. We can use this to automatically count the number of bathrooms in our Objectsheet house.

Generalized Template Rows There is an alluring danger to adding lots of specialized Template rows for this and that purpose into the Objectsheet structure. Spreadsheet applications have tended to pile bandaids for accomodating additional functionality (like cell commenting, named cells, and the like) each one adding its own set of management rules to the spreadsheet.

There are probably many uses for user-defined information to be aligned with properties themselves. The Objectsheet approach is to consolidate the management of property-related information into a single data structure (i.e. the Template Row). While we must provide the functionality to manage Template rows (e.g. adding, deleting, moving, showing, referencing), it captures much of the functionality of working with Objectsheets in a single schema.

This must be done in a very robust very easy fashion, or else it will fail. And if it fails, it must not get in the way of anything whatsoever. that's why it can't be built on top of the foundation, but must be built into the foundation (and most preferably, not be separate at all, but just be an outcome of it).

How is this incorporated into the object model, and how might we formulaicly reference property-related information (like formula or formatting). Unfortunately, a property is not an object! (i.e. by which we can reference its .formula property). We could make each Template row its own object, each element referenced to the property name, viz, Rooms.formula.Area (or Rooms.formula["Area"]) returning the string "=length*width". Rooms.units.Area returns "Sq. m.".

Can we use this generalized Template row model to include a place for Class-level variable definitions? From the perspective of visual-logical mapping, this is quite consistent with the other uses of generic Template rows to form Class-level variables. For instance, we add a new Template row, give it the name "totalArea" and place a formula in the next-door cell. The variable can then be accessed via the completely consistent Rooms.totalArea.

The goal is for other (either hidden or class-level) properties to be shown and manipulated in a fashion completely consistent with instance properties. This appears to be a real challenge. There are discrepencies in the visual formatting (it seems useful to distinguish Template properties from instance property attributes) as well as having a place in the "Show..." button list, and to show both formula and value at the same time. Most importantly though, we may wish to modify characteristics of a Template-based property besides the formula (like Constraints or Access). One approach is shown below.

This approach is clean, but it requires explicitly declaring the added row to be a Template property as opposed to an new instance row. It also denies viewing both formula and value at the same time. (unless we provided a single vertical divider for a Template property-- one could move it to the left to see more of the resulting value (which is on the right), and move it more to the right to see more of the formula on the left.

Another, more logically consistent approach would be to append all Template-based properties to the right of the instance-based ones:

This allows all properties to be accessed through the same graphical as well as logical structure. Unfortunately, it is also very ugly, and would probably result in class-level variables being hidden most of the time.

One final approach is to completely separate all class-oriented definitions from instance-oriented ones; to place the green shaded rows in a completely separate window. These could possibly be automatically grouped upon creation. The difficulty is that it impacts the graphical coherence (i.e. as single unit, not grouped units) of the Objectsheet.

Property Names: Logical vs. Visual Objectsheet property naming adopts a name tag convention. For a simple entered name, like Master Bath, the Objectsheet engine automatically strips spaces and certain punctuation (leaving _, $, &, %, #), prepends '_' to any name starting with a digit, and capitalizes the first letters of all words (although this is a changeable option). To eliminate confusion of the resulting name, the row or column containing the logical names can be selectively shown.

Two methods provide for tailoring of the logical name independent of the visual name. The first is simply to modify the name directly in the shown row or column. The visual name will not be changed. The second method is shorthand. While enterineg the visual name, the user can prefix any word with '/1', '/2', etc. The Objectsheet engine will automatically extract the designated words, and provide the proper name.

For instance, entering 'pp of acid in gas' (pp=partial pressure) as a property will generate a logical name of ppOfAcidInGas (although the displayed, or visual name will be that originally entered). While ppOfAcidInGas is descriptive, it may be longer than desired. On the other hand, if the user enters a property name of '/1pp of /2acid in gas', the generated logical name will be 'ppAcid', while the displayed name will be the same as above. Again, this tagging method is merely a shortcut; the novice can always change the logical name directly. (and we might consider including a separate '/' before the end of a word, to abbreviate the word in between the '/1' and '/'.

Constraint and Type Checking

As a analytical model grows in complexity, the ability to provide consistency checking can be quite useful in maintaining the quality and integrity of the model. This is not possible in the typeless realm of the Spreadsheet, where there is no consistency checking beyond the trivial (for instance, parameters passed to functions and existance of references). Even though the values in Objectsheets are loosely typed, its structure enables us to explicitly check calculated values.

A row in the Template, called the Constraints row, serves to check the validity of a calculated or entered property value. A cell in the Constraints row can be given a logical expression (that is, an expression yielding a True/False result). That expression serves as a goodness test for an evaluated cell. If that expression evaluates to True, everything is ok. If False, and the cell is flagged with special (user-configurable) cell formatting. The Constraints formula can check the type (integer, text, etc.) of the value, it can confirm that a value is within a range, any test that returns a True/False result. If the field is left blank, no consistency checking is done.

We use the variable thisProperty as reference for a property, whatever it may be. As an example of such a test, the Constraint formula "(thisProperty>0)" only accepts positive numbers (that is, it flags zero and negative numbers, as well as nonnumeric values), (typeOf(thisProperty)==Date) ensures a Javascript Date object (which is part of Javascript's internal object structure), and (Range(thisProperty, -10,10)) highlights results that either nonnumeric, or are outside the indicated numeric range (Range(var,minValue,maxValue) returns True if var is between minValue and maxValue). There are also expressions to force a result to be within a specified list (see GUI Elements, following).

Alt Introduction: The Objectsheet does not explicitly type objects and their properties, and coerces compatibility where possible. Nevertheless, a form of type checking is provided via the Constraints row in the Template. That row defaults to void (no value), but can be overridden with either a primitive (int, float, or char), or object designation (Date, String, or an object existing within the Objectsheet).

The Constraint row can also be used to provide more general constraint checking: a numeric range, one value of a designated array (allowing use of a finite-state GUI element). In this case, type checking could be provided via the Javascript typeof(-) function. For whatever expression is used, a False result could cause that cell to be flagged (hilighted) in some (user-defined) fashion. Examples of constraints:

=Range(0,20) Explicit numeric range (eqv to: this.thisProperty>=0 && this.thisProperty<=20)
=typeOf(int)&& Range(-5,5) An integer between -5 and 5
=(thisProperty>prev.thisProperty) Ensures monotonically increasing values
=typeOf(String)&& !isNaN(thisProperty.substring(0,1)) Ensures a string that starts with a digit (regex:/\d.*/)
=(thisProperty!="" && isDefined(thisProperty)) ensures non-blank(? what parallel does Javascript have?) (regex:/.+/)

This is obviously most useful where manual entry of values is called for. But could there also be use with Template formulas to reduce the effects of improper coersion?

Is this the perfect place for regex's (at least for the power user?) It is in the latest version of Javascript.

Template Plugins

It seems possible that there may be other uses for "standard" Template rows that we haven't thought of. It might make sense to provide a low-level specification for handling the behavior of new Template rows, from within the calculating engine (as opposed to placing interpreted behavior explicitly in an Objectsheet). What other uses for Template rows might there be? If there is not a comelling reason for doing this, it could have an overall negative effect, by complexifying the Template with all sorts of add-ins.


Persistance

Persistance and file storage The seemingly obvious solution is XML-- the Objectsheet is a brand new capability implying a new data format- there's no reason not to follow the open-source XML model. We should be able to automatically generate Document Type Definitions (DTDs) on the fly(!?) when saving a file. But XML is really a data-only format; it doesn't inherently package behavior beyond the mere connotation of a DTD's tags. Can Javascript adequately represent the formulae and behavior and correctly handle specific overriden object properties? Can we store class and object state via XML and store its behavior via a generated Javascript source file (.js)? Theoretically, Javascript, which is non-persistant, would store an object's behavioral template, while the XML stores its state. But, I expect meshing two separate files adequately is either impossible or impracticably complex.

Or is the solution to simply capture both behavior and data within the XML model? An Objectsheet can be stored entirely in XML, applying new tags for possible method types, and all appearances of Javascript are simply contained within a <SCRIPT> tag.

One challenge is in representing raw formulas vs actual object data-- there are advantages to both. We certainly want to retain the formulaic representation for later use by the tool, but we would also like the formulas evaluated and the results stored to create an explicit dataset for export or long term storage. While all the infomation is there in the formulaic version to translate to the evaluated version, we can't guarantee that all other applications can make that translation.

Still, our goal is to have one and only one, file format suit both purposes. One approach is to screw that and provide a distinct export function, where only the data is stored, with the right wrappers to make the object structure explicit. Another approach is in the File > Save dialog (i.e. saving formulas and overriden data only), to provide an option to save the data along with the formula. This would be done in such a way as to allow the formulas to be transparent to an application that doesn't need it- it just gets the data.

Second, pure (data-only) XML files themselves should be importable/exportable, by loading and saving XML written with other people's DTDs. If the application can follow the logical structures permissible with XML, then it opens up a new interesting realm of embedding specific behavior within anyone's XML; a normal XML parser can just ignore the contents of the <SCRIPT> tag, and it's just like the original XML file.

Translating from heritage applications Is it possible to conceive of a set of rules to translate spreadsheet syntax to the Objectsheet? It seems feasible to call "constants" or class properties, that which has a label and a single entry, and to call "instance properties" that which has a label and a duplicated set of formulas (in some direction). Of course, a generally-applicable solution seems to require artificial intelligence, but if name references can be gotten in a somewhat relaible way, We can envision making those references relational (named), and preserving the logical structure (if not the visual structure) of the spreadsheet.

Maybe the solution is to default to standard property names when a unique name cannot be found (like when a formula has text both above and to its left), but to somehow store the local context around that formula, and prompt the user to give appropriately place and name the formula.


The GUI

Capturing class methods & properties and instance methods We provide a text area or a set of rows in the Template, where the user can enter methods and class properties to his/her whim. Code is explicitly and intuitively associated with the Class itself.

Showing/Hiding Objectsheet data There's a lot of data that can be shown/hidden in the Template: instance methods, property defaults, property formulae, property access, class methods and class properties, formatting (display font and cell embellishments-- borders and shading). A intuitive means of hiding or showing these per the user's whim will be a challenge-- the Show/Hide button in the Objectsheet's titlebar is one approach; alternatively, we could have small, clickable annunciators small, but visible section (kind of like a toolbar), whereby a single click would bring up that portion of the Template.

The "Show..." drop-down list on the title bar is anticipated to get lots of use, to manipulate the visual presentation of the Template. We would like to control the presentation order of the "Show..." list when clicked, to allow quick access to the most frequently toggled rows. One, possibly the last, item in the list box would be a row management dialog box. In that dialog box, there would be a listbox containing all possible template rows, including user-defined rows. A line within the listbox would divide all those rows visible in the drop down button from those not visible (or there could be two listboxes, with an ftp-like transfer GUI between them). Dragging row labels up and down within the listbox would change that order. On exiting the dialog and pressing the titlebar's "Show..." button, the rows would be shown in the order they appeared in the listbox.

Similarly there may well be times when the user wants to hide the instance portion of the sheet, either completely, or maybe to filter what is shown by some formula (e.g. this[selectedIndex].x>0). Maybe we can define an (otherwise hidden) object property called visible, defaulting to true, but overridable somewhere in the template. Is there a bare minimim set of lines that must be shown (like the classname line and the property name line?)

Dividing and Combining Portions of the Objectsheet One (possibly horrendously complexifying) need is for the user to split off subsets of objects, properties, or Template Rows, and recombine them at a later time. This is necessary to achieve some reasonable level of control over visual layout of the whole. We might like to:

Sorting object data In the property name bar, clicking on a property causes the objects in the Objectsheet to sort per that property. Default is to sort from highest to lowest; a second click on that property reverses the sort. Can this be done with a weakly typed language, where for instance, numbers can be overriden with text? Can the analytical engine intuit that a column holds date objects, and sort them accordingly?

Copying by Chunks Traditionally, copying is only done on a per-field basis. This is one area where a spreadsheet excells: the ability to manipulate information in chunks. Nearly all other GUIs (including Visio's approximation to the spreadsheet) only allow copying single literals at a time. This must be fixed! We need to be able to copy/move/delete entire objects at a time, or move columns (arrays, whose type is defined by the column's property) around. This needs to be worked out.

One issue that comes up is when an entire object is pasted into a new place. Does the Paste function place all values (thus overriding cells that would have otherwise been caluculated) or does it paste only the literally-entered values, and allow the formula ones to be calculated by the new sheet? This certainly seems to call for a "Paste as..." behavior, similar to that in existing spreadsheets. Also, should Paste

Other Data Types References to image files (GIF and JPG) as primitive types should be provided, to allow Objectsheet cells to contain them, either by reference or by displaying the actual image (under overrideable control). This reference/content display issue involves more than images: referenced objects, audio files, and generic XML content, for instance. Managing the presentation to the user in a simple way will be a significant challenge.

GUI Elements: Checkbox, Listbox, etc. Enumerated data structures are those that have a finite set of possible states. They include checkboxes, radio buttons, and the different types of list boxes. These elements can be called on to graphically represent the value of a cell. While not strictly enumerated lists, other "continuous" user interface elements, including scrollbars, spin buttons (i.e. text boxes plus up/down arrows), and the like, have a place in the Objectsheet.

An Objectsheet property's "Properties" dialog box contains a tab to enter these enumerated structures and specify a special user interface element. By entering a list of possible values or choosing an existing one, this logical and visual structure is set. The user interface element and the enumerated list is represented as an entry in the Constraints row of the Template.

While a graphical element can be selected to render a cell's possible and selected values, the graphical element is not required. The cell's data structure is of how it is rendered; either as traditional text-entry, or as graphical element.

These user interface elements can be placed in a spreadsheet. Unfortunately, this is done "on top of" the spreadsheet structure itself; the graphical element is placed. It must be individually configured, then linked to a spreadsheet cell. In the Objectsheet model, the graphical element becomes the cell; creating one is a single step process,

 

Commenting and Documenting

While traditional spreadsheets naturally allow for cell values to be used to comment a spreadsheet, these can serve to document the user interface, not the logical flow. Unfortunately, making room for this (as well as sub-headings and spaces for readability in tables) can destroy the clean, contiguous Cartesian of an array of replicated formulas. Doing so requires changes to those formulas to be replicated around those cells, making the spreadsheet more cumbersome to develop.

Alternatively, comments that don't use up cell space are possible in spreadsheets, but they use a different interface structure, and require additional learning. Objectsheets on the other hand, enable commenting and documenting a sheet a more structured fashion, without adding to the structure and complexity of the operating environment, and without impacting the logical flow of the model.

Comments are identified through the natural C commenting constructs, "//..." and "/* ... */". Comments may be appended to entered cell formulas or values, providing flags and documentation for the developer. Entire cells may also serve as comments; either by overriding a cell in the instance section, or in an otherwise unused Template cell. Finally, summary properties (taking up an entire Objectsheet row) can serve as comments.

By changing the format characteristics of the text within a comment, the cell or entire row may be formatted as a title or section subheading in an Objectsheet, as instructions to the user, or as more extensive documentation to the developer. By turning "word-wrap" on, a comment row can be expanded into an entire text area, providing more extensive description or notation within the Objectsheet. By selectively showing and hiding Objectsheet rows (as we might with a traditional spreadsheet), those comments can be designated for Objectsheet user or for developer.

Simply by introducing an already "standard" commenting approach into the existing Objectsheet structure, we have enabled advantages over documenting traditional spreadsheets. We have provided a way to title, document, and comment an Objectsheet, without affecting its analytical structure.

Comments -(secondary) Comments can be added to any item. If all computing is executed through a Javascript engine, then the common syntax for comments: "//..." and "/* ... */" can be embedded in procedural code, in property definitions, or appended to values within cells. It is conceivable that cell-based comments could be shown in colored text, within the cell, appended to the cell's calculated value.

If the first column of an object is a column, then the entire row is comment, and is not treated as an object within the Objectsheet. The row is skipped in the row indexing. This allows for space separators and title headings, without disturbing the flow of calculation. This is a signficant problem with existing spreadsheets.

A command can hide all comments, show all comments, or maybe there's an intermediate version. Our approach to comments covers both titling and actual comments. Is there a utility in distinguishing between comments for titling and comments for commenting. We could introduce the distinction of using /**...*/ or //* (for single line) to designate a titling comment (although this is contrary to the meaning of /** in Java, it may still be worthwhile here). Similiar to the spreadsheet prefixes to denote justification, we can set an internal "comment type" flag to "title", by selecting it via the menu system, or by simply using //* or /**...*/ when making comments for titling.

Contextual model of the page Can the page itself be viewed as a canvas, allowing the page itself to be addressed as a graphical context, or to create graphical contexts within, as Java allows. None of this is in Javascript, but it might be an interesting to fill out its featureset.

Blank Entries How identify blank entries vs "" entries? This is a problem in spreadsheets. It can affect calculations with no feedback to the user.

Methods and Events Simply presenting data in the Objectsheet context is a conceptual challenge for one with limited exposure to the object way of thinking (the author). The implications of adding Stimulus/Response Behavior is downright mind-boggling! How can formal methods be used in this environment?

Handling Attribute/Behavoir Exceptions Is there an advantage in not requiring each property to relate to all objects of a given class? Javascript allows single object properties. Accomodating exceptions (literal "exceptions", not programming "exceptions") to the rule is implemented poorly in almost all information systems. While there one can at least flag exceptions through a comments field or such, we cannot reflect it analytically. Spreadsheets can override an indivual member of a range of copied formula with a new one, but tracking that becomes a chore, and can be a source of spreadsheet bugs, when the exception (in the real world) happens to change or is removed. With single-object properties, we at least have a method of explicitly identifying those changes, and can call them all up (via a menu selection or something). The nature of the underlying object model means that the exceptions can be anything- a simple comment, replacing a literal value with a table lookup (with the table having scope of that object only), etc.

This can manifest how? >Display of the object-- user can define a scratch field and put whatever he/she wants for any object. >Storage of the object-- Just because something is necessary for a single object doesn't mean we should store a placeholder for every object. >Analysis-- It would certainly be a challenge to wend a

In-Place Typing vs Formula Bar Certainly the more direct, desirable method is edit in place. But, what are the rules for handling formulas that spread beyond the cell's boundaries? Are all cells editable (even titles and such)? if so, then we don't need to specially notify the user of editability (as we don't do on a spreadsheet).

Reports 2 options-- Would be nice to be able to generate HTML/XML content, based on a template generated by the user. While it wouldn't make a distributed web page "live" with data, it would provide a web-ready report of completed models. separating view (HTML content) from model (XML) content means that the original model is generic, where the same data can take on multiple views.

The second object is to generate HTML/XML content, but also embed necessary Javascript behaviors. Since Javascript is not persistent, adding behavior seems to have limited value. But (at least it seems that) you can capture it in web-capable content.

Visible Organization of Objects The object-oriented approach replaces divided areas on a spreadsheet and between sheet in a workbook with Objectsheets. A single Objectsheet represents a semantically coherent set of objects; the workspace is thus divided up per explicit semantics-- each Objectsheet has its own coherent meaning. This is a much more intuive organization than for spreadsheets. In fact, as good object-oriented programming environment forces the user to think in an object oriented fashion, so should the Objectsheet force the user to work around semantic building blocks, and not mix data of disparate meaning within it. The user cannot hide a constant off on the corner of an Objectsheet; it must be defined in the Objectsheet's class property area. It is argued that there is little or no loss of convenience or interactivity, since the class's property area is always just a click or two away.

One challenge with the Objectsheet approach is that the number of Objectsheets may indeed grow quickly inside a given application. It should (probably) therefore be important to provide a way to collapse object sheets in some larger class structure and possibly glue them together within the user interface. I'd like to keep these sheets next to each other- they are tightly bound logically, and when I want to see one of them, I'd like to see them all.


Power- vs Lay- User Considerations

One of the critical considerations in this whole concept is to decide whether to appeal to the programmer or the domain user. One goal is to attain that which (in my mind) only Hypercards has attained. Hypercards has a GUI to which the non-programmer can create reasonably sophisticated structures without ever requiring a line of programming. Yet for the programmer, access to the programming is a mere click away. Both the layperson and the programmer interact with the same basic structure- an elegant approach.


Scenarios

Multiple functions on a similar graph There are two approaches here. One is the simpler, where all plotted proerties exist on a single Objectsheet. That's straightforward. The challenge is when the proerties are on separate Objectsheets. How represent a consistent x-domain for all functions? That domain should be replicable in the Templates of other Objectsheets. This is done by defining the x-domain purely by formula (no overridden items in the Objectsheet-- or can/should we somehow inherit them, too?), and copying it by reference into new Objectsheets. Changing the original x-domain Objectsheet (i.e. the one that is referenced in other Objectsheets) then changes the x-domain in all referenced Objectsheets.