def setup_file_association(force=False, silent=False):
    # Linux and OSX file associations are done together with desktop items
    if sys.platform != 'win32':
        return
    gmsh_bin = file_finder.path2bin('gmsh')
    extensions = ['.msh', '.geo', '.stl']
    associate = dict.fromkeys(extensions)
    for ext in extensions:
        if _is_associated(ext):
            if force:
                associate[ext] = True
            else:
                associate[ext] = _get_input(
                    f'Found other association for "{ext}" files, overwrite it?',
                    silent)
        else:
            associate[ext] = True
    # If all rejected, return
    if not any(associate.values()):
        return

    if sys.platform == 'win32':
        with winreg.OpenKey(winreg.HKEY_CURRENT_USER,
                            r'Software\Classes',
                            access=winreg.KEY_WRITE) as reg:
            winreg.CreateKey(
                reg, rf'SimNIBS.Gmsh.v{MINOR_VERSION}\shell\open\command')
            winreg.SetValue(
                reg, rf'SimNIBS.Gmsh.v{MINOR_VERSION}\shell\open\command',
                winreg.REG_SZ, f'"{gmsh_bin}" "%1"')
            for ext in extensions:
                try:
                    value = winreg.QueryValue(reg, ext)
                except FileNotFoundError:
                    register = True
                else:
                    if value:
                        register = _get_input(
                            f'Found other association for "{ext}" files, overwrite it?',
                            silent)
                    else:
                        register = True
                if register:
                    winreg.CreateKey(reg, ext)
                    winreg.SetValue(reg, ext, winreg.REG_SZ,
                                    fr'SimNIBS.Gmsh.v{MINOR_VERSION}')
Exemple #2
0
def setup_file_association(force=False, silent=False):
    # Linux and OSX file associations are done together with desktop items
    if sys.platform != 'win32':
        return
    gmsh_bin = file_finder.path2bin('gmsh')
    extensions = ['.msh', '.geo', '.stl']
    associate = dict.fromkeys(extensions)
    for ext in extensions:
        if _is_associated(ext):
            if force:
                associate[ext] = True
            else:
                associate[ext] = _get_input(
                    f'Found other association for "{ext}" files, overwrite it?',
                    silent)
        else:
            associate[ext] = True
    # If all rejected, return
    if not any(associate.values()):
        return

    if sys.platform == 'win32':
        # We need to run with admin privileges
        # So a write a .cmd script and run it with administrative privileges
        with tempfile.NamedTemporaryFile('w', delete=False,
                                         suffix='.cmd') as f:
            [
                f.write(f'call assoc {ext}=gmsh.simnibs\n')
                for ext, val in associate.items() if val
            ]
            f.write(f'call ftype gmsh.simnibs="{gmsh_bin}" "%1"')
            temp_fn = f.name
        # I need to run as admin for some reason
        # using a very ugly trick to get "%1" through
        # I have to use %1 as an argument so "%1" in the script becomes literal
        ret = subprocess.run(
            'powershell.exe -noprofile -executionpolicy bypass -Command '
            f'"Start-Process -Wait -WindowStyle Hidden -Verb RunAs -FilePath {temp_fn}"'
            f' -ArgumentList "%1"',
            shell=True)
        try:
            ret.check_returncode()
        except subprocess.CalledProcessError:
            print('Could not associate files')
        finally:
            os.remove(temp_fn)
Exemple #3
0
def copy_scripts(dest_dir):
    ''' Create scripts to call SimNIBS
    We need to write sh/cmd scripts due to the way python handles DLLs
    Additionaly, creates a 'simnibs' command in the matlab folder
    '''
    scripts = glob.glob(os.path.join(SIMNIBSDIR, 'cli', '[!_]*.py'))
    if not os.path.isdir(dest_dir):
        os.makedirs(dest_dir)
    # Create scripts
    for s in scripts:
        basename = os.path.splitext(os.path.basename(s))[0]
        if basename == 'run_simnibs':
            basename = 'simnibs'
        if basename == 'simnibs_gui':
            gui = True
        else:
            gui = False
        # Norma things
        bash_name = os.path.join(dest_dir, basename)

        # Special treatment to meshfix and gmsh
        if basename in ['meshfix', 'gmsh']:
            if sys.platform == 'win32':
                with open(bash_name + '.cmd', 'w') as f:
                    f.write("@echo off\n")
                    f.write(f'"{file_finder.path2bin(basename)}" %*')
            else:
                if os.path.lexists(bash_name):
                    os.remove(bash_name)
                os.symlink(file_finder.path2bin(basename), bash_name)
        # Other stuff
        else:
            if sys.platform == 'win32':
                _write_windows_cmd(s, bash_name, gui)
            else:
                _write_unix_sh(s, bash_name)

    # simnibs_python interpreter
    if sys.platform == 'win32':
        _write_windows_cmd(None, os.path.join(dest_dir, 'simnibs_python'))

    else:
        if os.path.lexists(os.path.join(dest_dir, 'simnibs_python')):
            os.remove(os.path.join(dest_dir, 'simnibs_python'))
        os.symlink(sys.executable, os.path.join(dest_dir, 'simnibs_python'))
