Example #1
0
File: core.cpp Project: Pik-9/qTox
void Core::setNospam(uint32_t nospam)
{
    uint8_t *nspm = reinterpret_cast<uint8_t*>(&nospam);
    std::reverse(nspm, nspm + 4);
    tox_self_set_nospam(tox, nospam);

    emit idSet(getSelfId().toString());
}
Example #2
0
void Core::setAvatar(const QByteArray& data)
{
    QPixmap pic;
    pic.loadFromData(data);
    Settings::getInstance().saveAvatar(pic, getSelfId().toString());
    emit selfAvatarChanged(pic);
    
    AvatarBroadcaster::setAvatar(data);
    AvatarBroadcaster::enableAutoBroadcast();
}
Example #3
0
File: core.cpp Project: Pik-9/qTox
void Core::setAvatar(const QByteArray& data)
{
    if (!data.isEmpty())
    {
        QPixmap pic;
        pic.loadFromData(data);
        profile.saveAvatar(data, getSelfId().publicKey);
        emit selfAvatarChanged(pic);
    }
    else
    {
        emit selfAvatarChanged(QPixmap(":/img/contact_dark.svg"));
    }

    AvatarBroadcaster::setAvatar(data);
    AvatarBroadcaster::enableAutoBroadcast();
}
Example #4
0
void Core::setAvatar(const QByteArray& data)
{
    if (!data.isEmpty())
    {
        QPixmap pic;
        pic.loadFromData(data);
        Settings::getInstance().saveAvatar(pic, getSelfId().toString());
        emit selfAvatarChanged(pic);
    }
    else
    {
        emit selfAvatarChanged(QPixmap(":/img/contact_dark.svg"));
    }

    AvatarBroadcaster::setAvatar(data);
    AvatarBroadcaster::enableAutoBroadcast();
}
Example #5
0
File: core.cpp Project: Pik-9/qTox
void Core::requestFriendship(const QString& friendAddress, const QString& message)
{
    const QString userId = friendAddress.mid(0, TOX_PUBLIC_KEY_SIZE * 2);

    if (message.isEmpty())
    {
        emit failedToAddFriend(userId, tr("You need to write a message with your request"));
    }
    else if (message.size() > TOX_MAX_FRIEND_REQUEST_LENGTH)
    {
        emit failedToAddFriend(userId, tr("Your message is too long!"));
    }
    else if (hasFriendWithAddress(friendAddress))
    {
        emit failedToAddFriend(userId, tr("Friend is already added"));
    }
    else
    {
        CString cMessage(message);

        uint32_t friendId = tox_friend_add(tox, CFriendAddress(friendAddress).data(),
                                      cMessage.data(), cMessage.size(), nullptr);
        if (friendId == std::numeric_limits<uint32_t>::max())
        {
            qDebug() << "Failed to request friendship";
            emit failedToAddFriend(userId);
        }
        else
        {
            qDebug() << "Requested friendship of "<<friendId;
            // Update our friendAddresses
            Settings::getInstance().updateFriendAddress(friendAddress);
            QString inviteStr = tr("/me offers friendship.");
            if (message.length())
                inviteStr = tr("/me offers friendship, \"%1\"").arg(message);

            Profile* profile = Nexus::getProfile();
            if (profile->isHistoryEnabled())
                profile->getHistory()->addNewMessage(userId, inviteStr, getSelfId().publicKey, QDateTime::currentDateTime(), true, QString());
            emit friendAdded(friendId, userId);
            emit friendshipChanged(friendId);
        }
    }
    profile.saveToxSave();
}
Example #6
0
void Core::setAvatar(uint8_t format, const QByteArray& data)
{
    if (tox_set_avatar(tox, format, (uint8_t*)data.constData(), data.size()) != 0)
    {
        qWarning() << "Core: Failed to set self avatar";
        return;
    }

    QPixmap pic;
    pic.loadFromData(data);
    Settings::getInstance().saveAvatar(pic, getSelfId().toString());
    emit selfAvatarChanged(pic);
    
    // Broadcast our new avatar!
    // according to tox.h, we need not broadcast this ourselves, but initial testing indicated elsewise
    const uint32_t friendCount = tox_count_friendlist(tox);;
    for (unsigned i=0; i<friendCount; i++)
        tox_send_avatar_info(tox, i);
}
Example #7
0
void Core::requestFriendship(const QString& friendAddress, const QString& message)
{
    const QString userId = friendAddress.mid(0, TOX_PUBLIC_KEY_SIZE * 2);

    if (message.isEmpty())
    {
        emit failedToAddFriend(userId, tr("You need to write a message with your request"));
    }
    else if (message.size() > TOX_MAX_FRIEND_REQUEST_LENGTH)
    {
        emit failedToAddFriend(userId, tr("Your message is too long!"));
    }
    else if (hasFriendWithAddress(friendAddress))
    {
        emit failedToAddFriend(userId, tr("Friend is already added"));
    }
    else
    {
        qDebug() << "Core: requesting friendship of "+friendAddress;
        CString cMessage(message);

        uint32_t friendId = tox_friend_add(tox, CFriendAddress(friendAddress).data(),
                                      cMessage.data(), cMessage.size(), nullptr);
        if (friendId == std::numeric_limits<uint32_t>::max())
        {
            emit failedToAddFriend(userId);
        }
        else
        {
            // Update our friendAddresses
            Settings::getInstance().updateFriendAdress(friendAddress);
            QString inviteStr = tr("/me offers friendship.");
            if (message.length())
                inviteStr = tr("/me offers friendship, \"%1\"").arg(message);

            HistoryKeeper::getInstance()->addChatEntry(userId, inviteStr, getSelfId().publicKey, QDateTime::currentDateTime(), true);
            emit friendAdded(friendId, userId);
        }
    }
    saveConfiguration();
}
Example #8
0
File: core.cpp Project: Pik-9/qTox
/**
 * @brief Initializes the core, must be called before anything else
 */
