দৃষ্টি আকর্ষণীয় এবং স্বজ্ঞাত উপায়ে লেবেল ছড়িয়ে দেওয়ার জন্য অ্যালগরিদম


24

সংক্ষিপ্ত সংস্করণ

কোনও অ-ওভারল্যাপিং ফ্যাশনে যানবাহনের লেবেল বিতরণ করার জন্য, তারা যে যানবাহনটি উল্লেখ করেন তার যথাসম্ভব নিকটে রাখার জন্য কি কোনও নকশার প্যাটার্ন রয়েছে? যদি তা না হয় তবে আমি প্রস্তাবিত কোনও পদ্ধতি কি কার্যকর? আপনি কীভাবে এটি বাস্তবায়ন করবেন?

বর্ধিত সংস্করণ

গেমটিতে আমি লিখছি আমার বায়ুবাহিত যানগুলির একটি পাখির চোখ রয়েছে। আমার প্রতিটি গাড়ীর পাশে গাড়ি সম্পর্কিত কী-ডেটা সহ একটি ছোট লেবেল রয়েছে। এটি একটি আসল স্ক্রিনশট:

তাদের লেবেল সহ দুটি গাড়ি

এখন, যেহেতু যানবাহনগুলি বিভিন্ন উচ্চতায় উড়তে পারে, তাই তাদের আইকনগুলি ওভারল্যাপ করতে পারে। তবে আমি তাদের লেবেলগুলি কখনই ওভারল্যাপিং করতে চাই না (বা যানবাহন 'এ' থেকে একটি লেবেল 'বি' যানবাহনের আইকনটিকে ওভারল্যাপ করে)।

বর্তমানে, আমি স্প্রাইটের মধ্যে সংঘর্ষগুলি সনাক্ত করতে পারি এবং আমি অন্যথায়-ওভারল্যাপেড স্প্রাইটের বিপরীত দিকে আপত্তিজনক লেবেলটি দূরে ঠেলে দিই । এটি বেশিরভাগ পরিস্থিতিতে কাজ করে, কিন্তু যখন আকাশসীমা ভিড় করে, লেবেলটি তার যানবাহন থেকে খুব দূরে ঠেলাঠেলি করতে পারে , এমনকি যদি সেখানে বিকল্প "চৌকস" বিকল্প থাকত। উদাহরণস্বরূপ আমি পেয়েছি:

  B - label
A -----------label
  C - label

যেখানে এটি পেতে ভাল হবে (= গাড়ির কাছাকাছি লেবেল):

          B - label
label - A
          C - label

সম্পাদনা: এটিকেও বিবেচনা করতে হবে যে ওভারল্যাপিং যানবাহনের ক্ষেত্রে, অন্যান্য কনফিগারেশন থাকতে পারে যাতে যানবাহনগুলি ওভারল্যাপ করতে পারে (ASCII- শিল্প উদাহরণগুলি উদাহরণস্বরূপ তিনটি খুব কাছাকাছি যানবাহন দেখায় যার লেবেলের Aআইকনটি ওভারল্যাপ করে Bএবং C)।

বর্তমান পরিস্থিতিটি কীভাবে উন্নত করা যায় সে সম্পর্কে আমার দুটি ধারণা রয়েছে তবে সেগুলি বাস্তবায়নে সময় ব্যয় করার আগে আমি পরামর্শের জন্য সম্প্রদায়ের দিকে ফিরতে ভেবেছিলাম (সর্বোপরি এটি "সাধারণ যথেষ্ট সমস্যা" বলে মনে হচ্ছে এটির জন্য একটি নকশার প্যাটার্ন বিদ্যমান থাকতে পারে)।

এটির মূল্যের জন্য, আমি যে দুটি ধারণাটি ভাবছিলাম তা এখানে:

লেবেল জায়গার স্লট-আইসেশন

এই পরিস্থিতিতে আমি সমস্ত স্ক্রিনটি লেবেলের জন্য "স্লট" এ ভাগ করব divide তারপরে, প্রতিটি যানবাহনের সর্বদা তার লেবেলটি নিকটতম শূন্য একটিতে (ফাঁকা = কোনও স্থানে অন্য স্প্রাইটে) রাখা উচিত।

সর্পিল অনুসন্ধান

স্ক্রিনে গাড়ির অবস্থান থেকে, লেবেলটি বর্ধমান কোণে এবং তারপরে ক্রমবর্ধমান রেডিওগুলিতে রাখার চেষ্টা করব, যতক্ষণ না কোনও ওভারল্যাপিং অবস্থান না পাওয়া যায়। এর লাইনে কিছু রয়েছে:

try 0°, 10px
try 10°, 10px
try 20°, 10px
...
try 350°, 10px
try 0°, 20px
try 10°, 20px
...

