如何在 wine 中安装 python3?

如何在 wine 中安装 python3?

我们如何在 32 位 ubuntu 的 wine 中安装 python3?

可以使用winetricks python2.7,但我的应用程序是用 python3 编写的

我没有窗口来测试我的应用程序,所以我只能走这条艰难的路

答案1

Python 3.7 现在可以在较新版本的 wine 中运行。 此用户使用 wine 4.14 安装 python 3.7.4,目前我在 wine 5.0-rc3 中使用 Python 3.7.6。我可以运行pyinstaller交叉编译,并且可以在 wine 中毫无问题地测试生成的 exe 包和我的源代码。我正在测试的应用程序有一个基于 PyQt5 的 GUI。

我首先尝试了 @Hibou57 的方法,使用嵌入式 Python,它不需要较新的 Wine 版本。虽然这种方法适用于最小的 Python 安装,但后来我遇到了很多恼人的问题,需要进行一些破解。当我无法弄清楚如何numpy在 Wine 中安装嵌入式 Python 时,我放弃了这种方法。

要在 wine 中安装 Python 3.7.6:

  1. 添加官方葡萄酒储藏室获取apt最新的开发版本
  2. 安装 wine 的开发者版本sudo apt install winehq-devel
  3. 只需在 wine 中下载并运行 Python 3.7.6 exe 安装文件wine cmd /c python-3.7.6.exe

下面的脚本是我用来在 docker 容器内安装 python 3.7.6 以使用 Ubuntu 18.04 映像进行交叉编译的脚本。我还使用了 64 位 wine 前缀。请注意,此脚本的某些部分处理特定于 docker 的问题。

#!/bin/bash

set -e

echo "---------------------------------"
echo "-------- setup wine prefix ------"
echo "---------------------------------"
# We need the developer version of wine.  We need at least version 4.14 (see link).
# This is the earliest version I've seen reported to work with python3 well
# Without this, we'd have to run the embedded install of python which is riddled
# with annoying issues.

# see: https://appdb.winehq.org/objectManager.php?sClass=version&iId=38187

echo "------ Installing required apt packages ------"
apt update
apt install -y wget gnupg software-properties-common apt-utils

echo "------ Add latest wine repo ------"
# Need at least wine 4.14 to install python 3.7
dpkg --add-architecture i386
wget -nc https://dl.winehq.org/wine-builds/winehq.key
apt-key add winehq.key
apt-add-repository 'deb https://dl.winehq.org/wine-builds/ubuntu/ bionic main'
apt update

# Add repo for faudio package.  Required for winedev
add-apt-repository -y ppa:cybermax-dexter/sdl2-backport

echo "-------- Install wine-dev ------"

apt install -y \
    winehq-devel \
    winetricks \
    xvfb        # This is for making a dummy X server disply 

echo "------ Download python ------"
wget https://www.python.org/ftp/python/3.7.6/python-3.7.6-amd64.exe
#wget https://www.python.org/ftp/python/3.7.6/python-3.7.6.exe

echo "------ Init wine prefix ------"
WINEPREFIX=~/.wine64 WINARCH=win64 winetricks \
    corefonts \
    win10

# Setup dummy screen
Xvfb :0 -screen 0 1024x768x16 &
jid=$!

echo "------ Install python ------"
DISPLAY=:0.0 WINEPREFIX=~/.wine64 wine cmd /c \
    python-3.7.6-amd64.exe \
    /quiet \
    PrependPath=1 \
    && echo "Python Installation complete!"
# Display=:0.0 redirects wine graphical output to the dummy display.  
# This is to avoid docker errors as the python installer requires a display, 
# even when quiet install is specified.

答案2

我有一个类似的问题:我必须在 Ubuntu 上开发一个 Python3 应用程序,该应用程序将在 Windows 上交付。我想使用py安装程序从 Wine 生成 Windows 可执行文件,因为不幸的是我无法访问 Windows 机器。但我也无法在 Wine 上安装 Python3。