void Core::start()
{
    bool isNewProfile = profile.isNewProfile();
    if (isNewProfile)
    {
        qDebug() << "Creating a new profile";
        makeTox(QByteArray());
        setStatusMessage(tr("Toxing on qTox"));
        setUsername(profile.getName());
    }
    else
    {
        qDebug() << "Loading user profile";
        QByteArray savedata = profile.loadToxSave();
        if (savedata.isEmpty())
        {
            emit failedToStart();
            return;
        }
        makeTox(savedata);
    }

    qsrand(time(nullptr));

    if (!tox)
    {
        ready = true;
        GUI::setEnabled(true);
        return;
    }

    // set GUI with user and statusmsg
    QString name = getUsername();
    if (!name.isEmpty())
        emit usernameSet(name);

    QString msg = getStatusMessage();
    if (!msg.isEmpty())
        emit statusMessageSet(msg);

    QString id = getSelfId().toString();
    if (!id.isEmpty())
        emit idSet(id);

    // TODO: This is a backwards compatibility check,
    // once most people have been upgraded away from the old HistoryKeeper, remove this
    if (Nexus::getProfile()->isEncrypted())
        checkEncryptedHistory();

    loadFriends();

    tox_callback_friend_request(tox, onFriendRequest, this);
    tox_callback_friend_message(tox, onFriendMessage, this);
    tox_callback_friend_name(tox, onFriendNameChange, this);
    tox_callback_friend_typing(tox, onFriendTypingChange, this);
    tox_callback_friend_status_message(tox, onStatusMessageChanged, this);
    tox_callback_friend_status(tox, onUserStatusChanged, this);
    tox_callback_friend_connection_status(tox, onConnectionStatusChanged, this);
    tox_callback_friend_read_receipt(tox, onReadReceiptCallback, this);
    tox_callback_group_invite(tox, onGroupInvite, this);
    tox_callback_group_message(tox, onGroupMessage, this);
    tox_callback_group_namelist_change(tox, onGroupNamelistChange, this);
    tox_callback_group_title(tox, onGroupTitleChange, this);
    tox_callback_group_action(tox, onGroupAction, this);
    tox_callback_file_chunk_request(tox, CoreFile::onFileDataCallback, this);
    tox_callback_file_recv(tox, CoreFile::onFileReceiveCallback, this);
    tox_callback_file_recv_chunk(tox, CoreFile::onFileRecvChunkCallback, this);
    tox_callback_file_recv_control(tox, CoreFile::onFileControlCallback, this);

    QPixmap pic = profile.loadAvatar();
    if (!pic.isNull() && !pic.size().isEmpty())
    {
        QByteArray data;
        QBuffer buffer(&data);
        buffer.open(QIODevice::WriteOnly);
        pic.save(&buffer, "PNG");
        buffer.close();
        setAvatar(data);
    }
    else
    {
        qDebug() << "Self avatar not found, will broadcast empty avatar to friends";
        setAvatar({});
    }

    ready = true;

    // If we created a new profile earlier,
    // now that we're ready save it and ONLY THEN broadcast the new ID.
    // This is useful for e.g. the profileForm that searches for saves.
    if (isNewProfile)
    {
        profile.saveToxSave();
        emit idSet(getSelfId().toString());
    }

    if (isReady())
        GUI::setEnabled(true);

    process(); // starts its own timer
    av->start();
}
Example #9
0
QString Core::getIDString() const
{
    return getSelfId().toString().left(12);
    // 12 is the smallest multiple of four such that
    // 16^n > 10^10 (which is roughly the planet's population)
}
Example #10
0
File: core.cpp Project: mpxc/qTox
/**
 * @brief Initializes the core, must be called before anything else
 */
