স্ক্রিনের বাইরে থাকা কোনও বস্তুর প্রতি ইশারা করে আমি কীভাবে পর্দার প্রান্তে একটি তীর আঁকব?


12

আমি এই বিষয়ে বর্ণিত যা করতে ইচ্ছুক:

http://www.allegro.cc/forums/print-thread/283220

আমি এখানে উল্লিখিত বিভিন্ন পদ্ধতির চেষ্টা করেছি।

প্রথমে আমি ক্যারাস 85 দ্বারা বর্ণিত পদ্ধতিটি ব্যবহার করার চেষ্টা করেছি:

কেবলমাত্র দুটি ত্রিভুজ হাইপোনটেনাসের অনুপাত নিন (আপনি অন্যটির জন্য কোন ত্রিভুজ ব্যবহার করেন তা বিবেচনাধীন নয়, আমি বিন্দু 1 এবং পয়েন্ট 2 কে আপনি যে দূরত্ব হিসাবে গণনা করছেন তা প্রস্তাব করি)। এটি আপনাকে বৃহত্তর ত্রিভুজ থেকে কোণে ত্রিভুজটির অনুপাতের শতাংশ দেবে। তারপরে আপনি কেবল এক্স-কো-অর্ডিনেট অফসেট পেতে সেই মানটি দিয়ে ডেল্ট্যাক্সকে এবং গুণমান দ্বারা ডেল্টে y- সমন্বিত অফসেট পাবেন।

তবে বস্তুটি পর্দার প্রান্ত থেকে কতটা দূরে রয়েছে তা গণনার কোনও উপায় আমি খুঁজে পাইনি।

আমি তারপরে রাই কাস্টিং ব্যবহার করার চেষ্টা করেছি (যা আমি এর আগে কখনও করিনি) 23 ইয়ারল্ড 3 ইয়ারল্ড প্রস্তাবিত:

স্ক্রিনের কেন্দ্র থেকে অফস্ক্রিন অবজেক্টে একটি রশ্মি ফায়ার করুন। আয়তক্ষেত্রে কোথায় রে ছেদ করে সেখানে গণনা করুন। আপনার স্থানাঙ্ক আছে।

আমি প্রথমে দুটি পয়েন্টের x এবং y অবস্থানের পার্থক্যের দ্বারা গঠিত ত্রিভুজের হাইপোপেনিউজ গণনা করেছি। আমি এই লাইন বরাবর ইউনিট ভেক্টর তৈরি করতে এটি ব্যবহার করেছি। আমি এক্সটিউন্ডেট বা y স্থানাঙ্ক স্ক্রিনটি বন্ধ না হওয়া পর্যন্ত আমি সেই ভেক্টরটির মধ্য দিয়ে লুপ করেছি। দুটি বর্তমান x এবং y মানগুলি তীরের x এবং y গঠন করে।

আমার রশ্মির castালাই পদ্ধতির কোড এখানে (সি ++ এবং অ্যালেগ্রো 5 এ লিখিত)

void renderArrows(Object* i)
{
    float x1 = i->getX() + (i->getWidth() / 2);
    float y1 = i->getY() + (i->getHeight() / 2);

    float x2 = screenCentreX;
    float y2 = ScreenCentreY;

    float dx = x2 - x1;
    float dy = y2 - y1;
    float hypotSquared = (dx * dx) + (dy * dy);
    float hypot = sqrt(hypotSquared);

    float unitX = dx / hypot;
    float unitY = dy / hypot;

    float rayX = x2 - view->getViewportX();
    float rayY = y2 - view->getViewportY();
    float arrowX = 0;
    float arrowY = 0;

    bool posFound = false;
    while(posFound == false)
    {
        rayX += unitX;
        rayY += unitY;

        if(rayX <= 0 ||
            rayX >= screenWidth ||
            rayY <= 0 ||
            rayY >= screenHeight)
        {
            arrowX = rayX;
            arrowY = rayY;
            posFound = true;
        }               
    }

    al_draw_bitmap(sprite, arrowX - spriteWidth, arrowY - spriteHeight, 0);
}