但是,可能还有另一种选择:使用所谓的可嵌入 Python 的 zip 存档。请参见此处:3.8. 嵌入式分布(docs.python.org)

您可以从版本下载页面下载它,如下所示(示例): Python 3.5.2(python.org)

你有两个:

  • Windows x86-64 可嵌入 zip 文件
  • Windows x86 可嵌入 zip 文件

这意味着您必须询问客户端他/她正在运行的是 32 位还是 64 位 Windows。

那是不是完美,因为如果 Python3 无法在 Wine 中运行,就无法测试应用程序的 Windows 版本。但至少,这是一种打包应该在 Windows 上运行的东西的方法,希望源代码在 Windows 上的行为与在 Ubuntu 上的行为相同。至少,你应该在 Ubuntu 端使用 Python 虚拟环境进行开发。参见28.3. venv — 创建虚拟环境

答案3

实际上你可以在 wine 上使用 python3:

基本上,您需要做的就是在 Windows 机器上安装 python3(仅供您使用,不适用于所有用户),然后将整个目录复制到 wine 机器上。

或者您可以从 Python 下载发布下载页面,正如 Hibou57 的帖子中提到的

然后在 wine 注册表中添加以下路径:“c:\python37;C:\python37\Scripts;...” 一切正常。

我提供了一些方便的脚本在 Github 上为 Ubuntu 自动执行此操作

但是,您需要首先决定是否要安装 WINE STABLE、WINE DEVELOP 还是 WINE STAGING(我建议安装 WINE DEVELOP)。

然后,您需要决定采用哪种架构(32 位或 64 位 Wine),然后在此基础上,您可以按照前面的说明通过复制来安装 32 位或 64 位 Python 2.7 或 Python 3.7。

整个过程有点冗长,您需要安装很多细节,这里是脚本:

#!/bin/bash
# ../home/install_wine.sh

function include_dependencies {
    local my_dir="$( cd "$(dirname "${BASH_SOURCE[0]}")" ; pwd -P )"  # this gives the full path, even for sourced scripts
    chmod +x "${my_dir}/lib_bash/*.sh"
    source "${my_dir}/lib_bash/lib_color.sh"
    source "${my_dir}/lib_bash/lib_retry.sh"
    source "${my_dir}/lib_bash/lib_wine_install.sh"
}

include_dependencies  # me need to do that via a function to have local scope of my_dir




clr_bold clr_green "Install WINE"
check_wine_version

clr_green "add 386 Architecture"
retry sudo dpkg --add-architecture i386
clr_green "add Wine Keys"
retry wget https://dl.winehq.org/wine-builds/winehq.key
sudo apt-key add winehq.key
sudo apt-add-repository 'deb https://dl.winehq.org/wine-builds/ubuntu/ xenial main'
clr_green "Wine Packages Update"
retry sudo apt-get update
clr_green "Wine Packages Install"
retry sudo apt-get install --install-recommends winehq-${wine_version}
retry sudo apt-get install -y cabextract
retry sudo apt-get install -y libxml2
retry sudo apt-get install -y libpng-dev

clr_green "Install latest Winetricks"
sudo rm -f /usr/bin/winetricks
retry sudo wget --directory-prefix=/usr/bin/ https://raw.githubusercontent.com/Winetricks/winetricks/master/src/winetricks
sudo chmod +x /usr/bin/winetricks
retry sudo winetricks -q --self-update
clr_green "Install latest Winetricks - done"

clr_green "done"
clr_green "******************************************************************************************************************"
clr_bold clr_green "FINISHED installing WINE and WINETRICKS"
clr_green "******************************************************************************************************************"

#!/bin/bash
# ../home/install_wine_machine.sh

function include_dependencies {
    local my_dir="$( cd "$(dirname "${BASH_SOURCE[0]}")" ; pwd -P )"  # this gives the full path, even for sourced scripts
    chmod +x "${my_dir}/lib_bash/*.sh"
    source "${my_dir}/lib_bash/lib_color.sh"
    source "${my_dir}/lib_bash/lib_retry.sh"
    source "${my_dir}/lib_bash/lib_wine_install.sh"
}