void Core::start(const QByteArray& savedata)
{
    bool isNewProfile = profile.isNewProfile();
    if (isNewProfile) {
        qDebug() << "Creating a new profile";
        makeTox(QByteArray());
        makeAv();
        setStatusMessage(tr("Toxing on qTox"));
        setUsername(profile.getName());
    } else {
        qDebug() << "Loading user profile";
        if (savedata.isEmpty()) {
            emit failedToStart();
            return;
        }

        makeTox(savedata);
        makeAv();
    }

    qsrand(time(nullptr));
    if (!tox) {
        ready = true;
        GUI::setEnabled(true);
        return;
    }

    // set GUI with user and statusmsg
    QString name = getUsername();
    if (!name.isEmpty()) {
        emit usernameSet(name);
    }

    QString msg = getStatusMessage();
    if (!msg.isEmpty()) {
        emit statusMessageSet(msg);
    }

    ToxId id = getSelfId();
    // TODO: probably useless check, comes basically directly from toxcore
    if (id.isValid()) {
        emit idSet(id);
    }

    loadFriends();

    tox_callback_friend_request(tox, onFriendRequest);
    tox_callback_friend_message(tox, onFriendMessage);
    tox_callback_friend_name(tox, onFriendNameChange);
    tox_callback_friend_typing(tox, onFriendTypingChange);
    tox_callback_friend_status_message(tox, onStatusMessageChanged);
    tox_callback_friend_status(tox, onUserStatusChanged);
    tox_callback_friend_connection_status(tox, onConnectionStatusChanged);
    tox_callback_friend_read_receipt(tox, onReadReceiptCallback);
    tox_callback_conference_invite(tox, onGroupInvite);
    tox_callback_conference_message(tox, onGroupMessage);
    tox_callback_conference_namelist_change(tox, onGroupNamelistChange);
    tox_callback_conference_title(tox, onGroupTitleChange);
    tox_callback_file_chunk_request(tox, CoreFile::onFileDataCallback);
    tox_callback_file_recv(tox, CoreFile::onFileReceiveCallback);
    tox_callback_file_recv_chunk(tox, CoreFile::onFileRecvChunkCallback);
    tox_callback_file_recv_control(tox, CoreFile::onFileControlCallback);

    QByteArray data = profile.loadAvatarData(getSelfPublicKey().toString());
    if (data.isEmpty()) {
        qDebug() << "Self avatar not found, will broadcast empty avatar to friends";
    }

    setAvatar(data);

    ready = true;

    if (isNewProfile) {
        profile.saveToxSave();
    }

    if (isReady()) {
        GUI::setEnabled(true);
    }

    process(); // starts its own timer
    av->start();
}
Example #11
0
File: core.cpp Project: mpxc/qTox
/**
 * @brief Sets the NoSpam value to prevent friend request spam
 * @param nospam an arbitrary which becomes part of the Tox ID
 */