1
একসাথে কয়টি প্লেন ওভারল্যাপ হতে পারে?
ওয়াংবার্গার

1
@ ওয়াংবার্গার - কখনও ভাবেন নি যে এটি প্রাসঙ্গিক হবে (আপনার চিন্তার রেখাটি সম্পর্কে আরও জানতে আগ্রহী হবে), তবে উত্তরটি হ'ল: এটি প্লেয়ারের গেম কৌশল থেকে নির্ভর করে। প্রযুক্তিগতভাবে বিশ্বে 24 টি গাড়ি ওভারল্যাপিং থাকতে পারে, তবে বেশিরভাগ গেমের অবস্থার মধ্যে একটি বাস্তব চিত্রটি 3-4 হয়।
ম্যাক 15

3
ওভারল্যাপিংয়ের চেয়ে বরং যুক্তিসঙ্গত সময়ের জন্য স্থিতাবস্থাগুলির চেয়ে চলমান লেবেলগুলি থাকা কি আরও বিভ্রান্তিকর নয়?
মাইক সেমদার

3
আপনি en.wikedia.org/wiki/… এ আগ্রহী হতে পারেন - এটি সমাধান করা খুব সহজ সমস্যা নয়। একটি নিখুঁত সমাধানের আশা করবেন না।
ব্লেকি

2
লেবেলে ওভারল্যাপ এড়ানোর প্রবণতা সহ গ্রাফভিজ দৃশ্যমান উপায়ে গ্রাফগুলি রাখার জন্য সরঞ্জামগুলির একটি স্যুট। এটি সরাসরি ব্যবহারযোগ্য না হলেও, আপনি তাদের ডকুমেন্টেশন বা সোর্স কোড থেকে কিছু ধরণের তথ্য সংগ্রহ করতে সক্ষম হতে পারেন যা তারা গ্রাফগুলি বিন্যাস করতে কোন ধরণের অ্যালগরিদম ব্যবহার করে। উদাহরণস্বরূপ, তাদের কাছে শক্তি-ভিত্তিক মডেল এবং বসন্ত-ভিত্তিক মডেল দুটি রয়েছে বলে মনে হয়।
লার্স ভিক্লুন্ড

উত্তর:


14

মূলত এই সমস্যাটি সংঘর্ষ এড়ানোর সমস্যার সাথে সমান। হ্যাঁ, বিমানগুলি বিভিন্ন উচ্চতায় উড়তে পারে তবে তাদের লেবেলগুলি একই "উচ্চতায়" রয়েছে।

আনইনেলাইনড ক্লিভিশন এড়য়েডেন্সের মতো অ্যালগরিদম রয়েছে , এটি আপনার পক্ষে সঠিক দিকের একটি পদক্ষেপ হবে। অবশ্যই আপনার পরিস্থিতির জন্য, লেবেলগুলি তাদের বিমানগুলিতে "টিচার্ড" রয়েছে, সুতরাং তাদের সীমিত পরিসর চলবে।

যদি আপনি ফ্লকিং আচরণের দিকে তাকান , আপনি ঝাঁকুনির প্রথম "বিধি" প্রয়োগ করতে চান: স্বল্প পরিসীমা বিকর্ষণ। তবে নিকটবর্তী প্রতিবেশীদের থেকে দূরে থাকা দিকটিতে "স্টিয়ারিং" পরিবর্তে আপনি "লেবেল" ভেক্টরটিকে আপনার লেবেলের স্থান নির্ধারণের স্থান হিসাবে ব্যবহার করবেন।

উদাহরণ স্বরূপ:

এখানে চিত্র বর্ণনা লিখুন

বৃহত্তর কালো চেনাশোনা আপনার প্রভাবের ক্ষেত্রকে প্রতিনিধিত্ব করে, সবুজ বৃত্তটি লেবেলের জন্য বৈধ স্থান নির্ধারণ করে, কেন্দ্রের সবুজ বিন্দুটি বর্তমানে আপনার বিবেচিত বিমানটি, ছোট সবুজ বিন্দু লেবেল স্থাপনের জন্য নির্বাচিত চেনাশোনাটির মূল বিষয়।

এখন কালো বিন্দুগুলি অন্য লেবেল বা অন্য প্লেনগুলির প্রতিনিধিত্ব করতে পারে। কোনটি সবচেয়ে ভাল কাজ করবে তা সম্পর্কে আমি নিশ্চিত নই, যদি তারা অন্য লেবেল হয় তবে আপনি আরও ভাল এড়াতে পারেন, তবে আমি নিশ্চিত নই। স্পষ্টতই "ফোর্স" তীরগুলি হ'ল আপনার বর্তমান বিমান এবং "প্রভাবের বস্তু "গুলির মধ্যে দিকের ভেক্টর। অবশেষে, বাক্সটি হ'ল লেবেল।

