Dynamic recursive treeview using nested-mat-tree by fetching data from rest api and json file alternatively

I’m trying to populate a dynamic treeview using nested-mat-tree.

The tree view alternates between fetching data from an API and displaying child nodes from a JSON file as you toggle through the levels. Here’s a recap:

First Level:
API Call: Fetch data from Spring Boot.
Display Data: Show fetched data.
Toggle: Reveals child nodes from a JSON file.

Next Level:
Toggle JSON Data: Triggers an API call with different end-point based on condition.
API Call: Fetch more data.
Display Data: Show the newly fetched api data.

Further Levels:
Toggle API Data: Displays child nodes from JSON again.
Repeat: This process continues indefinitely.
This ensures that the tree view dynamically switches between API calls and JSON data at each level of expansion.

Please provide if any reference for this case.

treeview.html

<div class="split-container">
  <div class="subpanel">
    <!-- Header for the Tree View section -->
    <div class="subpanel-header">Tree-View </div>
    <!-- Body of the Tree View section -->
    <div class="subpanel-body" id="subpanel-body">
      <!-- Angular Material Tree component -->
      <mat-tree [dataSource]="dataSource" [treeControl]="treeControl" class="example-tree">
        <!-- Tree node template for leaf nodes -->

        <!-- Tree node template for expandable nodes -->
        <mat-nested-tree-node *matTreeNodeDef="let node; when: hasChild">
          <div class="mat-tree-node">
            <button class="mat-icon-button-custom" (click)="onParentToggle(node)">
              <mat-icon>{{ treeControl.isExpanded(node) ? 'remove' : 'add' }}</mat-icon>
            </button>
            <button mat-button class="trail-button" (click)="attrVisualization(node)">
              {{ node.name.type?.toUpperCase().slice(0, 3) }}
            </button>
            <mat-icon class="status-icon" [ngStyle]="{'color': getIconColor(node)}">fiber_manual_record</mat-icon>
            {{node.name.name}}
          </div>
          <ul [class.example-tree-invisible]="!treeControl.isExpanded(node)">
            <ng-container matTreeNodeOutlet></ng-container>
          </ul>
        </mat-nested-tree-node>

        <!-- Tree node template for leaf nodes -->
        <mat-nested-tree-node *matTreeNodeDef="let node">
          <div class="mat-tree-node" (click)="onChildToggle(node)">
            <button class="mat-icon-button-custom">
              <mat-icon>{{ treeControl.isExpanded(node) ? 'remove' : 'add' }}</mat-icon>
            </button>
            {{node.name.name}}

            <ul [class.example-tree-invisible]="!treeControl.isExpanded(node)" *ngIf="node.children">
              <ng-container matTreeNodeOutlet>
                <ul *ngFor="let child of node.children">
                  <button class="mat-icon-button-custom" (click)="onChildToggle(child)">
                     <mat-icon>{{ treeControl.isExpanded(child) ? 'remove' : 'add' }}</mat-icon>
                   </button>
                 {{child.name.name}}
                </ul>
              </ng-container>
            </ul>
            
          </div>
        </mat-nested-tree-node>

      </mat-tree>
    </div>
  </div>

treeviewcomponent.ts

export interface TreeNode {
  name: {
    [key: string]: any;
  };
  children?: TreeNode[];
  parentId?: string; // Ensure parentId is defined in the interface
  parentDetails?: TreeNode;
}

@Component({
  selector: 'app-treeview',
  templateUrl: './treeview.component.html',
  styleUrls: ['./treeview.component.css']
})
export class TreeviewComponent implements OnInit {
  openTreeView = false;
  selectedNode: TreeNode | null = null;
  LocationData: any;
  treeChildren: any;
  apiData: any;

  treeControl = new NestedTreeControl<TreeNode>(node => node.children);
  dataSource = new MatTreeNestedDataSource<TreeNode>();

