예제 #1
0
파일: chart.cpp 프로젝트: Stretto/forge
void AbstractChart::renderTickLabels(int pWindowId, unsigned w, unsigned h,
        std::vector<std::string> &texts,
        glm::mat4 &transformation, int coor_offset,
        bool useZoffset)
{
    auto &fonter = getChartFont();
    fonter->setOthro2D(int(w), int(h));

    float pos[2];
    for (StringIter it = texts.begin(); it!=texts.end(); ++it) {
        int idx = int(it - texts.begin());
        glm::vec4 p = glm::vec4(mTickTextX[idx+coor_offset],
                                mTickTextY[idx+coor_offset],
                                (useZoffset ? mTickTextZ[idx+coor_offset] : 0), 1);
        glm::vec4 res = transformation * p;

        /* convert text position from [-1,1] range to
         * [0, 1) range and then offset horizontally
         * to compensate for margins and ticksize */
        pos[0] = w*(res.x/res.w+1.0f)/2.0f;
        pos[1] = h*(res.y/res.w+1.0f)/2.0f;

        /* offset based on text size to align
         * text center with tick mark position */
        if(coor_offset < mTickCount) {
            pos[0] -= ((CHART2D_FONT_SIZE*it->length()/2.0f));
        }else if(coor_offset >= mTickCount && coor_offset < 2*mTickCount) {
            pos[1] -= ((CHART2D_FONT_SIZE));
        }else {
            pos[0] -= ((CHART2D_FONT_SIZE*it->length()/2.0f));
            pos[1] -= ((CHART2D_FONT_SIZE));
        }
        fonter->render(pWindowId, pos, WHITE, it->c_str(), CHART2D_FONT_SIZE);
    }
}
예제 #2
0
void AbstractChart2D::renderChart(const void* pWnd, int pX, int pY, int pVPW, int pVPH)
{
    float w = float(pVPW - (mLeftMargin + mRightMargin + mTickSize));
    float h = float(pVPH - (mTopMargin + mBottomMargin + mTickSize));
    float offset_x = (1.9f * (mLeftMargin+mTickSize) + (w - pVPW)) / pVPW;
    float offset_y = (1.9f * (mBottomMargin+mTickSize) + (h - pVPH)) / pVPH;
    float scale_x = w / pVPW;
    float scale_y = h / pVPH;

    CheckGL("Begin Chart::render");

    bindResources(pWnd);

    /* bind the plotting shader program  */
    glUseProgram(mBorderProgram);

    /* set uniform attributes of shader
     * for drawing the plot borders */
    glm::mat4 trans = glm::scale(glm::translate(glm::mat4(1),
                                                glm::vec3(offset_x, offset_y, 0)),
                                 glm::vec3(scale_x, scale_y, 1));
    glUniformMatrix4fv(mBorderMatIndex, 1, GL_FALSE, glm::value_ptr(trans));
    glUniform4fv(mBorderColorIndex, 1, WHITE);

    /* Draw borders */
    glDrawArrays(GL_LINE_LOOP, 0, 4);

    /* reset shader program binding */
    glUseProgram(0);

    /* bind the sprite shader program to
     * draw ticks on x and y axes */
    glPointSize((GLfloat)mTickSize);

    glUseProgram(mSpriteProgram);
    glUniform4fv(mSpriteTickcolorIndex, 1, WHITE);
    glUniformMatrix4fv(mSpriteMatIndex, 1, GL_FALSE, glm::value_ptr(trans));
    /* Draw tick marks on y axis */
    glUniform1i(mSpriteTickaxisIndex, 1);
    glDrawArrays(GL_POINTS, 4, mTickCount);
    /* Draw tick marks on x axis */
    glUniform1i(mSpriteTickaxisIndex, 0);
    glDrawArrays(GL_POINTS, 4+mTickCount, mTickCount);

    glUseProgram(0);
    glPointSize(1);
    unbindResources();

    auto &fonter = getChartFont();
    fonter->setOthro2D(int(w), int(h));

    float pos[2];
    /* render tick marker texts for y axis */
    for (StringIter it = mYText.begin(); it!=mYText.end(); ++it) {
        int idx = int(it - mYText.begin());
        glm::vec4 res = trans * glm::vec4(mTickTextX[idx], mTickTextY[idx], 0, 1);
        /* convert text position from [-1,1] range to
         * [0, 1) range and then offset horizontally
         * to compensate for margins and ticksize */
        pos[0] = w*(res.x+1.0f)/2.0f;
        pos[1] = h*(res.y+1.0f)/2.0f;
        pos[0] -= (pVPW-w)*0.60f;
        fonter->render(pWnd, pos, WHITE, it->c_str(), CHART2D_FONT_SIZE);
    }
    /* render tick marker texts for x axis */
    for (StringIter it = mXText.begin(); it!=mXText.end(); ++it) {
        int idx = int(it - mXText.begin());
        /* mTickCount offset is needed while reading point coordinates for
         * x axis tick marks */
        glm::vec4 res = trans * glm::vec4(mTickTextX[idx+mTickCount], mTickTextY[idx+mTickCount], 0, 1);
        /* convert text position from [-1,1] range to
         * [0, 1) range and then offset vertically
         * to compensate for margins and ticksize */
        pos[0] = w*(res.x+1.0f)/2.0f;
        pos[1] = h*(res.y+1.0f)/2.0f;
        pos[1] -= (pVPH-h)*0.34f;
        /* offset horizontally based on text size to align
         * text center with tick mark position */
        pos[0] -= (CHART2D_FONT_SIZE*(it->length()-2)/2.0f);
        fonter->render(pWnd, pos, WHITE, it->c_str(), CHART2D_FONT_SIZE);
    }
    /* render chart axes titles */
    if (!mYTitle.empty()) {
        glm::vec4 res = trans * glm::vec4(-1.0f, 0.0f, 0.0f, 1.0f);
        pos[0] = w*(res.x+1.0f)/2.0f;
        pos[1] = h*(res.y+1.0f)/2.0f;
        pos[0] -= (pVPW-w)*0.76;
        fonter->render(pWnd, pos, WHITE, mYTitle.c_str(), CHART2D_FONT_SIZE, true);
    }
    if (!mXTitle.empty()) {
        glm::vec4 res = trans * glm::vec4(0.0f, -1.0f, 0.0f, 1.0f);
        pos[0] = w*(res.x+1.0f)/2.0f;
        pos[1] = h*(res.y+1.0f)/2.0f;
        pos[1] -= (pVPH-h)*0.66;
        fonter->render(pWnd, pos, WHITE, mXTitle.c_str(), CHART2D_FONT_SIZE);
    }

    CheckGL("End Chart::render");
}
예제 #3
0
void NmdcHub::onLine(const string& aLine) throw() {
	lastActivity = GET_TICK();

	if(aLine.length() == 0)
		return;
	
	if(aLine[0] != '$') {
		// Check if we're being banned...
		if(state != STATE_CONNECTED) {
			if(Util::findSubString(aLine, "banned") != string::npos) {
				reconnect = false;
			}
		}
		Speaker<NmdcHubListener>::fire(NmdcHubListener::Message(), this, Util::validateMessage(fromNmdc(aLine), true));
		return;
	}

	string cmd;
	string param;
	string::size_type x;
	
	if( (x = aLine.find(' ')) == string::npos) {
		cmd = aLine;
	} else {
		cmd = aLine.substr(0, x);
		param = aLine.substr(x+1);
	}

	if(cmd == "$Search") {
		if(state != STATE_CONNECTED) {
			return;
		}
		string::size_type i = 0;
		string::size_type j = param.find(' ', i);
		if(j == string::npos || i == j)
			return;
		
		string seeker = fromNmdc(param.substr(i, j-i));

		// Filter own searches
		if(SETTING(CONNECTION_TYPE) == SettingsManager::CONNECTION_ACTIVE) {
			if(seeker == (getLocalIp() + ":" + Util::toString(SETTING(IN_PORT)))) {
				return;
			}
		} else {
			// Hub:seeker
			if(Util::stricmp(seeker.c_str() + 4, getNick().c_str()) == 0) {
				return;
			}
		}

		i = j + 1;
		
		{
			Lock l(cs);
			u_int32_t tick = GET_TICK();

			seekers.push_back(make_pair(seeker, tick));

			// First, check if it's a flooder
			FloodIter fi;
			for(fi = flooders.begin(); fi != flooders.end(); ++fi) {
				if(fi->first == seeker) {
					return;
				}
			}

			int count = 0;
			for(fi = seekers.begin(); fi != seekers.end(); ++fi) {
				if(fi->first == seeker)
					count++;

				if(count > 7) {
					if(seeker.compare(0, 4, "Hub:") == 0)
						Speaker<NmdcHubListener>::fire(NmdcHubListener::SearchFlood(), this, seeker.substr(4));
					else
						Speaker<NmdcHubListener>::fire(NmdcHubListener::SearchFlood(), this, seeker + STRING(NICK_UNKNOWN));

					flooders.push_back(make_pair(seeker, tick));
					return;
				}
			}
		}

		int a;
		if(param[i] == 'F') {
			a = SearchManager::SIZE_DONTCARE;
		} else if(param[i+2] == 'F') {
			a = SearchManager::SIZE_ATLEAST;
		} else {
			a = SearchManager::SIZE_ATMOST;
		}
		i += 4;
		j = param.find('?', i);
		if(j == string::npos || i == j)
			return;
		string size = param.substr(i, j-i);
		i = j + 1;
		j = param.find('?', i);
		if(j == string::npos || i == j)
			return;
		int type = Util::toInt(param.substr(i, j-i)) - 1;
		i = j + 1;
		param = param.substr(i);

		if(param.size() > 0) {
			Speaker<NmdcHubListener>::fire(NmdcHubListener::Search(), this, seeker, a, Util::toInt64(size), type, fromNmdc(param));
			
			if(seeker.compare(0, 4, "Hub:") == 0) {
				User::Ptr u;
				{
					Lock l(cs);
					User::NickIter ni = users.find(seeker.substr(4));
					if(ni != users.end() && !ni->second->isSet(User::PASSIVE)) {
						u = ni->second;
						u->setFlag(User::PASSIVE);
					}
				}

				if(u) {
					updated(u);
				}
			}
		}
	} else if(cmd == "$MyINFO") {
		string::size_type i, j;
		i = 5;
		j = param.find(' ', i);
		if( (j == string::npos) || (j == i) )
			return;
		string nick = fromNmdc(param.substr(i, j-i));
		i = j + 1;
		User::Ptr u;
		dcassert(nick.size() > 0);

		{
			Lock l(cs);
			User::NickIter ni = users.find(nick);
			if(ni == users.end()) {
				u = users[nick] = ClientManager::getInstance()->getUser(nick, this);
			} else {
				u  = ni->second;
			}
		}
		j = param.find('$', i);
		if(j == string::npos)
			return;
		string tmpDesc = Util::validateMessage(fromNmdc(param.substr(i, j-i)), true);
		// Look for a tag...
		if(tmpDesc.size() > 0 && tmpDesc[tmpDesc.size()-1] == '>') {
			x = tmpDesc.rfind('<');
			if(x != string::npos) {
				// Hm, we have something...
				u->setTag(tmpDesc.substr(x));
				tmpDesc.erase(x);
			} else {
				u->setTag(Util::emptyString);
			}
		} else {
			u->setTag(Util::emptyString);
		}
		u->setDescription(tmpDesc);
		i = j + 3;
		j = param.find('$', i);
		if(j == string::npos)
			return;
		u->setConnection(fromNmdc(param.substr(i, j-i-1)));
		i = j + 1;
		j = param.find('$', i);
		if(j == string::npos)
			return;
		u->setEmail(Util::validateMessage(fromNmdc(param.substr(i, j-i)), true));
		i = j + 1;
		j = param.find('$', i);
		if(j == string::npos)
			return;
		u->setBytesShared(param.substr(i, j-i));

		Speaker<NmdcHubListener>::fire(NmdcHubListener::MyInfo(), this, u);
	} else if(cmd == "$Quit") {
		if(!param.empty()) {
			User::Ptr u;
			{
				Lock l(cs);
				User::NickIter i = users.find(fromNmdc(param));
				if(i == users.end()) {
					dcdebug("C::onLine Quitting user %s not found\n", param.c_str());
					return;
				}
				
				u = i->second;
				users.erase(i);
			}
			
			Speaker<NmdcHubListener>::fire(NmdcHubListener::Quit(), this, u);
			ClientManager::getInstance()->putUserOffline(u, true);
		}
	} else if(cmd == "$ConnectToMe") {
		if(state != STATE_CONNECTED) {
			return;
		}
		string::size_type i = param.find(' ');
		string::size_type j;
		if( (i == string::npos) || ((i + 1) >= param.size()) ) {
			return;
		}
		i++;
		j = param.find(':', i);
		if(j == string::npos) {
			return;
		}
		string server = fromNmdc(param.substr(i, j-i));
		if(j+1 >= param.size()) {
			return;
		}
		string port = param.substr(j+1);
		ConnectionManager::getInstance()->connect(server, (short)Util::toInt(port), getNick()); 
		Speaker<NmdcHubListener>::fire(NmdcHubListener::ConnectToMe(), this, server, (short)Util::toInt(port));
	} else if(cmd == "$RevConnectToMe") {
		if(state != STATE_CONNECTED) {
			return;
		}
		User::Ptr u;
		bool up = false;
		{
			Lock l(cs);
			string::size_type j = param.find(' ');
			if(j == string::npos) {
				return;
			}

			User::NickIter i = users.find(fromNmdc(param.substr(0, j)));
			if(i == users.end()) {
				return;
			}

			u = i->second;
			if(!u->isSet(User::PASSIVE)) {
				u->setFlag(User::PASSIVE);
				up = true;
			}
		}

		if(u) {
			if(SETTING(CONNECTION_TYPE) == SettingsManager::CONNECTION_ACTIVE) {
				connectToMe(u);
				Speaker<NmdcHubListener>::fire(NmdcHubListener::RevConnectToMe(), this, u);
			} else {
				// Notify the user that we're passive too...
				if(up)
					revConnectToMe(u);
			}

			if(up)
				updated(u);
		}
	} else if(cmd == "$SR") {
		SearchManager::getInstance()->onSearchResult(aLine);
	} else if(cmd == "$HubName") {
		name = fromNmdc(param);
		Speaker<NmdcHubListener>::fire(NmdcHubListener::HubName(), this);
	} else if(cmd == "$Supports") {
		StringTokenizer<string> st(param, ' ');
		StringList& sl = st.getTokens();
		for(StringIter i = sl.begin(); i != sl.end(); ++i) {
			if(*i == "UserCommand") {
				supportFlags |= SUPPORTS_USERCOMMAND;
			} else if(*i == "NoGetINFO") {
				supportFlags |= SUPPORTS_NOGETINFO;
			} else if(*i == "UserIP2") {
				supportFlags |= SUPPORTS_USERIP2;
			}
		}
		Speaker<NmdcHubListener>::fire(NmdcHubListener::Supports(), this, sl);
	} else if(cmd == "$UserCommand") {
		string::size_type i = 0;
		string::size_type j = param.find(' ');
		if(j == string::npos)
			return;

		int type = Util::toInt(param.substr(0, j));
		i = j+1;
 		if(type == UserCommand::TYPE_SEPARATOR || type == UserCommand::TYPE_CLEAR) {
			int ctx = Util::toInt(param.substr(i));
			Speaker<NmdcHubListener>::fire(NmdcHubListener::UserCommand(), this, type, ctx, Util::emptyString, Util::emptyString);
		} else if(type == UserCommand::TYPE_RAW || type == UserCommand::TYPE_RAW_ONCE) {
			j = param.find(' ', i);
			if(j == string::npos)
				return;
			int ctx = Util::toInt(param.substr(i));
			i = j+1;
			j = param.find('$');
			if(j == string::npos)
				return;
			string name = fromNmdc(param.substr(i, j-i));
			i = j+1;
			string command = fromNmdc(param.substr(i, param.length() - i));
			Speaker<NmdcHubListener>::fire(NmdcHubListener::UserCommand(), this, type, ctx, Util::validateMessage(name, true, false), Util::validateMessage(command, true, false));
		}
	} else if(cmd == "$Lock") {
		if(state != STATE_LOCK) {
			return;
		}
		state = STATE_HELLO;

		if(!param.empty()) {
			string::size_type j = param.find(" Pk=");
			string lock, pk;
			if( j != string::npos ) {
				lock = param.substr(0, j);
				pk = param.substr(j + 4);
			} else {
				// Workaround for faulty linux hubs...
				j = param.find(" ");
				if(j != string::npos)
					lock = param.substr(0, j);
				else
					lock = param;
			}

			if(CryptoManager::getInstance()->isExtended(lock)) {
				StringList feat;
				feat.push_back("UserCommand");
				feat.push_back("NoGetINFO");
				feat.push_back("NoHello");
				feat.push_back("UserIP2");
				feat.push_back("TTHSearch");

				if(BOOLSETTING(COMPRESS_TRANSFERS))
					feat.push_back("GetZBlock");
				supports(feat);
			}

			key(CryptoManager::getInstance()->makeKey(lock));
			validateNick(getNick());

			Speaker<NmdcHubListener>::fire(NmdcHubListener::CLock(), this, lock, pk);	
		}
	} else if(cmd == "$Hello") {
		if(!param.empty()) {
			string nick = fromNmdc(param);
			User::Ptr u = ClientManager::getInstance()->getUser(nick, this);
			{
				Lock l(cs);
				users[nick] = u;
			}

			if(getNick() == nick) {
				setMe(u);

				u->setFlag(User::DCPLUSPLUS);
				if(SETTING(CONNECTION_TYPE) != SettingsManager::CONNECTION_ACTIVE)
					u->setFlag(User::PASSIVE);
				else
					u->unsetFlag(User::PASSIVE);
			}

			if(state == STATE_HELLO) {
				state = STATE_CONNECTED;
				updateCounts(false);

				version();
				getNickList();
				myInfo();
			}

			Speaker<NmdcHubListener>::fire(NmdcHubListener::Hello(), this, u);
		}
	} else if(cmd == "$ForceMove") {
		disconnect();
		Speaker<NmdcHubListener>::fire(NmdcHubListener::Redirect(), this, param);
	} else if(cmd == "$HubIsFull") {
		Speaker<NmdcHubListener>::fire(NmdcHubListener::HubFull(), this);
	} else if(cmd == "$ValidateDenide") {		// Mind the spelling...
		disconnect();
		Speaker<NmdcHubListener>::fire(NmdcHubListener::ValidateDenied(), this);
	} else if(cmd == "$UserIP") {
		if(!param.empty()) {
			User::List v;
			StringTokenizer<string> t(fromNmdc(param), "$$");
			StringList& l = t.getTokens();
			for(StringIter it = l.begin(); it != l.end(); ++it) {
				string::size_type j = 0;
				if((j = it->find(' ')) == string::npos)
					continue;
				if((j+1) == it->length())
					continue;
				v.push_back(ClientManager::getInstance()->getUser(it->substr(0, j), this));
				v.back()->setIp(it->substr(j+1));
			}

			Speaker<NmdcHubListener>::fire(NmdcHubListener::UserIp(), this, v);
		}
	} else if(cmd == "$NickList") {
		if(!param.empty()) {
			User::List v;
			StringTokenizer<string> t(fromNmdc(param), "$$");
			StringList& sl = t.getTokens();

			for(StringIter it = sl.begin(); it != sl.end(); ++it) {
				v.push_back(ClientManager::getInstance()->getUser(*it, this));
			}

			{
				Lock l(cs);
				for(User::Iter it2 = v.begin(); it2 != v.end(); ++it2) {
					users[(*it2)->getNick()] = *it2;
				}
			}
			
			if(!(getSupportFlags() & SUPPORTS_NOGETINFO)) {
				string tmp;
				// Let's assume 10 characters per nick...
				tmp.reserve(v.size() * (11 + 10 + getNick().length())); 
				for(User::List::const_iterator i = v.begin(); i != v.end(); ++i) {
					tmp += "$GetINFO ";
					tmp += (*i)->getNick();
					tmp += ' ';
					tmp += getNick(); 
					tmp += '|';
				}
				if(!tmp.empty()) {
					send(tmp);
				}
			} 

			Speaker<NmdcHubListener>::fire(NmdcHubListener::NickList(), this, v);
		}
	} else if(cmd == "$OpList") {
		if(!param.empty()) {
			User::List v;
			StringTokenizer<string> t(fromNmdc(param), "$$");
			StringList& sl = t.getTokens();
			for(StringIter it = sl.begin(); it != sl.end(); ++it) {
				v.push_back(ClientManager::getInstance()->getUser(*it, this));
				v.back()->setFlag(User::OP);
			}

			{
				Lock l(cs);
				for(User::Iter it2 = v.begin(); it2 != v.end(); ++it2) {
					users[(*it2)->getNick()] = *it2;
				}
			}
			Speaker<NmdcHubListener>::fire(NmdcHubListener::OpList(), this, v);
			updateCounts(false);
			// Special...to avoid op's complaining that their count is not correctly
			// updated when they log in (they'll be counted as registered first...)
			myInfo();
		}
	} else if(cmd == "$To:") {
		string::size_type i = param.find("From:");
		if(i != string::npos) {
			i+=6;
			string::size_type j = param.find("$");
			if(j != string::npos) {
				string from = fromNmdc(param.substr(i, j - 1 - i));
				if(from.size() > 0 && param.size() > (j + 1)) {
					Speaker<NmdcHubListener>::fire(NmdcHubListener::PrivateMessage(), this, ClientManager::getInstance()->getUser(from, this, false), Util::validateMessage(fromNmdc(param.substr(j + 1)), true));
				}
			}
		}
	} else if(cmd == "$GetPass") {
		setRegistered(true);
		Speaker<NmdcHubListener>::fire(NmdcHubListener::GetPassword(), this);
	} else if(cmd == "$BadPass") {
		Speaker<NmdcHubListener>::fire(NmdcHubListener::BadPassword(), this);
	} else if(cmd == "$LogedIn") {
		Speaker<NmdcHubListener>::fire(NmdcHubListener::LoggedIn(), this);
	} else {
		dcassert(cmd[0] == '$');
		dcdebug("NmdcHub::onLine Unknown command %s\n", aLine.c_str());
	} 
}