এটি তুলনামূলকভাবে সফল ছিল। পর্দার উপরের এবং বামদিকে বস্তুগুলি অবস্থিত হলে তীরগুলি স্ক্রিনের নীচের ডান অংশে প্রদর্শিত হয় যেমন তীরগুলি আঁকানো হয়েছে তার অবস্থানগুলি পর্দার কেন্দ্রের চারপাশে 180 ডিগ্রি ঘোরানো হয়েছে।

আমি ধরে নিয়েছি এটি এই কারণে হয়েছিল যে যখন আমি ত্রিভুজটির অনুমানের গণনা করছিলাম, তখন x এর পার্থক্য বা y এর পার্থক্য নেতিবাচক হোক না কেন এটি সর্বদা ইতিবাচক হবে।

এটি সম্পর্কে চিন্তাভাবনা করে, রশ্মি ingালাই সমস্যাটি সমাধানের ভাল উপায় বলে মনে হচ্ছে না (এটি স্কয়ারটি () এবং লুপের জন্য একটি বৃহত ব্যবহার করে জড়িত থাকার কারণে)।

উত্তর:


6

সুতরাং আপনার দুটি স্থানাঙ্ক বা ভেক্টর রয়েছে, একটি হ'ল পর্দার কেন্দ্র (এখন থেকে সি) এবং অন্যটি আপনার অবজেক্ট (এখন থেকে পি))

আপনি যদি কিছু গণিত জানেন তবে আপনি হয়ত জানেন যে একটি লাইন একটি উত্স এবং দিক ভেক্টর হিসাবে প্রকাশ করা যেতে পারে। উত্সটি আপনার স্ক্রিন-কেন্দ্র, যখন দিক ভেক্টর পি থেকে সি বিয়োগ করে পাওয়া যায় This এই সমীকরণটি প্যারাম্যাট্রিক আকারেও প্রকাশ করা যেতে পারে যা মূলত একই:

x = (P.x - C.x)t + C.x;
y = (P.y - C.y)t + C.y;

(P.? - C.?)কিছুটা দেখুন ? এটি আপনার দিকের ভেক্টর (যেমনটি আমি বলেছি, পি থেকে সি বিয়োগ)। শেষ C.?বিট লাইনের উত্স।

tএকটি পরিবর্তনশীল যা থেকে পৃথক হতে পারে 0জন্য 1, 0ভেক্টর উৎপত্তি হচ্ছে (যদি আপনি চালনা, xএবং yপরিণত woulld C.xএবং C.y), 1আপনার বস্তুর তুল্য হচ্ছে (আবার, অপারেটিং, এটা পরিণত চাই P.xএবং P.y, বা ভেক্টরের "শেষ", যদি আপনি চান) এবং আপনার সেগমেন্টের উভয় প্রান্তের মধ্যে ইন্টারপোলটিংয়ের মধ্যে মানগুলি। আপনি বাহ্যিক মানগুলিও বরাদ্দ করতে পারেন: নীচে 0আপনি আপনার ভেক্টরটির দিকটি বিপরীত দিকে 1পাবেন এবং উপরে আপনি একইভাবে আপনার ভেক্টরকে আরও "প্রসারিত" করতে পারবেন।

এটি একবার পেয়ে গেলে এটি বেশ সহজ হয়ে যায়। আপনার উদ্দেশ্য হ'ল এই ভেক্টরের বিন্দুটি অনুসন্ধান করা ( xএবং yপ্রদত্ত মানের জন্য t) কোথায় X=WIDTHবা Y=HEIGHT, যা কিছু আগে আসে। আপনি দেখতে পাচ্ছেন, tএখানে আপনার একমাত্র পরিবর্তনশীল:

(0)
WIDTH = (P.x - C.x)t + C.x;
and
HEIGHT = (P.y - C.y)t + C.y;

বা এটি পুনরায় প্রকাশ:

(1)
t = (WIDTH - C.x)/(P.x - C.x)
and
t = (HEIGHT - C.y)/(P.y - C.y)

এটি আপনার ডান এবং উপরের সীমানায় আপনার ভেক্টর দ্বারা সংজ্ঞায়িত রেখার কাটিয়াঙ্কনটি পাবেন। আপনার পর্দার বাম এবং নীচের সীমানার ক্ষেত্রেও এটি একই রকম হয়, যেখানে আপনাকে 0উভয় ক্ষেত্রেই পরীক্ষা করতে হবে , না WIDTHএবং HEIGHT

যেহেতু এটি শেষ পর্যন্ত সীমানাগুলি, এমনকি স্ক্রিনের বাইরেও কেটে ফেলবে, তাই সর্বনিম্ন tমানটি আপনার যোগাযোগের প্রথম পয়েন্ট হবে। ক্রিয়াকলাপটি বিপরীত tকরা এবং সমীকরণগুলিতে (0)(উভয়ের জন্য একই মানের!) আপনার সন্ধান করা মান প্রয়োগ করা একটি নতুন আনবে (x,y)যা আপনার কাটা স্থানাঙ্ক হবে।

আপনার সমস্যার জন্য কিছু গণিত ত্রুটি বা প্রয়োগের পার্থক্য থাকতে পারে, তবে এটি মূল ধারণা। আমি কিছু অংশ খুব বাইরে রেখেছি (সবসময় কাটার চারটি কেস থাকে, এবং আপনার কেবল একটি প্রয়োজন) তবে কিছুটা চিন্তা আপনাকে চূড়ান্ত সমাধানে নিয়ে যাবে :)


ধন্যবাদ। আমি এক বার যেতে হবে। সম্পাদনা: কৌতূহলের বাইরে, আপনি কি মনে করেন যে এই পদ্ধতিটিই কারাস ৮৮ বর্ণিত (অনুমানের অনুপাত ব্যবহার করে) বর্ণনা করেছেন?
অ্যাডাম হেন্ডারসন

1
@ অ্যাডামহেন্ডারসন আমি সাহায্য করে আনন্দিত :) মনে রাখবেন আপনি আপনার দিকনির্দেশক ভেক্টর রাখতে পারেন যাতে আপনি পরে তীরটি আঁকতে পারেন। আপনি আপনার একক দিকনির্দেশক ভেক্টরটি পেতে এটি স্বাভাবিক করতে পারেন, arrow-lengthকাটিং ভেক্টর "এট ভয়েলা" থেকে বার বার বিয়োগ করুন , আপনার তীরটির একটি উত্স এবং গন্তব্য রয়েছে।
KaoD

1
@ অ্যাডামহেন্ডারসন দৃশ্যত এটি একই জিনিস, যেহেতু আপনার লাইনটি তিনি যে অনুমানের কথা বলছেন is ব্যবহারিকভাবে, এটি একই নয়, যেহেতু তাঁর পরামর্শে কোণগুলি অন্তর্ভুক্ত রয়েছে (এবং তাই ত্রিকোণমিতি) যা আমি মনে করি যে এটির জন্য ওভারকিল। এটি মোটেও ত্রিভুজগুলিকে জড়িত করে না (যদিও আপনি নিজের ভেক্টরটিকে ত্রিভুজ হিসাবে ভাবতে পারেন যেখানে xy
অনুভূতি

আবার ধন্যবাদ! তীরটি সঠিক দিকে নির্দেশ করার জন্য আপনি আমার পরবর্তী সমস্যাটি সমাধান করেছেন।
অ্যাডাম হেন্ডারসন

1
@ অ্যাডামহেন্ডারসন হ্যাঁ, নীচে যদি অক্ষ ফ্লিপ করা হয়। বিটিডাব্লু, আমি ভবিষ্যতের রেফারেন্সের জন্য এ্যালিগ্রোর ফোরামে এই প্রশ্নের লিঙ্ক পোস্ট করার পরামর্শ দেব।
কাওড
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.