  constructor(
    private router: Router,
    private treeviewService: TreeviewService,
    private popUpService: PopUpServiceService,
    private http: HttpClient
  ) { }

  ngOnInit(): void {
    this.apiData = this.popUpService.getData(); //this is api data called to display top level nodes
    console.log('apiData Data:', this.apiData);

    this.apiData = JSON.parse(this.apiData);

    this.treeviewService.fetchJsonData().subscribe((jsonData: any) => {
      console.log('JSON Data:', jsonData[this.apiData[0].type]);

      const combinedData: TreeNode[] = this.apiData.map((item: any) => ({
        name: item,
        children: this.createTreeChildren(item.id, jsonData[this.apiData[0].type])
      }));

      this.dataSource.data = combinedData;
      console.log('DataSource:', this.dataSource.data);
    });
  }

  createTreeChildren(parentId: string, childrenData: any[]): TreeNode[] {
    return childrenData.map((child: string) => ({
      name: { name: child },
      parentId: parentId // Add parentId to each child node
    }));
  }

  hasChild = (_: number, node: TreeNode) => !!node.children && node.children.length > 0;


  onParentToggle(node: TreeNode): void {
    console.log("Toggling node:", node.name?.['id']);

    if (this.treeControl.isExpanded(node)) {
      this.treeControl.collapse(node);
    } else {
      this.treeControl.expand(node);
    }

    if (this.hasChild(0, node)) {
      this.assignParentToChildren(node);
    }
  }

  onChildToggle(node: TreeNode): void {
    console.log('Child Node parentType:', node);
    console.log('Child Node parentID:', node.parentId);
    console.log('Child Node name:', node.name['name']);

    if (this.treeControl.isExpanded(node)) {
      this.treeControl.collapse(node);
    } else {
      this.treeControl.expand(node);

      // Fetch sub-child nodes using childDetailapi
      this.treeviewService.childDetailapi(node.name['name'], node.parentId || '')
        .subscribe(response => {
          console.log('detail view Response:', response);

          // Create sub-child nodes
          const subChildren: TreeNode[] = response.map((subChild: any) => ({
            name: subChild,
            parentId: node.parentId,
          }));

          // Check if node already has children, if so, add the new ones
          if (node.children) {
            node.children.push(...subChildren);
          } else {
            node.children = subChildren;
          }

          // Refresh the data source to update the view
          this.dataSource.data = this.dataSource.data.slice();
        }, error => {
          console.error('API Error:', error);
        });
    }
  }


  findParentNode(childNode: TreeNode): TreeNode | null {
    for (const parentNode of this.dataSource.data) {
      if (parentNode.children && parentNode.children.some(child => child.name['name'] === childNode.name['name'])) {
        return parentNode;
      }
    }
    return null;
  }

  assignParentToChildren(parentNode: TreeNode): void {
    if (parentNode.children && parentNode.children.length > 0) {
      parentNode.children.forEach(childNode => {
        childNode.parentDetails = parentNode;
        this.assignParentToChildren(childNode);
      });
    }
  }

  getIconColor(node: any): string {
    switch (node.type) {
      case 'trail':
        return 'green';
      case 'port':
        return 'purple';
      case 'ne':
        return 'orange';
      default:
        return 'RGB(146,206,18)';
    }
  }
}
 

treeview service


@Injectable({
  providedIn: 'root'
})
export class TreeviewService {

   private jsonUrl = 'assets/properties.json';

  constructor(private http: HttpClient) { }

   fetchJsonData(): Observable<any> {
     return this.http.get<any>(this.jsonUrl);
   }