include_dependencies  # me need to do that via a function to have local scope of my_dir

clr_bold clr_green "Install Wine Machine"
check_wine_prefix
check_wine_arch
check_wine_windows_version
check_headless_xvfb

clr_green "Setup Wine Machine at ${WINEPREFIX}, WINEARCH=${WINEARCH}, wine_windows_version=${wine_windows_version}"
mkdir -p ${WINEPREFIX}
wine_drive_c_dir=${WINEPREFIX}/drive_c
# xvfb-run --auto-servernum winecfg # fails marshal_object couldnt get IPSFactory buffer for interface ...

if [[ ${xvfb_framebuffer_service_active} == "True" ]]; then sudo service xvfb stop ; fi   # winecfg fails if xvfb server is running
winecfg
if [[ ${xvfb_framebuffer_service_active} == "True" ]]; then sudo service xvfb start ; fi     # winecfg fails if xvfb server is running

echo "Disable GUI Crash Dialogs"
winetricks nocrashdialog

echo "Set Windows Version to ${wine_windows_version}"
winetricks -q ${wine_windows_version}

echo "Install common Packets"

retry winetricks -q windowscodecs
retry winetricks -q msxml3

clr_green "done"
clr_green "******************************************************************************************************************"
clr_bold clr_green "FINISHED installing Wine Machine ${WINEPREFIX}"
clr_green "******************************************************************************************************************"

#!/bin/bash
# ../home/install_wine_python2_preinstalled.sh

function include_dependencies {
    local my_dir="$( cd "$(dirname "${BASH_SOURCE[0]}")" ; pwd -P )"  # this gives the full path, even for sourced scripts
    chmod +x "${my_dir}/lib_bash/*.sh"
    source "${my_dir}/lib_bash/lib_color.sh"
    source "${my_dir}/lib_bash/lib_retry.sh"
    source "${my_dir}/lib_bash/lib_wine_install.sh"
}

include_dependencies  # me need to do that via a function to have local scope of my_dir

# if used outside github/travis You need to set :
# WINEARCH=win32    for 32 Bit Wine
# WINEARCH=         for 64 Bit Wine
# WINEPREFIX defaults to ${HOME}/.wine   or you need to pass it via environment variable
# if running headless, the xvfb service needs to run


clr_bold clr_green "Install Python 2.7 on WINE"
check_wine_prefix
check_wine_arch

wine_drive_c_dir=${WINEPREFIX}/drive_c
decompress_dir=${HOME}/bitranox_decompress
mkdir -p ${decompress_dir}

python_version_short=python27
python_version_doc="Python 2.7"

clr_green "Download ${python_version_doc} Binaries from https://github.com/bitranox/binaries_${python_version_short}_wine/archive/master.zip"
retry wget -nc --no-check-certificate -O ${decompress_dir}/binaries_${python_version_short}_wine-master.zip https://github.com/bitranox/binaries_${python_version_short}_wine/archive/master.zip

clr_green "Unzip ${python_version_doc} Master to ${HOME}"
unzip -nqq ${decompress_dir}/binaries_${python_version_short}_wine-master.zip -d ${decompress_dir}

if [[ "${WINEARCH}" == "win32" ]]
    then
        clr_green "Joining Multipart Zip in ${decompress_dir}/binaries_${python_version_short}_wine-master/bin"
        cat ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/python*_wine_32* > ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/joined_${python_version_short}.zip
        add_pythonpath="c:/Python27-32;c:/Python27-32/Scripts"
    else
        clr_green "Joining Multipart Zip in ${decompress_dir}/binaries_${python_version_short}_wine-master/bin"
        cat ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/python*_wine_64* > ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/joined_${python_version_short}.zip
        add_pythonpath="c:/Python27-64;c:/Python27-64/Scripts"
    fi