সুতরাং উপরে আপনার উদাহরণ ব্যবহার করে, আমি মনে করি এটি এর মতো কিছু তৈরি করবে:

            - label
           / 
          B 
label - A
          C 
           \
            - label

এই পদ্ধতিটি ব্যবহার করে কিছু পরিস্থিতি রয়েছে যা আপনাকে তিনটি প্লেনের মতো উল্লম্বভাবে সারিবদ্ধভাবে তৈরি করতে হবে:

          - label       label -
          |                   |
          B                   B
  label - A                   A - label
          C                   C
          |                   |
          - label       label -

আপনার লেবেল কোণগুলি কীভাবে সংজ্ঞায়িত করা হয়েছে তার উপর নির্ভর করে সমস্ত তিনটি লেবেল ডান থেকে বামে ফ্লপ করতে পারে। মূলত, আপনাকে কেবলমাত্র বৃত্তের চারপাশের কোণগুলির জন্য নজর রাখতে হবে যেখানে আপনার লেবেলগুলি কোন কোণটি সরিয়ে নিয়ে যেতে পারে: 0, 90, 180, 270:

এখানে চিত্র বর্ণনা লিখুন

আমি মনে করি শেষ পর্যন্ত, এটি একরকম ঝরঝরে দেখবে, লেবেলগুলি একে অপরকে এড়ানো দেখছে। যদি এটি খুব বিভ্রান্তিকর হয়ে ওঠে, সম্ভবত আপনি কম ঘন ঘন চলাচলের জন্য নিকটস্থ 10 ডিগ্রি পর্যন্ত গোল করতে পারেন।

অদ্ভুত বিবরণের জন্য দুঃখিত, আমি যখন আমার গেমটির জন্য একটি রেডিয়াল মেনু তৈরি করছিলাম তখন এই জিনিসগুলির বেশিরভাগটি আমি ভেবেছিলাম তবে আমি মনে করি এই "গতিশীল" ফর্মটি এটি বেশ ভালভাবে কাজ করবে।


1
প্রকৃতপক্ষে আমার উদাহরণ এমনকি একে অপরের শীর্ষে থাকা অ্যাকাউন্ট প্লেনগুলিতেও নেয়নি, যেমনটি তাদের এক্স এবং জেড স্থানাঙ্কে ঠিক মেলে (তবে আপনি যদি ভাসা ব্যবহার করছেন তবে সম্ভবত এটি ঘটবে না)। আমি যে উদাহরণগুলি দিয়েছি তা হ'ল একে অপরের কাছে বিমানগুলি। অতিরিক্ত হিসাবে, আপনি যেমনটি বলেছিলেন, উপরের চিত্রের কালো বিন্দাগুলি অন্যান্য লেবেল হিসাবে ভাবতে পারেন।
MichaelHouse

1
ওহ, আপনি আপনার মন্তব্য মুছে ফেলা হয়েছে?
মাইকেলহাউস

1
আমার পূর্ববর্তী [দুর্বল সূত্রবদ্ধ এবং এভাবে মুছে ফেলা] মন্তব্যটির অর্থ আমি কী বোঝাতে চেয়েছি তা হ'ল আপনি এমন একটি দৃশ্যের মুখোমুখি হতে পারেন যাতে অন্য অস্থাবর (অর্থাত্ যানবাহন) স্প্রাইট দ্বারা কোনও লেবেল "আটকা / ঘেরা" থাকে। এই ক্ষেত্রে লেবেলটি সম্ভবত ঘেরের বৃত্তের বাইরে "লাফানো" উচিত, তবে এটি কীভাবে হওয়া উচিত তা আমার কাছে ঠিক পরিষ্কার নয়। বিটিডাব্লু: আমি মূলত যদিও আপনার ছবির সবুজ বিন্দুতে বেশ কয়েকটি বিমান ছিল অন্যটির উপরে একটি স্তুপীকৃত, তবে আপনার মন্তব্যের পরে আমি বুঝতে পারি যে আমি ভুল ছিল ... দুঃখিত!)।
ম্যাক

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

9

কিছু চিন্তাভাবনা করার পরে, অবশেষে আমি মূল প্রশ্নে সংক্ষিপ্তভাবে বর্ণনা করা সর্পিল অনুসন্ধান পদ্ধতিটি প্রয়োগ করার সিদ্ধান্ত নিয়েছি ।