   childDetailapi(childType: string, parentId: string): Observable<any> {
    let apiUrl = '';

    switch (childType) {
      case 'Trail':
        apiUrl = `http://localhost:8080/pipe/locationId/${parentId}`;
        console.log(apiUrl);
        break;
      case 'Physical Device':
        apiUrl = `http://localhost:8080/physicalDevice/locationId/${parentId}`;
        
        console.log(apiUrl);
        break;
      case 'Leased Line':
        apiUrl = `http://localhost:8080/leasedLine/locationId/${parentId}`;
        
        console.log(apiUrl);
        break;
      default:
        throw new Error('Unknown child type');
    }

    return this.http.get(apiUrl);
  }
  

}

How do I get React CountUp to count from a previous number?

I am new to React and am using the React CountUp to animate a number counting up, eg:

<CountUp end={totalAmount} />

This works – whenever totalAmount is changed CountUp will animate a count from 0 to whatever the new number is.

However, I want to animate it to count from whatever the previous number was. For example if the totalAmount changes from 70 to 100 I want the animate just to count from 70. As it is now, whatever totalAmount changes to it will always start at 0.

I see there is an update prop available, but I am unsure how to use it. I have tried:

<CountUp end={totalAmount} update={totalAmount} />

I see there is a way to do this in a “hook”, but to be honest have no idea how to incporporate a hook into my broader React component.

Would anyone be able to point me in the right direction at all?

How to capture Tab + Escap key combinations in angular?

When the user pressed Tab + Escape key then I wanted to call my function but I couldn’t capture this combination. If this combination is not possible then I want one combination with Escape key but those combination are not used in Windows, Ubuntu and Mac.

I tried like this:

@HostListener('window:keydown', ['$event'])
async onkeyDown($event: KeyboardEvent) {
  if($event.key === 'Tab' && $event.code === 'Escape') {
    console.log('Tab + Escape keys pressed');  
  }
} 

I want to capture Tab + Escape key combination.

html and php load child select using parent select

i need some help in loading the child select based on the master select. Like i want to load the states based on the country select in the first place.

<div class="form-group">
<label for="customerID" class="col-sm-3 control-label">Customer</label>
<div class="col-sm-9">
<select class="form-control" name="countryName[]" id="countryrName">
<option value="">~~SELECT~~</option>
<?php
$countrySql = "SELECT * FROM countries WHERE transactionstatus='1' and companyid='1'";
$countryData = $connect->query($countrySql);

while($row = $countryData->fetch_array()) {                                            
echo "<option value='".$row['countryid']."' id='changeCustomer".$row['countryid']."'>".$row['countryname']."</option>";
} // /while 

?>

</select>
</div>
</div> <!--/form-group-->             
<div class="form-group">

Adding the highlightjs API interface to self in a web worker?

I’m coding a web worker in Typescript and this works:

onmessage = (e) => {
    importScripts(
      'https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.10.0/highlight.min.js'
    );
    const language = e.data.language;
    const result = language
      ? (self as any).hljs.highlightAuto(e.data.code, { language })
      : (self as any).hljs.highlightAuto(e.data.code);
    postMessage(result.value);
  };

I’m curious if there is a way to type self more strictly with the types from @types/highlightjs?

Why do most components – or even the browser – only offer to set the locale but not regional formatting?

In MacOS, Windows and Linux you can set your preferred language, e.g. en-US but also choose a region for formatting.

For example, I’ve set my MacOS to en-US but with German formatting.

In JavaScript there’s no possibility to get both OS settings.

  • navigator.language returns en-US.
  • Intl.DateTimeFormat().resolvedOptions().locale returns en-GB (for whatever reason? Chrome’s language setting is en-US)

I’ve also noticed that MacOS is doing it wrong. In its menu bar it currently shows “Wed Sep 4” which is not in German formatting. When changing the OS language to “en-GB” it changes to “Wed 4. Sep” – so it’s clearly using the language setting and not my regional preference for formatting. Also, shouldn’t it be Mi 4. Sept. which would be the real German formatting?

Now, when it comes to using components, most of them only offer a locale, so any formatting is derived from the language.

Why do most components (or even apps) not allow you to set preferences for formatting? Is it uncommon for most people to use a language with a different regional formatting?