clr_green "Unzip ${python_version_doc} to ${wine_drive_c_dir}"
unzip -qq ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/joined_${python_version_short}.zip -d ${wine_drive_c_dir}

prepend_path_to_wine_registry ${add_pythonpath}

clr_green "done"
clr_green "******************************************************************************************************************"
clr_bold clr_green "FINISHED installing Python 2.7 on Wine Machine ${WINEPREFIX}"
clr_green "******************************************************************************************************************"

#!/bin/bash
# ../home/install_wine_python3_preinstalled.sh

function include_dependencies {
    local my_dir="$( cd "$(dirname "${BASH_SOURCE[0]}")" ; pwd -P )"  # this gives the full path, even for sourced scripts
    chmod +x "${my_dir}/lib_bash/*.sh"
    source "${my_dir}/lib_bash/lib_color.sh"
    source "${my_dir}/lib_bash/lib_retry.sh"
    source "${my_dir}/lib_bash/lib_wine_install.sh"
}

include_dependencies  # me need to do that via a function to have local scope of my_dir

# if used outside github/travis You need to set :
# WINEARCH=win32    for 32 Bit Wine
# WINEARCH=""       for 64 Bit Wine
# WINEPREFIX defaults to ${HOME}/.wine   or you need to pass it via environment variable

# if running headless, the xvfb service needs to run

clr_bold clr_green "Install Python 3.7 on WINE"
check_wine_prefix
check_wine_arch


wine_drive_c_dir=${WINEPREFIX}/drive_c
decompress_dir=${HOME}/bitranox_decompress
mkdir -p ${decompress_dir}

python_version_short=python37
python_version_doc="Python 3.7"

clr_green "Download ${python_version_doc} Binaries from https://github.com/bitranox/binaries_${python_version_short}_wine/archive/master.zip"
retry wget -nc --no-check-certificate -O ${decompress_dir}/binaries_${python_version_short}_wine-master.zip https://github.com/bitranox/binaries_${python_version_short}_wine/archive/master.zip

clr_green "Unzip ${python_version_doc} Master to ${HOME}"
unzip -nqq ${decompress_dir}/binaries_${python_version_short}_wine-master.zip -d ${decompress_dir}

if [[ "${WINEARCH}" == "win32" ]]
    then
        clr_green "Joining Multipart Zip in ${decompress_dir}/binaries_${python_version_short}_wine-master/bin"
        cat ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/python*_wine_32* > ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/joined_${python_version_short}.zip
        add_pythonpath="c:/Python37-32;c:/Python37-32/Scripts"
    else
        clr_green "Joining Multipart Zip in ${decompress_dir}/binaries_${python_version_short}_wine-master/bin"
        cat ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/python*_wine_64* > ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/joined_${python_version_short}.zip
        add_pythonpath="c:/Python37-64;c:/Python37-64/Scripts"
    fi

clr_green "Unzip ${python_version_doc} to ${wine_drive_c_dir}"
unzip -qq ${decompress_dir}/binaries_${python_version_short}_wine-master/bin/joined_${python_version_short}.zip -d ${wine_drive_c_dir}

prepend_path_to_wine_registry ${add_pythonpath}


clr_green "done"
clr_green "******************************************************************************************************************"
clr_bold clr_green "FINISHED installing Python 3.7 on Wine Machine ${WINEPREFIX}"
clr_green "******************************************************************************************************************"

#!/bin/bash
# ../home/install_wine_git_portable.sh

function include_dependencies {
    local my_dir="$( cd "$(dirname "${BASH_SOURCE[0]}")" ; pwd -P )"  # this gives the full path, even for sourced scripts
    chmod +x "${my_dir}/lib_bash/*.sh"
    source "${my_dir}/lib_bash/lib_color.sh"
    source "${my_dir}/lib_bash/lib_retry.sh"
    source "${my_dir}/lib_bash/lib_wine_install.sh"
}

