iTwin / appui

Monorepo for iTwin.js AppUi
MIT License
9 stars 2 forks source link

Unable to load SVG file if IconSpec created using IconSpecUtilities.createWebComponentIconSpec #421

Closed ShoaibEhsan1 closed 1 year ago

ShoaibEhsan1 commented 1 year ago

Describe the bug Unable to load svg icon from the file using the IconSpecUtilities.createWebComponentIconSpec and ToolbarItemUtilities.createActionItem

To Reproduce Steps to reproduce the behavior:

  1. Import SVG as import Exportsvg from "./assets/minimize.svg"
  2. Create a Tool class as below and create iconSpec using the imported svg above export class ExportTextTool extends Tool { public static override iconSpec = IconSpecUtilities.createWebComponentIconSpec(Exportsvg);

    public static override toolId = "ExportTextTool"; // public static override iconSpec = "icon-info"; public static override namespace = "MyExportTextToolNamespace"; public override async run(): Promise { const imodel = UiFramework.getIModelConnection(); if (!imodel) throw Error("export button loaded but no iModel connection found!"); UiFramework.dialogs.modal.open(); return super.run(); } }

  3. Create a ToolbarItem as const toolbarItem = ToolbarItemUtilities.createActionItem( ExportTextTool.toolId, 0, ExportTextTool.iconSpec, ExportTextTool.description, async () => { await IModelApp.tools.run(ExportTextTool.toolId); } );
  4. The new tool is loaded in the viewer but instead of icon, some weird text appears (see image)
  5. The weird text can be different for different svg

Expected behavior Image in the SVG should be shown

Screenshots If applicable, add screenshots to help explain your problem.

Desktop (please complete the applicable information):

NancyMcCallB commented 1 year ago

Hi, I emailed to let you know that I can't reproduce this problem in our test app and asking for a link to the code that exhibits the problem. Can you help?

ShoaibEhsan1 commented 1 year ago

Sent the email with the files that reproduce the issue.

kckst8 commented 1 year ago

@raplemie any updates on this?

raplemie commented 1 year ago

Nope, sadly investigation will need to be picked up by someone else.

raplemie commented 1 year ago

From the description given in #521, the svg you are using are not loaded with svg-loader, which is what this method is describing to support: https://github.com/iTwin/itwinjs-core/blob/21becd3c475d9fa7ff208aec36fc373b2018d015/ui/appui-abstract/src/appui-abstract/utils/IconSpecUtilities.ts#L24-L29

raplemie commented 1 year ago

Apparently, the expected input is a string, which is not what svg-loader returns, so this documentation is wrong, I'll look at fixing it to clarify what the string should return, turns out that it support base64 svg+xml data url, or simple urls. the information given in 521 indicate that you are simply using direct import (not base 64, so one short term solution would be to do something like this to convert the import (not tested)

function toDataBase64(dataRaw: string) {
  const dataParts = dataRaw.split(",");
  const b64 = btoa(dataParts[1]);
  return `${dataParts[0]};base64,${b64}`;
}

I'll look to incorporate this variant of the data url support if we can validate that this is indeed the issue you are having.

raplemie commented 1 year ago

Hi @ShoaibEhsan1, @kckst8, a fix for this have been released in 4.6.2, data:image/svg+xml uri are now supported by the Icon component, let us know if this fixes your issue!