Or is my understanding of how it should work wrong?

Wikipedia scrolls up on mouse text selection

When I try to select a word of text in the top 5% of the page in any English Wikipedia article (Example page) in Chrome, the page automatically starts scrolling up, even if the mouse pointer is far from the top edge of the page. How can I prevent this unwanted scrolling with user CSS/JS?

Trying to select "MA Cantab" on the page

Same behavior in Firefox and Safari. This doesn’t happen in other wikipedias, like German.

Redux project delete button isn’t working

I’m working on redux project that has add to card button and delete item from card. The delete button isn’t working and when I check with console.log it’s adding item to card. I’m trying to fix it but it’s not working.

I’m adding the code that I have below

import { createSlice } from "@reduxjs/toolkit";

export const slice = createSlice({
  name: "recipeCart",
  initialState: {
    itemsInCart: []
  },
  reducers: {
    addItemToCard: (state, action) => {
      const timeId = new Date().getTime()
      state.itemsInCart.push({
        idFood: timeId,
        dishId: action.payload.dish.idFood,
        quantity: action.payload.quantity,
        totalPrice: action.payload.quantity * action.payload.dish.price
      })
    },
    removeItemFromCart: (state, action) => {
      state.itemsInCart = state.itemsInCart.filter(
        itemsInCart => itemsInCart.idFood !== action.payload.itemsInCartId
      )
    }
  }
})

export const getTotalPrice = state => {
  return state.recipeCart.itemsInCart.reduce((total, itemsInCart) => {
    return itemsInCart.totalPrice + total
  }, 0)
}

export const getCartItems = state => state.recipeCart.itemsInCart;
export const { addItemToCard, removeItemFromCart } = slice.actions;
export default slice.reducer
import dishesData from "../data/dishesData";
import { removeItemFromCart } from "../redux/cartSliceFood.js";
import { useDispatch } from "react-redux";

const CartItemFood = ({ itemsInCart }) => {
  const recipeDishes = dishesData.find(
    item => item.idFood === itemsInCart.dishId
  )
  const dispatch = useDispatch();
  console.log(recipeDishes)
    
  return (
    <div>
      <div className="headerCart">
        <div className="container-cart"> 
          <p className="cartPar">{recipeDishes.name}</p>
          <p className="cartPar">{itemsInCart.quantity} portion(s)</p>
          <p className="cartPar price">
            Price: ${recipeDishes.price * itemsInCart.quantity}
          </p>
          <span
            onClick={() => dispatch(removeItemFromCart({
              itemsInCartId: itemsInCart.id
            }))}
          >
            <img
              className="icon cartPar"
              src="https://img.icons8.com/material-outlined/48/000000/trash--v1.png"
              alt="icon"
            /> 
          </span>
        </div>
      </div>
    </div>  
  )
}

export default CartItemFood;
import { configureStore } from '@reduxjs/toolkit';
import dishes from './DessertComponent/redux/dishesSlice';
import cart from './DessertComponent/redux/cartSlice';
import recipeDishes from './FoodComponent/redux/dishesSliceFood';
import recipeCart from './FoodComponent/redux/cartSliceFood'

export const store = configureStore({
  reducer: {
    dishes: dishes,
    cart: cart,
    recipeDishes: recipeDishes,
    recipeCart: recipeCart
  }
})

Trouble getting a value from a website using Google Apps Script and Regex

