Git Product home page Git Product logo

ts-spreadsheet's Introduction

Spreadsheet app written in TypeScript

  1. Run the web service: To run ts-spreadsheet app locally, first clone the ts-spreadsheet-api repo and run it by calling npm run start.
  2. Then clone this repo and run it by calling npm run start.
  3. Open http://localhost:3000 in your browser.

Features

  • Flexible grid cells
responsive-design.mp4
  • Change spreadsheet name.
rename-spreadsheet.mp4
  • Copy/paste/cut one cell using keyboard or context menu
copy-paste-cut.mp4

Features using mouse

  • Single select cell and multi-select cells
single-and-multi-cell-select.mp4
  • Add/delete one column
add-and-delete-one-column.mp4
  • Add/delete multiple columns
add-and-delete-multiple-columns.mp4
  • Add/delete one row
add-delete-one-row.mp4
  • Add/delete multiple rows
add-delete-multiple-rows.mp4
  • Drag and drop one cell using mouse
drag-drop-one-cell.mp4
  • Drag and drop multiple cells using mouse
  • Undo/redo (version history)
  • Resize columns and rows
  • Freeze columns and rows
  • Sort columns
  • Add comments to cells. Comments are displayed in a tooltip when hovering over a cell. Add images to comments.
    • Option to edit comments in a modal dialog
    • Option to delete comment
    • Option to mark comment resolved.
    • Get link to this comment. Copy the link to clipboard.

Features using keyboard

  • Single select cell and multi-select cells
  • Keyboard navigation: move up, down, left, right
keyboard-navigation.mp4
  • Drag and drop one or more cells using keyboard
  • Undo/redo (version history)

Icons

๐Ÿ’ก React uses SVGR to convert svg icons to React components.

  1. Add svg icons to the src/assets/icons folder.

  2. Import icons as React components like this

    import { ReactComponent as IconAdd } from "../../assets/icons/add.svg";
  3. Use icons like this

    <IconAdd /> // Add any props like color, width, height, etc.

Change the color of an icon

Change the fill attribute of the SVG element to currentColor like this:

  <span className="search-icon">
    <svg viewBox="0 0 731 731" fill="none" xmlns="http://www.w3.org/2000/svg">
      <path
        d="M551.28 468C641.348 333.253 609.029 142.973 465.296 48.8133C354.932 -23.4053 207.576 -14.072 107.016 71.3293C-28.3176 186.36 -34.5043 390.409 88.5838 513.609C189.849 614.875 350.384 629.807 468.33 550.943L613.344 708.436C639.36 736.785 683.693 737.837 710.874 710.655C738.057 683.472 737.125 639.019 708.656 613.124L551.162 468.111L551.28 468ZM449.78 449.448C367.878 531.349 234.646 531.349 152.753 449.448C70.8518 367.547 70.8518 234.315 152.753 152.421C193.701 111.473 247.488 91.0573 301.273 91.0573C355.054 91.0573 408.841 111.588 449.793 152.421C531.694 234.323 531.694 367.555 449.793 449.448H449.78Z"
        fill="currentColor"
      />
    </svg>
 </span>

This allows us to style the icon with the color CSS property.

.search-icon {
  color: red;
}

Or we can use prop color and pass the color to the icon component.

  • Usage:
<IconAdd color="red" />

Change other props of the svg element (width, height, etc.)

๐Ÿ’ก Find other props you can add to the svg element: search interface SVGAttributes<T> in node_modules/@types/react/index.d.ts file.

Use the className prop to pass a class name to the svg element.

<IconAdd className="icon" />

Then use CSS to style the svg element.

.icon {
  width: 20px;
  height: 20px;
}

Selected and Focused cell

  • Selected and focused cell are two different things. They can be the same cell but they don't have to be.
  • Selected cell is the cell that is clicked on and there can be multiple selected cells at the same time.
  • Focused cell is the cell that is focused (by pressing Tab key or clicking on a cell). There can be only one focused cell. We use focused cell to select multiple cells by pressing Shift key and clicking on another cell.

Events and the order they get called

  • While holding down the mouse on a cell (onMouseDown), then move the cursor over the next cell, onMouseOver gets called on the currently hovered cell. When releasing the mouse button, onMouseUp gets called on the currently hovered cell:

    1. onMouseDown
    2. onMouseOver
    3. onMouseUp
    • Note: onClick event handler will not be called!!
    1. onDrag, onDragEnd, onDragEnter, onDragExit, onDragLeave, onDragOver, onDragStart, onDrop: These are HTML5 drag and drop events. They are not part of the normal mouse event flow and need to be triggered manually by calling event.dataTransfer.setData() in an onMouseDown or onDragStart event handler.
  • When holding down the mouse on a cell (onMouseDown), then releasing the mouse button over the same cell, the following event handlers get called:

    1. onMouseDown
    2. onMouseUp
    3. onClick

Select/multi-select cells

  • First we check direction: if the user selected a cell in the same row as selectionStartCell.rowIdx or cell in a row down from selectionStartCell.rowIdx. If yes, then in that row add all the columns from selectionStartCell.columnIdx to currentCell.columnIdx to selectedCells array.
  • If the user selected a cell in a row above selectionStartCell.rowIdx, then loop over all the rows from selectionStartCell.rowIdx to currentCell.rowIdx and add all the columns from selectionStartCell.columnIdx to currentCell.columnIdx to selectedCells array.

Selection data structure

interface SelectedCell {
  rowIdx: number | null;
  columnIdx: number | null;
}

interface SelectedCells {
  previousCell: SelectedCell;
  selectionStartCell: SelectedCell;
  selectionEndCell: SelectedCell;
  allSelectedCells: SelectedCell[];
}

Image description

Code style guide

  • Truth/falsy and control flow:
    • Arrays: always use myArray.length > 0 instead of myArray.length. This is more explicit and easier to read. Also don't use just myArray and expect it to return falsy if the array is empty. This is not true. An empty array is truthy in JavaScript (same as empty object).

ts-spreadsheet's People

Contributors

dependabot[bot] avatar nadiaidris avatar

Stargazers

 avatar  avatar

Watchers

 avatar

Forkers

superbahbi

ts-spreadsheet's Issues

BUG: update context menu component

If selectionStartCell row and column indices are larger than selectionEndCell row and/or column indices, then use selectionEndCell object to add rows above and columns to left.

Feature: Add copy, paste and cut options to context menu

Current behavior

There is no option to cut, copy, paste on context menu. If user selects text in a cell, they can use keyboard shortcut to copy, cut or paste text, but these options are not available on context menu.

Image

Desired behavior

When user selects text in a cell and right clicks on the cell to open the context menu, the user will see options to "Copy", "Cut", "Paste" the text content inside the cell.

Drag/drop: add nicer design when dragging cell

Is it possible to add rounded corners and make that gray border color appear more stylish. The cell also had 1px green border when dragging. Remove that?

simplescreenrecorder-2023-10-04_13.47.01.mp4

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.