def _create_apps(install_dir):
    """ Creates an apps for MacOS
    """

    plist = dict(CFBundleDisplayName="SimNIBS GUI",
                 CFBundleName="SimNIBS GUI",
                 CFBundleIdentifier="org.simnibs",
                 CFBundleShortVersionString=__version__,
                 CFBundleGetInfoString=f'SimNIBS GUI {__version__}',
                 CFBundleIconFile="gui_icon.icns",
                 CFBundleExecutable="simnibs_gui",
                 CFBundleInfoDictionaryVersion='6.0')
    _create_app(os.path.join(install_dir, 'SimNIBS GUI.app'),
                os.path.join(SIMNIBSDIR, 'cli', 'simnibs_gui.py'),
                os.path.join(SIMNIBSDIR, 'resources', 'gui_icon.icns'), plist)

    # Gmsh app setup
    target_dir = os.path.join(install_dir, 'Gmsh.app')
    if os.path.isdir(target_dir):
        shutil.rmtree(target_dir)
    print('Installing Gmsh')
    contents_dir = os.path.join(target_dir, 'Contents')
    resouces_dir = os.path.join(contents_dir, 'Resources')
    macos_dir = os.path.join(contents_dir, 'MacOS')
    os.mkdir(target_dir)
    os.mkdir(contents_dir)
    os.mkdir(resouces_dir)
    os.mkdir(macos_dir)

    _copy_and_log(os.path.join(SIMNIBSDIR, 'resources', 'gmsh', 'Info.plist'),
                  os.path.join(contents_dir))

    for icns in glob.glob(
            os.path.join(SIMNIBSDIR, 'resources', 'gmsh', '*.icns')):
        _copy_and_log(icns, resouces_dir)

    _copy_and_log(file_finder.path2bin('gmsh'), os.path.join(macos_dir))
def copy_scripts(dest_dir):
    ''' Create scripts to call SimNIBS
    We need to write sh/cmd scripts due to the way python handles DLLs
    Additionaly, creates a 'simnibs' command in the matlab folder
    '''
    # On windows, copy the sitecustomize script
    # in order to be able to use the python interpreter without activating the environment
    if sys.platform == 'win32':
        simnibs_sitecustomize = os.path.join(SIMNIBSDIR, 'utils',
                                             'sitecustomize.py')
        env_sitecustomize = os.path.join(os.path.dirname(sys.executable),
                                         'Lib', 'site-packages',
                                         'sitecustomize.py')
        write_sitecustomize = True
        with open(simnibs_sitecustomize, 'r') as f:
            simnibs_sitecustomize_contents = f.read()
        # Check if there is a sitecustomize file alread present and if it is identical ti the SimNIBS one
        if os.path.isfile(env_sitecustomize):
            with open(env_sitecustomize, 'r') as f:
                env_sitecustomize_contents = f.read()
            # If it's alteady there, will not append the PATH
            write_sitecustomize = not (simnibs_sitecustomize_contents
                                       in env_sitecustomize_contents)
        if write_sitecustomize:
            with open(env_sitecustomize, 'a') as f:
                f.write('\n')
                f.write(simnibs_sitecustomize_contents)
    scripts = glob.glob(os.path.join(SIMNIBSDIR, 'cli', '[!_]*.py'))
    if not os.path.isdir(dest_dir):
        os.makedirs(dest_dir)
    # Create scripts
    for s in scripts:
        basename = os.path.splitext(os.path.basename(s))[0]
        if basename == 'run_simnibs':
            basename = 'simnibs'
        if basename == 'simnibs_gui':
            gui = True
        else:
            gui = False
        # Norma things
        bash_name = os.path.join(dest_dir, basename)

        # Special treatment to meshfix and gmsh
        if basename in ['meshfix', 'gmsh']:
            if sys.platform == 'win32':
                with open(bash_name + '.cmd', 'w') as f:
                    f.write("@echo off\n")
                    f.write(f'"{file_finder.path2bin(basename)}" %*')
            else:
                if os.path.lexists(bash_name):
                    os.remove(bash_name)
                os.symlink(file_finder.path2bin(basename), bash_name)
        # Other stuff
        else:
            if sys.platform == 'win32':
                _write_windows_cmd(s, bash_name, gui)
            else:
                _write_unix_sh(s, bash_name)

    # simnibs_python interpreter
    if sys.platform == 'win32':
        _write_windows_cmd(None, os.path.join(dest_dir, 'simnibs_python'))

    else:
        if os.path.lexists(os.path.join(dest_dir, 'simnibs_python')):
            os.remove(os.path.join(dest_dir, 'simnibs_python'))
        os.symlink(sys.executable, os.path.join(dest_dir, 'simnibs_python'))