void Core::setNospam(uint32_t nospam)
{
    tox_self_set_nospam(tox, nospam);
    emit idSet(getSelfId());
}
Example #12
0
void Core::start()
{
    // IPv6 needed for LAN discovery, but can crash some weird routers. On by default, can be disabled in options.
    bool enableIPv6 = Settings::getInstance().getEnableIPv6();
    bool forceTCP = Settings::getInstance().getForceTCP();

    bool useProxy = Settings::getInstance().getUseProxy();

    if (enableIPv6)
        qDebug() << "Core starting with IPv6 enabled";
    else
        qWarning() << "Core starting with IPv6 disabled. LAN discovery may not work properly.";

    Tox_Options toxOptions;
    toxOptions.ipv6enabled = enableIPv6;
    toxOptions.udp_disabled = forceTCP;

    // No proxy by default
    toxOptions.proxy_enabled = false;
    toxOptions.proxy_address[0] = 0;
    toxOptions.proxy_port = 0;

    if (useProxy)
    {
        QString proxyAddr = Settings::getInstance().getProxyAddr();
        int proxyPort = Settings::getInstance().getProxyPort();

        if (proxyAddr.length() > 255)
        {
            qWarning() << "Core: proxy address" << proxyAddr << "is too long";
        }
        else if (proxyAddr != "" && proxyPort > 0)
        {
            qDebug() << "Core: using proxy" << proxyAddr << ":" << proxyPort;
            toxOptions.proxy_enabled = true;
            uint16_t sz = CString::fromString(proxyAddr, (unsigned char*)toxOptions.proxy_address);
            toxOptions.proxy_address[sz] = 0;
            toxOptions.proxy_port = proxyPort;
        }
    }

    tox = tox_new(&toxOptions);
    if (tox == nullptr)
    {
        if (enableIPv6) // Fallback to IPv4
        {
            toxOptions.ipv6enabled = false;
            tox = tox_new(&toxOptions);
            if (tox == nullptr)
            {
                if (toxOptions.proxy_enabled)
                {
                    //QMessageBox::critical(Widget::getInstance(), tr("Proxy failure", "popup title"), 
                    //tr("toxcore failed to start with your proxy settings. qTox cannot run; please modify your "
                       //"settings and restart.", "popup text"));
                    qCritical() << "Core: bad proxy! no toxcore!";
                    emit badProxy();
                } 
                else
                {
                    qCritical() << "Tox core failed to start";
                    emit failedToStart();
                }
                return;
            } 
            else
                qWarning() << "Core failed to start with IPv6, falling back to IPv4. LAN discovery may not work properly.";
        }
        else if (toxOptions.proxy_enabled)
        {
            emit badProxy();
            return;
        }
        else
        {
            qCritical() << "Tox core failed to start";
            emit failedToStart();
            return;
        }
    }

    toxav = toxav_new(tox, TOXAV_MAX_CALLS);
    if (toxav == nullptr)
    {
        qCritical() << "Toxav core failed to start";
        emit failedToStart();
        return;
    }

    qsrand(time(nullptr));

    if (!loadConfiguration())
    {
        emit failedToStart();
        tox_kill(tox);
        tox = nullptr;
        return;
    }

    tox_callback_friend_request(tox, onFriendRequest, this);
    tox_callback_friend_message(tox, onFriendMessage, this);
    tox_callback_friend_action(tox, onAction, this);
    tox_callback_name_change(tox, onFriendNameChange, this);
    tox_callback_typing_change(tox, onFriendTypingChange, this);
    tox_callback_status_message(tox, onStatusMessageChanged, this);
    tox_callback_user_status(tox, onUserStatusChanged, this);
    tox_callback_connection_status(tox, onConnectionStatusChanged, this);
    tox_callback_group_invite(tox, onGroupInvite, this);
    tox_callback_group_message(tox, onGroupMessage, this);
    tox_callback_group_namelist_change(tox, onGroupNamelistChange, this);
    tox_callback_file_send_request(tox, onFileSendRequestCallback, this);
    tox_callback_file_control(tox, onFileControlCallback, this);
    tox_callback_file_data(tox, onFileDataCallback, this);
    tox_callback_avatar_info(tox, onAvatarInfoCallback, this);
    tox_callback_avatar_data(tox, onAvatarDataCallback, this);

    toxav_register_callstate_callback(toxav, onAvInvite, av_OnInvite, this);
    toxav_register_callstate_callback(toxav, onAvStart, av_OnStart, this);
    toxav_register_callstate_callback(toxav, onAvCancel, av_OnCancel, this);
    toxav_register_callstate_callback(toxav, onAvReject, av_OnReject, this);
    toxav_register_callstate_callback(toxav, onAvEnd, av_OnEnd, this);
    toxav_register_callstate_callback(toxav, onAvRinging, av_OnRinging, this);
    toxav_register_callstate_callback(toxav, onAvStarting, av_OnStarting, this);
    toxav_register_callstate_callback(toxav, onAvEnding, av_OnEnding, this);
    toxav_register_callstate_callback(toxav, onAvMediaChange, av_OnMediaChange, this);
    toxav_register_callstate_callback(toxav, onAvRequestTimeout, av_OnRequestTimeout, this);
    toxav_register_callstate_callback(toxav, onAvPeerTimeout, av_OnPeerTimeout, this);

    toxav_register_audio_recv_callback(toxav, playCallAudio, this);
    toxav_register_video_recv_callback(toxav, playCallVideo, this);

    uint8_t friendAddress[TOX_FRIEND_ADDRESS_SIZE];
    tox_get_address(tox, friendAddress);
    emit friendAddressGenerated(CFriendAddress::toString(friendAddress));

    QPixmap pic = Settings::getInstance().getSavedAvatar(getSelfId().toString());
    if (!pic.isNull() && !pic.size().isEmpty())
    {
        QByteArray data;
        QBuffer buffer(&data);
        buffer.open(QIODevice::WriteOnly);
        pic.save(&buffer, "PNG");
        buffer.close();
        setAvatar(TOX_AVATAR_FORMAT_PNG, data);
    }
    else
        qDebug() << "Core: Error loading self avatar";
    
    process(); // starts its own timer
}
Example #13
0
void Core::start()
{
    qDebug() << "Core: Starting up";

    QByteArray savedata = loadToxSave(loadPath);

    make_tox(savedata);

    // Do we need to create a new save & profile?
    if (savedata.isNull())
    {
        qDebug() << "Save file not found, creating a new profile";
        Settings::getInstance().load();
        setStatusMessage(tr("Toxing on qTox"));
        setUsername(tr("qTox User"));
    }

    qsrand(time(nullptr));

    // set GUI with user and statusmsg
    QString name = getUsername();
    if (!name.isEmpty())
        emit usernameSet(name);

    QString msg = getStatusMessage();
    if (!msg.isEmpty())
        emit statusMessageSet(msg);

    QString id = getSelfId().toString();
    if (!id.isEmpty())
        emit idSet(id);

    // tox core is already decrypted
    if (Settings::getInstance().getEnableLogging() && Settings::getInstance().getEncryptLogs())
        checkEncryptedHistory();

    loadFriends();

    tox_callback_friend_request(tox, onFriendRequest, this);
    tox_callback_friend_message(tox, onFriendMessage, this);
    tox_callback_friend_name(tox, onFriendNameChange, this);
    tox_callback_friend_typing(tox, onFriendTypingChange, this);
    tox_callback_friend_status_message(tox, onStatusMessageChanged, this);
    tox_callback_friend_status(tox, onUserStatusChanged, this);
    tox_callback_friend_connection_status(tox, onConnectionStatusChanged, this);
    tox_callback_friend_read_receipt(tox, onReadReceiptCallback, this);
    tox_callback_group_invite(tox, onGroupInvite, this);
    tox_callback_group_message(tox, onGroupMessage, this);
    tox_callback_group_namelist_change(tox, onGroupNamelistChange, this);
    tox_callback_group_title(tox, onGroupTitleChange, this);
    tox_callback_group_action(tox, onGroupAction, this);
    tox_callback_file_chunk_request(tox, CoreFile::onFileDataCallback, this);
    tox_callback_file_recv(tox, CoreFile::onFileReceiveCallback, this);
    tox_callback_file_recv_chunk(tox, CoreFile::onFileRecvChunkCallback, this);
    tox_callback_file_recv_control(tox, CoreFile::onFileControlCallback, this);

    toxav_register_callstate_callback(toxav, onAvInvite, av_OnInvite, this);
    toxav_register_callstate_callback(toxav, onAvStart, av_OnStart, this);
    toxav_register_callstate_callback(toxav, onAvCancel, av_OnCancel, this);
    toxav_register_callstate_callback(toxav, onAvReject, av_OnReject, this);
    toxav_register_callstate_callback(toxav, onAvEnd, av_OnEnd, this);
    toxav_register_callstate_callback(toxav, onAvRinging, av_OnRinging, this);
    toxav_register_callstate_callback(toxav, onAvMediaChange, av_OnPeerCSChange, this);
    toxav_register_callstate_callback(toxav, onAvMediaChange, av_OnSelfCSChange, this);
    toxav_register_callstate_callback(toxav, onAvRequestTimeout, av_OnRequestTimeout, this);
    toxav_register_callstate_callback(toxav, onAvPeerTimeout, av_OnPeerTimeout, this);

    toxav_register_audio_callback(toxav, playCallAudio, this);
    toxav_register_video_callback(toxav, playCallVideo, this);

    QPixmap pic = Settings::getInstance().getSavedAvatar(getSelfId().toString());
    if (!pic.isNull() && !pic.size().isEmpty())
    {
        QByteArray data;
        QBuffer buffer(&data);
        buffer.open(QIODevice::WriteOnly);
        pic.save(&buffer, "PNG");
        buffer.close();
        setAvatar(data);
    }
    else
    {
        qDebug() << "Core: Error loading self avatar";
    }

    ready = true;

    // If we created a new profile earlier,
    // now that we're ready save it and ONLY THEN broadcast the new ID.
    // This is useful for e.g. the profileForm that searches for saves.
    if (savedata.isNull())
    {
        saveConfiguration();
        emit idSet(getSelfId().toString());
    }

    if (isReady())
        GUI::setEnabled(true);

    process(); // starts its own timer
}
Example #14
0
void Core::requestFriendship(const ToxId& friendAddress, const QString& message)
{
    ToxPk friendPk = friendAddress.getPublicKey();

    if (!friendAddress.isValid())
    {
        emit failedToAddFriend(friendPk,
                               tr("Invalid Tox ID"));
    }
    else if (message.isEmpty())
    {
        emit failedToAddFriend(friendPk,
                               tr("You need to write a message with your request"));
    }
    else if (message.size() > TOX_MAX_FRIEND_REQUEST_LENGTH)
    {
        emit failedToAddFriend(friendPk,
                               tr("Your message is too long!"));
    }
    else if (hasFriendWithPublicKey(friendPk))
    {
        emit failedToAddFriend(friendPk,
                               tr("Friend is already added"));
    }
    else
    {
        CString cMessage(message);

        uint32_t friendId = tox_friend_add(tox, friendAddress.getBytes(),
                                      cMessage.data(), cMessage.size(), nullptr);
        if (friendId == std::numeric_limits<uint32_t>::max())
        {
            qDebug() << "Failed to request friendship";
            emit failedToAddFriend(friendPk);
        }
        else
        {
            qDebug() << "Requested friendship of " << friendId;
            // Update our friendAddresses
            Settings::getInstance().updateFriendAddress(friendAddress.toString());

            // TODO: start: this really shouldn't be in Core
            QString inviteStr = tr("/me offers friendship.");
            if (message.length())
                inviteStr = tr("/me offers friendship, \"%1\"").arg(message);

            Profile* profile = Nexus::getProfile();
            if (profile->isHistoryEnabled())
            {
                profile->getHistory()->addNewMessage(friendAddress.toString(),
                                                     inviteStr,
                                                     getSelfId().getPublicKey().toString(),
                                                     QDateTime::currentDateTime(),
                                                     true,
                                                     QString());
            }
            // TODO: end

            emit friendAdded(friendId, friendAddress.getPublicKey());
            emit friendshipChanged(friendId);
        }
    }
    profile.saveToxSave();
}