include_dependencies  # me need to do that via a function to have local scope of my_dir

# if used outside github/travis You need to set :
# WINEARCH=win32    for 32 Bit Wine
# WINEARCH=         for 64 Bit Wine
# WINEPREFIX defaults to ${HOME}/.wine   or you need to pass it via environment variable

# if running headless, the xvfb service needs to run

clr_bold clr_green "Install Git Portable"
check_wine_prefix
check_wine_arch

wine_drive_c_dir=${WINEPREFIX}/drive_c
decompress_dir=${HOME}/bitranox_decompress
mkdir -p ${decompress_dir}

clr_green "Download Git Portable Binaries"
retry wget -nc --no-check-certificate -O ${decompress_dir}/binaries_portable_git-master.zip https://github.com/bitranox/binaries_portable_git/archive/master.zip

clr_green "Unzip Git Portable Binaries Master to ${decompress_dir}"
unzip -nqq ${decompress_dir}/binaries_portable_git-master.zip -d ${decompress_dir}

if [[ "${WINEARCH}" == "win32" ]]
    then
        clr_green "Joining Multipart Zip in ${decompress_dir}/binaries_portable_git-master/bin"
        cat ${decompress_dir}/binaries_portable_git-master/bin/PortableGit32* > ${decompress_dir}/binaries_portable_git-master/bin/joined_PortableGit.zip
        add_git_path="c:/PortableGit32/cmd"
    else
        clr_green "Joining Multipart Zip in ${decompress_dir}/binaries_portable_git-master/bin"
        cat ${decompress_dir}/binaries_portable_git-master/bin/PortableGit64* > ${decompress_dir}/binaries_portable_git-master/bin/joined_PortableGit.zip
        add_git_path="c:/PortableGit64/cmd"
    fi

clr_green "Unzip Git Portable Binaries to ${wine_drive_c_dir}"
unzip -qq ${decompress_dir}/binaries_portable_git-master/bin/joined_PortableGit.zip -d ${wine_drive_c_dir}

prepend_path_to_wine_registry ${add_git_path}

clr_green "done"
clr_green "******************************************************************************************************************"
clr_bold clr_green "FINISHED installing Git Portable on Wine Machine ${WINEPREFIX}"
clr_green "******************************************************************************************************************"

#!/bin/bash
# ../home/lib_bash/lib_color.sh
#
# Constants and functions for terminal colors.
# Author: Max Tsepkov <[email protected]>
# Manual see https://github.com/mercuriev/bash_colors
#


CLR_ESC="\033["

# All these variables has a function with the same name, but in lower case.
#
CLR_RESET=0             # reset all attributes to their defaults
CLR_RESET_UNDERLINE=24  # underline off
CLR_RESET_REVERSE=27    # reverse off
CLR_DEFAULT=39          # set underscore off, set default foreground color
CLR_DEFAULTB=49         # set default background color

CLR_BOLD=1              # set bold
CLR_BRIGHT=2            # set half-bright (simulated with color on a color display)
CLR_UNDERSCORE=4        # set underscore (simulated with color on a color display)
CLR_REVERSE=7           # set reverse video

CLR_BLACK=30            # set black foreground
CLR_RED=31              # set red foreground
CLR_GREEN=32            # set green foreground
CLR_BROWN=33            # set brown foreground
CLR_BLUE=34             # set blue foreground
CLR_MAGENTA=35          # set magenta foreground
CLR_CYAN=36             # set cyan foreground
CLR_WHITE=37            # set white foreground

CLR_BLACKB=40           # set black background
CLR_REDB=41             # set red background
CLR_GREENB=42           # set green background
CLR_BROWNB=43           # set brown background
CLR_BLUEB=44            # set blue background
CLR_MAGENTAB=45         # set magenta background
CLR_CYANB=46            # set cyan background
CLR_WHITEB=47           # set white background