def setup_shortcut_icons(scripts_dir, force=False, silent=False):
    ''' Creates shortcut icons for the gui_scripts '''
    if sys.platform == 'darwin':
        _create_apps(os.path.abspath(os.path.join(scripts_dir, '..')))
        return
    elif sys.platform == 'win32':
        shortcut_folder = os.path.join(os.environ['APPDATA'], "Microsoft",
                                       "Windows", "Start Menu", "Programs",
                                       f"SimNIBS {MINOR_VERSION}")
        gmsh_icon = None
        simnibs_icon = os.path.join(SIMNIBSDIR, 'resources', 'gui_icon.ico')

    elif sys.platform == 'linux':
        shortcut_folder = os.path.expanduser(
            f'~/.local/share/applications/SimNIBS-{MINOR_VERSION}')
        gmsh_icon = os.path.join(SIMNIBSDIR, 'resources', 'gmsh', 'logo.png')
        simnibs_icon = os.path.join(SIMNIBSDIR, 'resources', 'gui_icon.png')

    if os.path.isdir(shortcut_folder):
        if force:
            overwrite = True
        else:
            overwrite = _get_input(
                'Found other SimNIBS menu icons, overwrite them?', silent)
        if not overwrite:
            print('Not adding shortucts to the current SimNIBS install')
            return

        else:
            shortcut_icons_clenup()

    os.makedirs(shortcut_folder, exist_ok=True)

    _create_shortcut(
        os.path.join(shortcut_folder, 'Gmsh'),
        file_finder.path2bin('gmsh'),
        'Gmsh is a free 3D finite element mesh generator with a built-in CAD engine and'
        ' post-processor',
        mime_type='model/x.stl-binary',
        icon=gmsh_icon)
    fn_gui_script = os.path.join(scripts_dir, 'simnibs_gui')
    if sys.platform == 'win32':
        fn_gui_script += '.cmd'
    _create_shortcut(
        os.path.join(shortcut_folder, 'SimNIBS GUI'),
        fn_gui_script,
        'SimNIBS is software for simulating electric fields caused by NIBS',
        icon=simnibs_icon)
    if sys.platform == 'win32':
        _create_shortcut(
            os.path.join(shortcut_folder, 'SimNIBS Directory'),
            os.path.abspath(os.path.join(scripts_dir, '..')),
        )
        _create_shortcut(
            os.path.join(shortcut_folder, 'SimNIBS Documentation'),
            os.path.abspath(
                os.path.join(scripts_dir, '..', 'documentation',
                             'index.html')),
        )
        _create_shortcut(
            os.path.join(shortcut_folder, 'SimNIBS Prompt'),
            r'%windir%\System32\cmd.exe',
            arguments=f'/K ""{_get_activate_bin()}"" {_get_conda_env()}')
    if sys.platform == 'linux':
        try:
            subprocess.run([
                'update-desktop-database',
                os.path.expanduser('~/.local/share/applications')
            ])
        except:
            print('Could not update desktop database')