I’m trying to get the value of the current week from the ESPN NFL schedule (https://www.espn.com/nfl/schedule). Week 1 is in the center of the wrapper in the top half of the page. I’m using GAS since I’ve connected this to google sheets/google forms. I’ve been able to get the values in the tables (the schedule), but I can’t get this value from outside the tables.

I’ve found a regex expression that should find the value that I want. I tested it using regex101 here: https://regex101.com/r/xDJCXT/1

var url = 'https://www.espn.com/nfl/schedule';
var html2 = UrlFetchApp.fetch(url).getContentText();
var regex = /class=["']bcustom--week is-activeb.*?range["]>(.*?)<//gm;
var weekNum = html2.match(regex);
console.log(weekNum);

However, my code is outputting “null” in the console

javascript in Adobe Animate frames

To learn and experiment with JavaScript I am using the following approach/structure:
I have individual blocks of code in several individual frames, all of them in one Action named layer.
This way I can have only one Animate file to contain all my testing.

On frame One I have the following code:

this.stop()  //this is optional HERE
alert("Frame ONE")

//frame number to go to
    var myFrame = nn //(I replace nn with either 5, 10, 15, 20, 25 etc)
//5 10 15 etc are the frame numbers where I have JS code

myFrame -= 1     //create.js => frame number - 1
this.gotoAndPlay(myFrame);

When I run the above code (CTRL+Enter) with any valid nn value, a new tab is opened BUT the expected code does not execute.

I am getting these error msgs in Chrome:

Uncaught SyntaxError: Unexpected token ‘)’ SandBoxt.js:3520
and
Uncaught ReferenceError: AdobeAn is not defined SandBoxt.html?10700:24
at init (SandBoxt.html?10700:24:11)
at onload (SandBoxt.html?10700:48:44)

My impression is that all (my currently fifteen blocks of) code in individual frames are checked regardless of which individual block I am trying to excute.
Nowhere do I have a 3520 line number. (This is, I guess, a cumulative line count).

I would like to hear from you people a suggestion on a clever/efficient way to find the offending line.
Thank you all very much in advance.

I am trying to comment each entire code in frame one by one but I still could not find the error.

How to click an element without navigating away from the page

I would like to ask whether it is there a way for you to select an element without going to be navigate away,

I am new to coding , I trying to automate the unfollowing button. in instagram

unfolllow

let say I wanted to unfollow all by dbclick the “following” , can I just run my code on homepage URL?

https://www.instagram.com/_chaeboll/ — home page url
https://www.instagram.com/_chaeboll/following/ — after clicking following

const unfollow = document.querySelectorAll("following")

unfollow.forEach(() => { runing the code to click the button})
  • as the element isnt in home page , it will returned undefined, but i hope there is away when something happen in background which navigate away to the following URL and execute the code.

I know u can use the deobfuscate/debuggger to find the function which are called to do the action, but it is to advance for me to find the function

Im building it as extension in content.js

if there is isnt , is there any resources that teaches the process of automating things for me to learn more about finding the way to deobfuscate

Cross reference Language injected javascript in jetbrains