# check if string exists as function
# usage: if fn_exists "sometext"; then ... fi
function fn_exists
{
    type -t "$1" | grep -q 'function'
}

# iterate through command arguments, o allow for iterative color application
function clr_layer
{
    # default echo setting
    CLR_ECHOSWITCHES="-e"
    CLR_STACK=""
    CLR_SWITCHES=""
    ARGS=("$@")

    # iterate over arguments in reverse
    for ((i=$#; i>=0; i--)); do
        ARG=${ARGS[$i]}
        # echo $ARG
        # set CLR_VAR as last argtype
        firstletter=${ARG:0:1}

        # check if argument is a switch
        if [ "$firstletter" = "-" ] ; then
            # if -n is passed, set switch for echo in clr_escape
            if [[ $ARG == *"n"* ]]; then
                CLR_ECHOSWITCHES="-en"
                CLR_SWITCHES=$ARG
            fi
        else
            # last arg is the incoming string
            if [ -z "$CLR_STACK" ]; then
                CLR_STACK=$ARG
            else
                # if the argument is function, apply it
                if [ -n "$ARG" ] && fn_exists $ARG; then
                    #continue to pass switches through recursion
                    CLR_STACK=$($ARG "$CLR_STACK" $CLR_SWITCHES)
                fi
            fi
        fi
    done

    # pass stack and color var to escape function
    clr_escape "$CLR_STACK" $1;
}

# General function to wrap string with escape sequence(s).
# Ex: clr_escape foobar $CLR_RED $CLR_BOLD
function clr_escape
{
    local result="$1"
    until [ -z "${2:-}" ]; do
    if ! [ $2 -ge 0 -a $2 -le 47 ] 2>/dev/null; then
        echo "clr_escape: argument \"$2\" is out of range" >&2 && return 1
    fi
        result="${CLR_ESC}${2}m${result}${CLR_ESC}${CLR_RESET}m"
    shift || break
    done

    echo "$CLR_ECHOSWITCHES" "$result"
}

function clr_reset           { clr_layer $CLR_RESET "$@";           }
function clr_reset_underline { clr_layer $CLR_RESET_UNDERLINE "$@"; }
function clr_reset_reverse   { clr_layer $CLR_RESET_REVERSE "$@";   }
function clr_default         { clr_layer $CLR_DEFAULT "$@";         }
function clr_defaultb        { clr_layer $CLR_DEFAULTB "$@";        }
function clr_bold            { clr_layer $CLR_BOLD "$@";            }
function clr_bright          { clr_layer $CLR_BRIGHT "$@";          }
function clr_underscore      { clr_layer $CLR_UNDERSCORE "$@";      }
function clr_reverse         { clr_layer $CLR_REVERSE "$@";         }
function clr_black           { clr_layer $CLR_BLACK "$@";           }
function clr_red             { clr_layer $CLR_RED "$@";             }
function clr_green           { clr_layer $CLR_GREEN "$@";           }
function clr_brown           { clr_layer $CLR_BROWN "$@";           }
function clr_blue            { clr_layer $CLR_BLUE "$@";            }
function clr_magenta         { clr_layer $CLR_MAGENTA "$@";         }
function clr_cyan            { clr_layer $CLR_CYAN "$@";            }
function clr_white           { clr_layer $CLR_WHITE "$@";           }
function clr_blackb          { clr_layer $CLR_BLACKB "$@";          }
function clr_redb            { clr_layer $CLR_REDB "$@";            }
function clr_greenb          { clr_layer $CLR_GREENB "$@";          }
function clr_brownb          { clr_layer $CLR_BROWNB "$@";          }
function clr_blueb           { clr_layer $CLR_BLUEB "$@";           }
function clr_magentab        { clr_layer $CLR_MAGENTAB "$@";        }
function clr_cyanb           { clr_layer $CLR_CYANB "$@";           }
function clr_whiteb          { clr_layer $CLR_WHITEB "$@";          }

# Outputs colors table
function clr_dump
{
    local T='gYw'

    echo -e "\n                 40m     41m     42m     43m     44m     45m     46m     47m";

    for FGs in '   0m' '   1m' '  30m' '1;30m' '  31m' '1;31m' \
               '  32m' '1;32m' '  33m' '1;33m' '  34m' '1;34m' \
               '  35m' '1;35m' '  36m' '1;36m' '  37m' '1;37m';
    do
        FG=${FGs// /}
        echo -en " $FGs \033[$FG  $T  "
        for BG in 40m 41m 42m 43m 44m 45m 46m 47m; do
            echo -en " \033[$FG\033[$BG  $T  \033[0m";
        done
        echo;
    done

    echo
    clr_bold "    Code     Function           Variable"
    echo \
'    0        clr_reset          $CLR_RESET
    1        clr_bold           $CLR_BOLD
    2        clr_bright         $CLR_BRIGHT
    4        clr_underscore     $CLR_UNDERSCORE
    7        clr_reverse        $CLR_REVERSE

    30       clr_black          $CLR_BLACK
    31       clr_red            $CLR_RED
    32       clr_green          $CLR_GREEN
    33       clr_brown          $CLR_BROWN
    34       clr_blue           $CLR_BLUE
    35       clr_magenta        $CLR_MAGENTA
    36       clr_cyan           $CLR_CYAN
    37       clr_white          $CLR_WHITE

    40       clr_blackb         $CLR_BLACKB
    41       clr_redb           $CLR_REDB
    42       clr_greenb         $CLR_GREENB
    43       clr_brownb         $CLR_BROWNB
    44       clr_blueb          $CLR_BLUEB
    45       clr_magentab       $CLR_MAGENTAB
    46       clr_cyanb          $CLR_CYANB
    47       clr_whiteb         $CLR_WHITEB
'
}

function fail {
  clr_bold clr_red "${1}" >&2
  exit 1
}

## make it possible to call functions without source include
# Check if the function exists (bash specific)
if [[ ! -z "$1" ]]
    then
        if declare -f "${1}" > /dev/null
        then
          # call arguments verbatim
          "$@"
        else
          # Show a helpful error
          function_name="${1}"
          library_name="${0}"
          fail "\"${function_name}\" is not a known function name of \"${library_name}\""
        fi
    fi

#!/bin/bash
# ../home/lib_bash/lib_retry.sh

function include_dependencies {
    local my_dir="$( cd "$(dirname "${BASH_SOURCE[0]}")" ; pwd -P )"  # this gives the full path, even for sourced scripts
    source "${my_dir}/lib_color.sh"
}

include_dependencies  # we need to do that via a function to have local scope of my_dir


function fail {
  clr_bold clr_red "${1}" >&2
  exit 1
}


function retry {
  local n=1
  local max=5
  local delay=5
  while true; do
    my_command="${@}"
    "$@" && break || {
      if [[ $n -lt $max ]]; then
        ((n++))
        clr_bold clr_red "Command \"${my_command}\" failed. Attempt ${n}/${max}:"
        sleep $delay;
      else
        fail "The command \"${my_command}\" has failed after ${n} attempts."
      fi
    }
  done
}


## make it possible to call functions without source include
# Check if the function exists (bash specific)
if [[ ! -z "$1" ]]
    then
        if declare -f "${1}" > /dev/null
        then
          # call arguments verbatim
          "$@"
        else
          # Show a helpful error
          function_name="${1}"
          library_name="${0}"
          fail "\"${function_name}\" is not a known function name of \"${library_name}\""
        fi
    fi

#!/bin/bash
# ../home/lib_bash/lib_wine_install.sh

function include_dependencies {
    local my_dir="$( cd "$(dirname "${BASH_SOURCE[0]}")" ; pwd -P )"  # this gives the full path, even for sourced scripts
    chmod +x "${my_dir}/*.sh"
    source "${my_dir}/lib_color.sh"
    source "${my_dir}/lib_retry.sh"
}

include_dependencies  # we need to do that via a function to have local scope of my_dir


function fail {
  clr_bold clr_red "${1}" >&2
  exit 1
}


function check_wine_version {
    if [[ -z ${wine_version} ]]
        then
            clr_bold clr_red "WARNING - no wine_version in environment set - set now to default: devel"
            echo "available Versions: stable, devel, staging"
            export wine_version="devel"
        fi
}


function check_wine_prefix {
    ## set wine prefix to ${HOME}/.wine if not given by environment variable
    if [[ -z ${WINEPREFIX} ]]
        then
            clr_bold clr_red "WARNING - no WINEPREFIX in environment - set now to ${HOME}/.wine"
            export WINEPREFIX=${HOME}/.wine
        fi
}

function check_wine_arch {
    if [[ -z ${WINEARCH} ]]
        then
            clr_bold clr_red "WARNING - no WINEARCH in environment - will install 64 Bit Wine"
            clr_bold clr_red "in Order to install 32Bit You need to set WINEARCH=\"win32\""
            clr_bold clr_red "in Order to install 64Bit You need to set WINEARCH=\"\""
        fi
}


function check_wine_windows_version {
    if [[ -z ${wine_windows_version} ]]
        then
            clr_bold clr_red "WARNING - no wine_windows_version in environment - set now to win10"
            clr_bold clr_red "available Versions: win10, win2k, win2k3, win2k8, win31, win7, win8, win81, win95, win98, winxp"
            export wine_windows_version="win10"
        fi
}


function check_headless_xvfb {
    clr_green "Check if we run headless and xvfb Server is running"
    export xvfb_framebuffer_service_active="False"
    systemctl is-active --quiet xvfb && export xvfb_framebuffer_service_active="True"
    # run winetricks with xvfb if needed
    if [[ ${xvfb_framebuffer_service_active} == "True" ]]
        then
            clr_green "we run headless, xvfb service is running"
        else
            clr_green "we run on normal console, xvfb service is not running"
        fi
}

function prepend_path_to_wine_registry {
    add_pythonpath="${1}"
    clr_green "add Path Settings to Registry"
    wine_current_reg_path="`wine reg QUERY \"HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment\" /v PATH | grep REG_SZ | sed 's/^.*REG_SZ\s*//'`"
    wine_new_reg_path="${add_pythonpath};${wine_current_reg_path}"
    wine reg add "HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment" /t REG_SZ /v PATH /d "${wine_new_reg_path}" /f
    wine_actual_reg_path="`wine reg QUERY \"HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment\" /v PATH | grep REG_SZ | sed 's/^.*REG_SZ\s*//'`"
    clr_green "adding Path done"
    clr_bold clr_green "Wine Registry PATH=${wine_actual_reg_path}"
}


## make it possible to call functions without source include
# Check if the function exists (bash specific)
if [[ ! -z "$1" ]]
    then
        if declare -f "${1}" > /dev/null
        then
          # call arguments verbatim
          "$@"
        else
          # Show a helpful error
          function_name="${1}"
          library_name="${0}"
          fail "\"${function_name}\" is not a known function name of \"${library_name}\""
        fi
    fi

答案4

以下是我用过的简单指南:

#1 Use Wine 2.4
apt install add-apt-repository
add-apt-repository ppa:wine/wine-builds
apt install --install-recommends winehq-devel


#2 Use winetricks (a newer one that what is available in the repo)
wget  https://raw.githubusercontent.com/Winetricks/winetricks/master/src/winetricks
./winetricks -q win10
./winetricks vcrun2015

之后只需执行 wine python-3.4.4.exe 或任何 Python 版本。如果您使用的是 python 3.5,则“安装”选项将不可见,但如果您单击安装程序的中心,它将成功完成并且 python 可以正常工作。

来源:http://realtechtalk.com/How_To_Install_python_34_35_and_up_on_Linux_with_wine_Working_Solution-2288-articles

相关内容