যুক্তিটি হ'ল বাইট 5 এর পদ্ধতিতে কিছু শর্তের জন্য বিশেষ চিকিত্সার প্রয়োজন হয়, যখন স্প্রিলিং অনুসন্ধান অনুসন্ধান করে না এবং এটি একটি সত্যই সংক্ষিপ্ত উপায়ে কোড করে । এছাড়াও, ছড়িয়ে পড়া অনুসন্ধান লেবেল স্থাপনের জন্য গাড়ির নিকটতম জায়গাটি অনুসন্ধানের উপর জোর দেয় , যা মানচিত্রটি পাঠযোগ্য করে তোলার প্রধান বিষয় আইএমও।

তবে দয়া করে তার উত্তরটিকে উঁচু করে চালিয়ে যান, কারণ এটি কেবল কার্যকর নয়, এটি খুব ভালভাবে লেখাও রয়েছে!

সর্পিলিং কোডের সাথে প্রাপ্ত ফলাফলটির একটি স্ক্রিনশট এখানে:

এখানে চিত্র বর্ণনা লিখুন

এবং কোডটি এখানে - যা স্ব-অন্তর্ভুক্ত নয় - এটি বাস্তবায়ন কতটা সহজ তা সম্পর্কে একটি ধারণা দেয়:

def place_tags(self):
    for tag in self.tags:
        start_angle = tag.angle
        while not tag.place() or is_colliding(tag):  #See note n.1
            tag.angle = (tag.angle + angle_step) % 360
            if tag.angle == start_angle:
                tag.radius += radius_step
        tag.connector.update()                       #See note n.2

নোট 1 - tag.place()ট্যাগটি পুরোপুরি স্ক্রিন / রাডারের দৃশ্যমান স্থানে থাকলে সত্যটি ফিরে আসে। সুতরাং সেই লাইনটি এমন লেখা পড়ে "ট্যাগটি রাডারের বাইরে থাকলে বা এটি অন্য কোনও কিছুকে ওভারল্যাপ করে যদি লুপিং চালিয়ে যান ..."

নোট 2 - tag.connector.updateহ'ল পদ্ধতিটি যা পাঠ্য তথ্যের সাথে লেবেল / ট্যাগের সাথে বিমানের আইকনটি সংযুক্ত করে লাইন আঁকবে।


ভাল, সত্যিই খুব কমপ্যাক্ট। প্রশংসা করার জন্য ধন্যবাদ। এছাড়াও আপনি কী শেষ করেছেন তা পোস্ট করার জন্য ধন্যবাদ, এটি উত্তরগুলির জন্য পরে অনুসন্ধান করার জন্য সর্বদা দরকারী। স্ক্রিনশট থেকে দেখে মনে হচ্ছে এটি খুব ভালভাবে কাজ করছে! আপনার উত্তরটি গ্রহণ করার বিষয়ে নিশ্চিত হোন, আপনি যা দিয়ে শেষ করেছেন ঠিক তেমনই।
MichaelHouse

@ বাইট 55 - "বিপরীতমুখী প্রশংসা" এর জন্য ধন্যবাদ;) আমি উত্তরটি গ্রহণযোগ্য হিসাবে বাছাইয়ের জন্য অপেক্ষা করছি কারণ আমি এখনও আপনার সমাধানটি কোড করতে এবং ফলাফলটির সাথে তুলনা করতে চাই। একটির জন্য, আমি সন্দেহ করি যে আপনার সমাধানটি কার্যকর করতে দীর্ঘতর তবে দ্রুত কোডও পেতে পারে। এছাড়াও, আমি দেখতে চাই যে কীভাবে দু'জন খুব ক্র্যামড আকাশসীমাতে তুলনা করে ... তাই এখনও একটি সুযোগ আছে যা আমি আপনার অ্যালগরিদমের সাথে কোডটি প্রকাশ করতে পারি। এই জায়গা দেখুন! ;)
ম্যাক

@ বাইট ৫5 - আপনার অ্যালগরিদমটি কার্যকর করতে আমার একযোগে যেতে হয়েছিল। এটি কম ঘনত্বগুলিতে সূক্ষ্ম এবং দ্রুত কাজ করেছিল, তবে স্থান ক্র্যাশ হওয়ার সাথে সাথে আমার একটি সরল বাস্তবায়ন খুঁজে পেতে সমস্যা হয়েছিল যা নির্দিষ্ট পরিস্থিতিতে পরিচালনা করতে পারে যেখানে একটি লেবেল অন্যান্য লেবেলের একটি ব্লক "লাফিয়ে" পড়ে বা অ-দ্বারা আটকা পড়ে যায় manage চলনযোগ্য (অর্থাত্ বিমানের আইকন) স্প্রিট। আমি এই উত্তরটিকে তখন নির্বাচিত হিসাবে চিহ্নিত করছি, তবে আবার: সময় এবং অবদানের জন্য অনেক ধন্যবাদ! :)
ম্যাক
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.