Skip to content

netless-io/netless-app

Repository files navigation

Netless App

Official Apps for the Agora Interactive Whiteboard.

Installation:

If you don't have pnpm installed:

npm i -g pnpm

Clone or fork this project, at project root run:

pnpm i
pnpm build-all

Environment

By default the playground demo uses a shared Agora Whiteboard account.

We recommend you use your own. Please register a new account and create a new env file packages/playground/.env.local. See packages/playground/.env.example for reference.

Development

pnpm dev

Create A New App

pnpm create-app

Useful Context APIs

Replayable Synced Storages

Storage that synced across clients. Operations on storages are kept which can be replayed.

// Create a storage under "counter" namespace with default value.
// You can create multiple storages under the same namespace.
// They will share the same synced storage.
const storage1 = context.createStorage("counter", { count: 1 });

// Access states
console.log(storage1.state.count); // 1

// Listen to state changes
const storage1StateListenerDisposer = storage1.on("stateChanged", diff => {
  if (diff.count) {
    console.log(diff.count.newValue, diff.count.oldValue);
  }
});

const sea = {
  a: 1,
  b: false,
};

// Only writable user can setState
if (context.isWritable) {
  // Similar to React setState, unchanged values will be filtered by a root-level shallow-compare.
  storage1.setState({
    count: 2,
    disabled: true,
    // Note that `setState` only performs root-level shallow-compare.
    // Object `sea` will be compared with `===`.
    // Keys of `sea` will not be compared!
    sea,
  });
}

// Remember to remove unused listener later
context.emitter.on("destroy", () => {
  storage1StateListenerDisposer();
});

context.emitter.on("destroy", () => {
  stateListenerDisposer();
});

Replayable Client Messaging

Messaging between clients. Note that client will also receive the message sent by itself.

const magixListenerDisposer = context.addMagixEventListener("ping", message => {
  console.log("Received Message", message);
});

if (context.isWritable) {
  context.dispatchMagixEvent("ping", 22);
}

context.emitter.on("destroy", () => {
  magixListenerDisposer();
});

License

The MIT license.