The current IDE i am using is Rider (ASP.NET Core C#)

How can i resolve these warnings for unidentified javascript functions/classes/members if they are declared in language injected variables?

The same issue occurs in PHPStorm, and I assume it happens in pycharm as well.

public abstract class SelectorScript
{
    public static GlobalDefinition chooseProduct { get; } = new();

    public static ScriptFile File()
    {
        return new ScriptFile(
            /* lang=javascript */
            $$"""
              
                /**
                 * @param {string|Node|$Selector|Window} selector - element or selector
                 * @param {Document|Node} [baseElement] - base element
                 * @returns $Selector
                 */
                $S = (selector, baseElement = document) => {
                    return (new $Selector).$set(selector, baseElement);
                }
          """);
    }
}
    

Code Screenshot
enter image description here

Warning Shown
Warning Shown

Firebase signInWithEmailAndPassword lag

I am doing this:

    signInWithEmailAndPassword(auth, email, password).then(() => {
        navigate('/')
    }).catch((error) => {

On my routes page, I am doing this:

function LandingPageRedirect({ children }) {
    if (loading) {
        return <div>Loading...</div>; // Or a spinner/loader
    }
    if (user) {
        return <>{children}</>
    } else {
        return (
            <Navigate
            to="/landing"
            state={{
                from: location.pathname,
            }}
            replace
            />
        )
    }
}

return (
    <div>
        <BrowserRouter>
            <Routes>
                <Route path='/' element={
                        <LandingPageRedirect>
                            <Home />
                        </LandingPageRedirect>
                    } 
                />

However, after sign in I am being sent back to”/landing” rather than “/home”. How do I fix this?

Why Email not being sent with NextJS server actions with Resend.com?

I have a NextJS 13.5.1 and have enabled server actions, project where I try to submit a form that should send an email using server actions and resend. I have copy and pasted a curl snippet which worked and had sent the email, but it doesn’t work in the app.

packages/landing/src/containers/AgencyFormal/ContactUs/index.js

import React, { useState } from 'react';
import {
  Container,
  FormWrapper,
  Heading,
  Form,
  Row,
  FormField,
  RequiredLabel,
  Input,
  Button,
  Label,
  Textarea,
} from "./contactUs.style";
import { sendEmail } from '@/../actions/sendEmail';

const ContactUs = () => {
  const [name, setName] = useState('');
  const [email, setEmail] = useState('');
  const [message, setMessage] = useState('');
  const [isLoading, setIsLoading] = useState(false);
  const [status, setStatus] = useState(null);

  const onSubmit = async (e) => {
    e.preventDefault();
    setIsLoading(true);
    const result = await sendEmail({ name, email, message });
    console.log("Sending...")

    if (result.success) {
      console.log("Success")
      setStatus('Email sent successfully!');
      setName('');
      setEmail('');
      setMessage('');
    } else {
      setStatus(result.error);
    }
    setIsLoading(false);
  };

  return (
    <Container>
      <Heading>Connect with Our Team of Experts</Heading>
      <FormWrapper>
        <Form onSubmit={onSubmit}>
          <Row>
            <FormField>
              <RequiredLabel htmlFor="name">Full Name</RequiredLabel>
              <Input
                type="text"
                id="name"
                name="name"
                placeholder="John Doe"
                onChange={(e) => setName(e.target.value)}
                value={name}
                required
              />
            </FormField>
            <FormField>
              <RequiredLabel htmlFor="email">Email</RequiredLabel>
              <Input
                type="email"
                id="email"
                name="email"
                placeholder="[email protected]"
                onChange={(e) => setEmail(e.target.value)}
                value={email}
                required
              />
            </FormField>
          </Row>
          <Row>
            <FormField>
              <RequiredLabel htmlFor="phone">Phone</RequiredLabel>
              <Input
                type="tel"
                id="phone"
                name="phone"
                placeholder="+1 555 123 4567"
                required
              />
            </FormField>
            <FormField>
              <Label htmlFor="website">Website</Label>
              <Input
                type="text"
                id="website"
                name="website"
                placeholder="yourwebsite.com"
              />
            </FormField>
          </Row>
          <FormField>
            <RequiredLabel htmlFor="message">Message</RequiredLabel>
            <Textarea
              id="message"
              name="message"
              placeholder="How can I help you?"
              onChange={(e) => setMessage(e.target.value)}
              value={message}
              required
            />
          </FormField>
          <Button type="submit" disabled={isLoading}>
            {isLoading ? 'Sending...' : 'Submit'}
          </Button>
          {status && <p>{status}</p>}
        </Form>
      </FormWrapper>
    </Container>
  );
};

export default ContactUs;

packages/landing/src/actions/sendEmail.js

import { Resend } from 'resend';


export async function sendEmail(data) {
  'use server';
  const { name, email, message } = data;
  const resend = new Resend(process.env.RESEND_KEY);

  try {
    await resend.emails.send({
      from: "[email protected]",
      to: ['[email protected]'],
      subject: 'Contact form submission',
      text: "This is website",
    });
    console.log("try")
    return { success: true };
  } catch (error) {
    console.error('Error sending email:', error);
    return { error: 'Failed to send email' };
  }
}