<commit_before>import {Now} from "hareactive/Now";
import {Stream, empty} from "hareactive/Stream";
import {Behavior, sink, subscribe, isBehavior} from "hareactive/Behavior";
import {Component, runComponentNow} from "./component";
import {CSSStyleType} from "./CSSStyleType";

export type Showable = string | number;

type StreamDescription<A> = [string, string, (evt: any) => A]
type BehaviorDescription<A> = [string, string, (evt: any) => A, A];

type Properties = {
  streams?: StreamDescription<any>[],
  behaviors?: BehaviorDescription<any>[],
  style?: CSSStyleType,
  attribute?: {
    [name: string]: string | Behavior<string>;
  }
};

type Children = Component<any> | string;

function isChildren(a: any): a is Component<any>{
  return a instanceof Component || typeof a === "string";
}

class CreateDomNow<A> extends Now<A> {
  constructor(
    private parent: Node,
    private tagName: string,
    private props?: Properties,
    private children?: Children
  ) { super(); };
  run(): A {
    let output: any = {};

    const parsedTag = this.tagName.match(/[.#]?\w+/g);
    const elm = document.createElement(parsedTag[0]);
    for (let i = 1; i < parsedTag.length; i++) {
      let classOrId = parsedTag[i];
      let name = classOrId.substring(1, classOrId.length);
      if (classOrId[0] === "#") {
        elm.setAttribute("id", name);
      } else if (classOrId[0] === ".") {
        elm.classList.add(name);
      }
    }

    if (this.props !== undefined) {
      if (this.props.style !== undefined) {
        for (const styleProp in this.props.style) {
          const value = (<any>this).props.style[styleProp];
          if (isBehavior(value)) {
            value.subscribe((newValue) => (<any>elm.style)[styleProp] = newValue);
          } else {
            (<any>elm.style)[styleProp] = value;
          }
        }
      }

      if (this.props.attribute !== undefined) {
        for (const name in this.props.attribute) {
          const value = this.props.attribute[name];
          if (isBehavior(value)) {
            value.subscribe((newValue) => elm.setAttribute(name, newValue));
          } else {
            elm.setAttribute(name, value);
          }
        }
      }

      if (this.props.behaviors !== undefined) {
        for (const [evt, name, extractor, initial] of this.props.behaviors) {
          output[name] = behaviorFromEvent(evt, initial, extractor, elm);
        }
      }<commit_msg>added a way to put props on an element in Dom-builder.<commit_after>import {Now} from "hareactive/Now";
import {Stream, empty} from "hareactive/Stream";
import {Behavior, sink, subscribe, isBehavior} from "hareactive/Behavior";
import {Component, runComponentNow} from "./component";
import {CSSStyleType} from "./CSSStyleType";

export type Showable = string | number;

type StreamDescription<A> = [string, string, (evt: any) => A]
type BehaviorDescription<A> = [string, string, (evt: any) => A, A];

type Properties = {
  streams?: StreamDescription<any>[],
  behaviors?: BehaviorDescription<any>[],
  style?: CSSStyleType,
  props?: {
    [name: string]: string | Behavior<string>;
  }
  attribute?: {
    [name: string]: string | Behavior<string>;
  }
};

type Children = Component<any> | string;

function isChildren(a: any): a is Component<any>{
  return a instanceof Component || typeof a === "string";
}

class CreateDomNow<A> extends Now<A> {
  constructor(
    private parent: Node,
    private tagName: string,
    private props?: Properties,
    private children?: Children
  ) { super(); };
  run(): A {
    let output: any = {};

    const parsedTag = this.tagName.match(/[.#]?\w+/g);
    const elm = document.createElement(parsedTag[0]);
    for (let i = 1; i < parsedTag.length; i++) {
      let classOrId = parsedTag[i];
      let name = classOrId.substring(1, classOrId.length);
      if (classOrId[0] === "#") {
        elm.setAttribute("id", name);
      } else if (classOrId[0] === ".") {
        elm.classList.add(name);
      }
    }

    if (this.props !== undefined) {
      if (this.props.style !== undefined) {
        for (const styleProp in this.props.style) {
          const value = (<any>this).props.style[styleProp];
          if (isBehavior(value)) {
            value.subscribe((newValue) => (<any>elm.style)[styleProp] = newValue);
          } else {
            (<any>elm.style)[styleProp] = value;
          }
        }
      }

      if (this.props.attribute !== undefined) {
        for (const name in this.props.attribute) {
          const value = this.props.attribute[name];
          if (isBehavior(value)) {
            value.subscribe((newValue) => elm.setAttribute(name, newValue));
          } else {
            elm.setAttribute(name, value);
          }
        }
      }

      if (this.props.props !== undefined) {
        for (const name in this.props.props) {
          const value = this.props.props[name];
          if (isBehavior(value)) {
            value.subscribe((newValue) => (<any>elm)[name] = newValue);
          } else {
            (<any>elm)[name] = value;
          }
        }
      }

      if (this.props.behaviors !== undefined) {
        for (const [evt, name, extractor, initial] of this.props.behaviors) {
          output[name] = behaviorFromEvent(evt, initial, extractor, elm);
        }
      }
{'fraction_non_alphanumeric': 0.15329566854990584, 'fraction_numerical': 0.0018832391713747645, 'mean_word_length': 2.69589422407794, 'pattern_counts': {'":': 0, '<': 32, '<?xml version=': 0, '>': 39, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4849034', 'n_tokens_mistral': 1625, 'n_tokens_neox': 1611, 'n_words': 400}